首页
社区
课程
招聘
[旧帖] [求助]Hook SSDT 偶现蓝屏, 请高手帮忙分析下, 实在找不到原因了. 0.00雪花
发表于: 2014-1-6 15:17 1749

[旧帖] [求助]Hook SSDT 偶现蓝屏, 请高手帮忙分析下, 实在找不到原因了. 0.00雪花

2014-1-6 15:17
1749
不多废话, 下面是dump文件信息:

Microsoft (R) Windows Debugger Version 6.11.0001.404 X86
Copyright (c) Microsoft Corporation. All rights reserved.

Loading Dump File [C:\Users\Administrator\Desktop\Driver-Tools-admin\Dump\ysy-2014-01-06.dmp]
Mini Kernel Dump File: Only registers and stack trace are available

Symbol search path is: srv*F:\Driver-Debug\NtSymbol*http://msdl.microsoft.com/download/symbols;C:\Users\Administrator\Desktop\Driver-Tools-admin\Sys
Executable search path is: C:\Users\Administrator\Desktop\Driver-Tools-admin\Sys
Windows 7 Kernel Version 7601 (Service Pack 1) MP (4 procs) Free x86 compatible
Product: WinNt, suite: TerminalServer SingleUserTS
Built by: 7601.17514.x86fre.win7sp1_rtm.101119-1850
Machine Name:
Kernel base = 0x8400b000 PsLoadedModuleList = 0x84155850
Debug session time: Mon Jan  6 14:42:18.948 2014 (GMT+8)
System Uptime: 0 days 6:18:30.337
Loading Kernel Symbols
...............................................................
................................................................
.........
Loading User Symbols
Loading unloaded module list
..........
2: kd> !analyze -v
*******************************************************************************
*                                                                             *
*                        Bugcheck Analysis                                    *
*                                                                             *
*******************************************************************************

PAGE_FAULT_IN_NONPAGED_AREA (50)
Invalid system memory was referenced.  This cannot be protected by try-except,
it must be protected by a Probe.  Typically the address is just plain bad or it
is pointing at freed memory.
Arguments:
Arg1: ce93d000, memory referenced.
Arg2: 00000001, value 0 = read operation, 1 = write operation.
Arg3: 840447f3, If non-zero, the instruction address which referenced the bad memory
        address.
Arg4: 00000000, (reserved)

Debugging Details:
------------------

Unable to load image \??\C:\Windows\System32\drivers\Yb_Process.sys, Win32 error 0n2
*** WARNING: Unable to verify timestamp for Yb_Process.sys
*** WARNING: Unable to verify timestamp for TSKsp.sys
*** ERROR: Module load completed but symbols could not be loaded for TSKsp.sys
*** WARNING: Unable to verify timestamp for TsFltMgr.sys
*** ERROR: Module load completed but symbols could not be loaded for TsFltMgr.sys

WRITE_ADDRESS: GetPointerFromAddress: unable to read from 84175718
Unable to read MiSystemVaType memory at 841551a0
ce93d000

FAULTING_IP:
nt!memcpy+33
840447f3 f3a5            rep movs dword ptr es:[edi],dword ptr [esi]

MM_INTERNAL_CODE:  0

CUSTOMER_CRASH_COUNT:  6

DEFAULT_BUCKET_ID:  COMMON_SYSTEM_FAULT

BUGCHECK_STR:  0x50

PROCESS_NAME:  YBOSProtect.ex

CURRENT_IRQL:  0

TRAP_FRAME:  a1891964 -- (.trap 0xffffffffa1891964)
ErrCode = 00000002
eax=892e85dc ebx=00000000 ecx=00000048 edx=00000000 esi=892e84bc edi=ce93d000
eip=840447f3 esp=a18919d8 ebp=a18919e0 iopl=0         nv up ei pl nz ac po nc
cs=0008  ss=0010  ds=0023  es=0023  fs=0030  gs=0000             efl=00010212
nt!memcpy+0x33:
840447f3 f3a5            rep movs dword ptr es:[edi],dword ptr [esi]
Resetting default scope

LAST_CONTROL_TRANSFER:  from 8404c3d8 to 8409941b

STACK_TEXT:  
a189194c 8404c3d8 00000001 ce93d000 00000000 nt!MmAccessFault+0x106
a189194c 840447f3 00000001 ce93d000 00000000 nt!KiTrap0E+0xdc
a18919e0 a139cc46 ce93ce04 892e82c0 0000031c nt!memcpy+0x33
a1891a28 a139d3c6 8990e350 87657190 ce924000 Yb_Process!SfGetCurrentProcFile+0x1f6 [e:\ybworkspace\example\watchprocess\driverprocess\driverprocess.c @ 1363]
a1891a60 84042593 8990e350 87657190 87657190 Yb_Process!SfSetInterestFile+0x226 [e:\ybworkspace\example\watchprocess\driverprocess\driverprocess.c @ 1681]
a1891a78 8423699f 875d1878 87657190 87657200 nt!IofCallDriver+0x63
a1891a98 84239b71 8990e350 875d1878 00000000 nt!IopSynchronousServiceTail+0x1f8
a1891b34 842803f4 8990e350 87657190 00000000 nt!IopXxxControlFile+0x6aa
a1891b68 939b6a46 000002c8 00000000 00000000 nt!NtDeviceIoControlFile+0x2a
WARNING: Stack unwind information not available. Following frames may be wrong.
a1891bb0 8d53ff4e 000002c8 00000000 00000000 TSKsp+0x14a46
a1891c04 840491ea 000002c8 00000000 00000000 TsFltMgr+0x4f4e
a1891c04 778870b4 000002c8 00000000 00000000 nt!KiFastCallEntry+0x12a
01c1c618 00000000 00000000 00000000 00000000 0x778870b4

STACK_COMMAND:  kb

FOLLOWUP_IP:
Yb_Process!SfGetCurrentProcFile+1f6 [e:\ybworkspace\example\watchprocess\driverprocess\driverprocess.c @ 1363]
a139cc46 ??              ???

FAULTING_SOURCE_CODE:  
  1359:
  1360:         IoCompleteRequest(pIrp, IO_NO_INCREMENT);
  1361:
  1362:         return STATUS_SUCCESS;
> 1363: }
  1364:
  1365: NTSTATUS
  1366: SfGetCurrentProcSection(PDEVICE_OBJECT DeviceObject, PIRP pIrp, PVOID pIoBuffer)
  1367: {
  1368:         ULONG i = 0;

SYMBOL_STACK_INDEX:  3

SYMBOL_NAME:  Yb_Process!SfGetCurrentProcFile+1f6

FOLLOWUP_NAME:  MachineOwner

MODULE_NAME: Yb_Process

IMAGE_NAME:  Yb_Process.sys

DEBUG_FLR_IMAGE_TIMESTAMP:  52c7617c

FAILURE_BUCKET_ID:  0x50_Yb_Process!SfGetCurrentProcFile+1f6

BUCKET_ID:  0x50_Yb_Process!SfGetCurrentProcFile+1f6

Followup: MachineOwner
---------

对应的SfGetCurrentProcFile的源码如下:

NTSTATUS
SfGetCurrentProcFile(PDEVICE_OBJECT DeviceObject, PIRP pIrp, PVOID pIoBuffer)
{
        ULONG i = 0;
        ULONG r = 0;

        PUSER_FILE_DATA   pUserFileData = (PUSER_FILE_DATA)pIoBuffer;
        POP_FILE_SET_NODE pNode         = g_p_opened_file_list->NodeHead;
        PFILE_DATA_NODE   pNodeFileData = NULL;
        PCHAR             pTempo        = NULL;

        __try
        {
                // 拷贝驱动层监控数据到上层数据缓存区
                while (pNode != NULL)
                {
                        pNodeFileData = pNode->FileOPSet.FileDataList.NodeHead;

                        while (pNodeFileData != NULL)
                        {
                                pTempo = strrchr((CHAR*)pNodeFileData->FileData.FilePath, '\\');       

                                if (pTempo != NULL && (pTempo + 1) != NULL)
                                {
                                        // "Office"系列软件会生成的临时文件不应该上传给上层
                                        if (pTempo[1]  == '~' && pTempo[2] == '$')
                                        {
                                                pNodeFileData = pNodeFileData->NodeNext;

                                                continue;
                                        }
                                }

                                // "Explore"打开的文件不应该上传给上层
                                // ...

                                // 已经上传的文件不用再次上传
                                if (pNodeFileData->FileData.Saved)
                                {
                                        pNodeFileData = pNodeFileData->NodeNext;

                                        continue;
                                }

                                // 置上传标志位
                                pNodeFileData->FileData.Saved = TRUE;
                               
                                if (!MmIsAddressValid(pNodeFileData)                 ||
                                        !MmIsAddressValid(&pUserFileData->FileObject[i]) ||
                                        !MmIsAddressValid(&pNodeFileData->FileData))
                                {
                                        DbgPrint(("YUBAN.FILEWATCH.DRIVER <<<<<< !SfGetCurrentProcFile ------ Check params is fails! ------ >>>>>>"));

                                        goto Leave;
                                }

                                // 内存拷贝
                                RtlCopyMemory(&pUserFileData->FileObject[i], &pNodeFileData->FileData, sizeof(OP_FILE));

                                // 自增量
                                i++;

                                // 移向下一个数据节点
                                pNodeFileData = pNodeFileData->NodeNext;

                                r = r + sizeof(OP_FILE);
                        }

                        pNode = pNode->NodeNext;
                }

                pUserFileData->Count = i;
        }
        __except(EXCEPTION_EXECUTE_HANDLER)
        {
                r = 0;

                DbgPrint(("YUBAN.FILEWATCH.DRIVER <<<<<< !SfGetCurrentProcFile ------ Exception: Catch Error ------ >>>>>>"));
        }

Leave:

        pIrp->IoStatus.Status      = STATUS_SUCCESS;
        pIrp->IoStatus.Information = r;

        IoCompleteRequest(pIrp, IO_NO_INCREMENT);

        return STATUS_SUCCESS;
}

NTSTATUS
SfProcMonDispath(IN PDEVICE_OBJECT DeviceObject, IN PIRP pIrp)
{
        PIO_STACK_LOCATION   IrpStack;
        PVOID                InputBuffer;
        PVOID                OutputBuffer;
        ULONG                InputBufferLength;
        ULONG                OutputBufferLength;
        ULONG                IoControlCode;
        PVOID                                  pIoBuffer;

        pIrp->IoStatus.Status      = STATUS_SUCCESS;
        pIrp->IoStatus.Information = 0;

        IrpStack           = IoGetCurrentIrpStackLocation(pIrp);

        InputBuffer        = pIrp->AssociatedIrp.SystemBuffer;
        OutputBuffer       = pIrp->AssociatedIrp.SystemBuffer;
        InputBufferLength  = IrpStack->Parameters.DeviceIoControl.InputBufferLength;
        OutputBufferLength = IrpStack->Parameters.DeviceIoControl.OutputBufferLength;
        IoControlCode      = IrpStack->Parameters.DeviceIoControl.IoControlCode;
        pIoBuffer                    = pIrp->AssociatedIrp.SystemBuffer;
       
        switch (IrpStack->MajorFunction)
    {
                case IRP_MJ_DEVICE_CONTROL:
                {
                        switch(IoControlCode)
                        {
                        case PROCDENY_PROCESS_MONITOR: // 取进程信息
                                {
                                        // 取当前调用态
                                        if (ExGetPreviousMode() == UserMode)
                                        {
                                                __try
                                                {
                                                        // 判断用户态的对象是否可读
                                                        ProbeForRead(pIoBuffer, InputBufferLength, 1);
                                                }
                                                __except(EXCEPTION_EXECUTE_HANDLER)
                                                {
                                                        DbgPrint(("YUBAN.FILEWATCH.DRIVER <<<<<< !PROCDENY_PROCESS_MONITOR ------ Exception: Pass It! ------ 0x%08x>>>>>>"), GetExceptionCode());

                                                        pIrp->IoStatus.Status      = STATUS_SUCCESS;
                                                        pIrp->IoStatus.Information = 0;

                                                        IoCompleteRequest(pIrp, IO_NO_INCREMENT);

                                                        return STATUS_SUCCESS;
                                                }
                                        }

                                        return SfGetCurrentProcSection(DeviceObject, pIrp, pIoBuffer);
                                }
                        case PROCDENY_FILE_MONITOR:    // 取文件信息
                                {
                                        // 取当前调用态
                                        if (ExGetPreviousMode() == UserMode)
                                        {
                                                __try
                                                {
                                                        // 判断用户态的对象是否可读
                                                        ProbeForRead(pIoBuffer, InputBufferLength, 1);
                                                }
                                                __except(EXCEPTION_EXECUTE_HANDLER)
                                                {
                                                        DbgPrint(("YUBAN.FILEWATCH.DRIVER <<<<<< !PROCDENY_FILE_MONITOR ------ Exception: Pass It! ------ 0x%08x>>>>>>"), GetExceptionCode());

                                                        pIrp->IoStatus.Status      = STATUS_SUCCESS;
                                                        pIrp->IoStatus.Information = 0;

                                                        IoCompleteRequest(pIrp, IO_NO_INCREMENT);

                                                        return STATUS_SUCCESS;
                                                }
                                        }

                                        return SfGetCurrentProcFile(DeviceObject, pIrp, pIoBuffer);
                                }
                        case PROCDENY_PROCESS_FILTER:  // 设置进程过滤列表
                                {
                                        return SfSetProcessFilter(DeviceObject, pIrp, InputBuffer);
                                }
                        case PROCDENY_INTEREST_FILE:   // 设置感兴趣的文件后缀名列表
                                {
                                        return SfSetInterestFile(DeviceObject, pIrp, InputBuffer);
                                }
                        case PROCDENY_DENYPROCESS:
                                {
                                        return SfDenyProcessMonter(DeviceObject, pIrp, pIoBuffer, InputBufferLength);
                                }
                        case PROCDENY_CANCELDENY:
                                {
                                        return SfCancelProcessMonter(DeviceObject, pIrp, pIoBuffer);
                                }
                        case PROCDENY_PAUSE:
                                {
                                        g_b_stop = TRUE;      // 暂停

                                        pIrp->IoStatus.Status      = STATUS_SUCCESS;
                                        pIrp->IoStatus.Information = 0;

                                        DbgPrint(("YUBAN.FILEWATCH.DRIVER <<<<<< !PROCDENY_PAUSE ------ Set Pause! ------ >>>>>>"));

                                        IoCompleteRequest(pIrp, IO_NO_INCREMENT);

                                        return STATUS_SUCCESS;
                                }
                        case PROCDENY_RESUME:          // 恢复
                                {
                                        g_b_stop = FALSE;

                                        pIrp->IoStatus.Status      = STATUS_SUCCESS;
                                        pIrp->IoStatus.Information = 0;

                                        DbgPrint(("YUBAN.FILEWATCH.DRIVER <<<<<< !PROCDENY_PAUSE ------ Set Resume! ------ >>>>>>"));

                                        IoCompleteRequest(pIrp, IO_NO_INCREMENT);

                                        return STATUS_SUCCESS;
                                }
                        default:
                                {
                                        break;
                                }
                        }
                        break;
                }
                case IRP_MJ_CREATE:
                {
                        break;
                }
                case IRP_MJ_CLOSE:
                {
                        DbgPrint(("YUBAN.FILEWATCH.DRIVER <<<<<< !SfProcMonDispath ------ Process is Closed ------ >>>>>>"));

                        break;
                }
                default:
                {
                        break;
                }
        }

        pIrp->IoStatus.Status      = STATUS_SUCCESS;
        pIrp->IoStatus.Information = 0;

        IoCompleteRequest(pIrp, IO_NO_INCREMENT);

        return STATUS_SUCCESS;
}

另外还有点很是疑惑, Yb_Process!SfSetInterestFile 这个我压根就没有在上层发Io消息, 怎么windbg分析出来, 它也在堆栈里?windbg 分析指向不明确, 找不到原因. 请高人分析下. 谢谢了.  

[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

上传的附件:
收藏
免费 0
支持
分享
最新回复 (6)
雪    币: 40
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
2
还没人... 自己顶一下.
2014-1-6 16:32
0
雪    币: 31
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
3
没看懂,不过明显是访问了非法地址嘛,看看memcpy的目标地址是否有效,长度是否越界
2014-1-6 21:36
0
雪    币: 1785
活跃值: (3975)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
4
RtlCopyMemory(&pUserFileData->FileObject[i], &pNodeFileData->FileData, sizeof(OP_FILE));

应该是这里,注释掉看下
2014-1-7 09:38
0
雪    币: 40
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
5
后来又蓝了一次, 这次指向的是"RtlCopyMemory", 不过我代码中做了MmIsAddressValid的判断, 也做了PreboForRead的判断, 怎么还会这样呢? 请问还有什么方法可以排除这个错误吗?
驱动中结构的定义如下:
// ------------------------------------------------------------------------- 驱动层文件进程类定义 ------------------------------------------------------------------------- //

#define MAX_FILE_EXT            16    // 文件扩展名
#define MAX_FILE_NAME           128   // 文件名
#define MAX_PROCESS_NAME        128   // 进程名
#define MAX_FILE_PATH           256   // 文件/进程 全路径
#define MAX_FILE_SET            32    // 文件集(同一进程)
#define MAX_PROCESS             128   // 最大支持记录的进程个数
#define MAX_FILE                128   // 最大支持记录的文件个数
#define NT_PROCESS_NAME_LENGTH  16    // "NT"中最大进程名长度

#define PROCESS_OPEN_STATE      0     // 进程状态 - 打开
#define PROCESS_CLOSE_STATE     1     // 进程状态 - 关闭

#define COMPARE_TYPE_PROCESS_ID 0     // 仅比较进程标识符
#define COMPARE_TYPE_FILE_PATH  1     // 比较进程标识符和文件全路径

// 文件数据结构对象
typedef struct _TAG_OP_FILE
{
        DWORD ProcessId;                // 与之关联的进程标识符

        WCHAR FileName[MAX_FILE_NAME];   // 文件名
        WCHAR FilePath[MAX_FILE_PATH];   // 文件全路径
        WCHAR FileExt [MAX_FILE_EXT];    // 文件扩展名

        DWORD FileType;                 // 文件实际类型

        PVOID OpenTime;                 // 文件被打开的时间
        PVOID CloseTime;                // 文件被关闭的时间

        DWORD OpenTick;                 // 文件打开了多长时间
        DWORD OpenCount;                // 文件被打开了多少次
        DWORD FileOrgSize;              // 文件原始大小
        DWORD FileCurSize;              // 文件现在大小

        BOOL  Closed;                   // 文件是否被关闭
        BOOL  Saved;                    // 文件已上传到上层(上传了的文件不用再次上传)

} OP_FILE, *POP_FILE;

// 进程数据结构对象
typedef struct _TAG_OP_PROCESS
{
        DWORD ProcessId;                  // 进程标识符
        DWORD FileCountOpened;            // 进程打开了多少个文件

        WCHAR ProcessName[MAX_FILE_NAME];  // 进程名
        WCHAR ProcessPath[MAX_FILE_PATH];  // 进程全路径

        PVOID OpenTime;                   // 进程打开的时间
        PVOID CloseTime;                  // 进程关闭的时间

        DWORD OpenTick;                   // 进程打开了多长时间

        BOOL  Closed;                     // 进程是否被关闭
        BOOL  Saved;                      // 进程已上传到上层(上传了的进程不用再次上传)

} OP_PROCESS, *POP_PROCESS;

// 文件集
typedef struct _TAG_FILE_DATA_NODE
{
        OP_FILE FileData;

        struct _TAG_FILE_DATA_NODE *NodeNext;

} FILE_DATA_NODE, *PFILE_DATA_NODE;

// 文件记录列表
typedef struct _TAG_FILE_DATA_LIST
{
        DWORD Count;                      // 列表中成员数量(默认为零)

        PFILE_DATA_NODE NodeHead;

} FILE_DATA_LIST, *PFILE_DATA_LIST;

// 被同一进程打开的文件集合结构体
typedef struct _TAG_OP_FILE_SET
{
        OP_PROCESS ProcessObject;             // 与此文件关联的进程对象

        FILE_DATA_LIST FileDataList;          // 被同一进程打开的文件记录列表

} OP_FILE_SET, *POP_FILE_SET;

// 文件集
typedef struct _TAG_OP_FILE_SET_NODE
{
        OP_FILE_SET FileOPSet;

        struct _TAG_OP_FILE_SET_NODE *NodeNext;

} OP_FILE_SET_NODE, *POP_FILE_SET_NODE;

// 文件记录列表
typedef struct _TAG_OP_FILE_LIST
{
        DWORD Count;                      // 列表中成员数量(默认为零)

        POP_FILE_SET_NODE NodeHead;

} OP_FILE_LIST, *POP_FILE_LIST;

// 与用户层通讯的进程对象数据
typedef struct _TAG_USER_PROCESS_DATA
{
        ULONG Count;                            // 进程个数

        OP_PROCESS ProcessObject[MAX_PROCESS];  // 进程对象

} USER_PROCESS_DATA, *PUSER_PROCESS_DATA;

typedef struct _TAG_USER_FILE_DATA
{
        ULONG Count;                            // 进程个数

        OP_FILE FileObject[MAX_PROCESS];        // 进程对象

} USER_FILE_DATA, *PUSER_FILE_DATA;

// 进程过滤节点数据结构
typedef struct _TAG_PROCESS_FILTER_NODE
{
        LIST_ENTRY ListEntry;

        WCHAR ProcessName[MAX_PROCESS_NAME];

} PROCESS_FILTER_NODE, *PPROCESS_FILTER_NODE;

我RtlCopyMemory之前对目标地址和源地址都做了"MmIsAddressValid"的判断, 目标和源的结构大小都是OP_FILE类型的, 应该不会超长吧...
2014-1-7 09:45
0
雪    币: 40
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
6
期待大牛解答...
2014-1-7 17:44
0
雪    币: 40
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
7
都几天了... 就没人指点一下吗 ..
2014-1-10 09:33
0
游客
登录 | 注册 方可回帖
返回
//