码迷,mamicode.com
首页 > 其他好文 > 详细

跟踪 Ring3 - Ring0 的运行流程

时间:2017-08-18 13:36:42      阅读:322      评论:0      收藏:0      [点我收藏+]

标签:form   .dll   内存   stc   搜索   initial   symbols   ogr   pen   

理论知识

SYSENTER 指令是在 Inter Pentium(R) Ⅱ 处理器上作为“高速系统调用”功能的一部分被首次引用的。
SYSENTER 指令进行过专门的优化,能够以最佳性能由 Ring3 层切换到 Ring0 层。


微软首次引用 SYSENTER 指令是在 Windows 2000 的系统上,再次之前微软的系统是通过自陷指令 int 0x2E 进入 Ring0 层的系统空间的。
在 Windows 2000 及以后的系统中,假设想要从 Ring3 层进入 Ring0 层,系统首先会将要调用的系统调用号(SSDT调用号)放入 EAX 中。然后将当前栈指针 ESP 的内容放入 EDX 中后运行SYSENTER 指令;
SYSENTER 被运行后会将控制权传递给特殊模块寄存器 IA32_SYSENTER_EIP 所指向的函数中,完毕兴许操作。

特殊模块寄存器组(Model-Specific registers。MSRs)是 CPU 中负责运行一些特定的、与计算逻辑相关性不大的、且操作较复杂的功能的一组寄存器。
特殊模块寄存器可通过使用 rdmsr/wrmsr 指令读写其位于 MSRs 指定偏移处的某个寄存器的信息。


MSRs 共包括上百种具有不同功能的寄存器。每一个寄存器所在的偏移与所占用的空间都不尽同样。眼下 MSRs 的可用偏移范围是 0x00000000 ~ 0xC0000103。

与 SYSENTER 相配合的 MSRs 共同拥有3个,其具体信息例如以下所看到的:

名称 偏移 说明
SYSENTER_CS_MSR 0x174 切换到 Ring0 层之后的 CS 选择器
SYSENTER_ESP_MSR 0x175 切换到 Ring0 层之后的 ESP
SYSENTER_EIP_MSR 0x176 切换到 Ring0 层之后的 EIP

SYSENTER 被运行时,这 3 个寄存器会运行以下操作配合.
SYSENTER 完毕的切换操作:

  1. 装载 SYSENTER_CS_MSR 到 CS 寄存器,设置目标代码段。
  2. 装载 SYSENTER_EIP_MSR 到 EIP 寄存器。设置目标指令;
  3. 将 SYSENTER_CS_MSR + 8 装载到 SS 寄存器,设置栈段;
  4. 装载 SYSENTER_ESP_MSR 到 ESP 寄存器,设置栈帧;
  5. 切换 Ring0。
  6. 清除 EFLAGS 的 VM 标志;(虚拟8086方式标志)
  7. 运行位于 EIP 处的 RING0 例程。

实验開始~

说了这么多理论,如今来实践一下咯:( 以 CreateFileW 函数为例 )
在虚拟机中运行 notepad.exe ,用 windbg 使断下
搜索 notepad.exe 进程:

2: kd> !process 0 0 notepad.exe
PROCESS 87b697c0  SessionId: 1  Cid: 0d10    Peb: 7ffdf000  ParentCid: 0474
    DirBase: 6612b000  ObjectTable: 931868f0  HandleCount:  61.
    Image: notepad.exe

我们得到了 notepad.exe 的进程首地址,如今转到他的进程空间:

2: kd> .process /i /p 87b697c0
You need to continue execution (press ‘g‘ <enter>) for the context
to be switched. When the debugger breaks in again, you will be in
the new process context.

当中两个參数的含义:(注:此中文解释来自 http://www.dbgtech.net/windbghelp/。站长翻译了windbg的帮助文档,英语文盲的福音)

/i
(Windows XP 和之后的系统;仅活动调试;非本地内核调试) 指定要侵入(invasively)调试Process 。这样的调试意味着目标机上的操作系统实际上将指定的进程激活。

(假设不带该參数。.process 命令改变调试器的输出,可是不会作用于目标机本身。

)假设使用了 /i,必须使用g (Go)命令来运行目标。

数秒之后,目标会再次中断到调试器中。而且指定的 Process 被激活并用作当前进程上下文。


/p
假设使用了/p 而且Process 非0。在訪问之前将该进程全部页表入口(PTE)转换成物理地址。

这样的转换可能造成速度变慢,由于调试器必须找到该进程使用的全部内存的物理地址。调试器也须要通过调试电缆传输大量数据。

(该行为和.cache forcedecodeuser一样。

)
假设包括/p 而且Process为0或者省略,则禁用这样的转换。

(这样的行为和.cache noforcedecodeptes一样。)

上面提示我们说要运行一下才干切换上下文,那么 g 一下

2: kd> g
Break instruction exception - code 80000003 (first chance)
nt!RtlpBreakWithStatusInstruction:
8406dd00 cc              int     3

如今我们就断在了 notepad.exe 的进程里
如今又一次载入一下符号表

2: kd> .reload /f /user
Loading User Symbols
.
DBGHELP: notepad - public symbols  
        f:\program files\nt_dbg_symbols\notepad.pdb\E325F5195AE94FAEB58D25C9DF8C0CFD2\notepad.pdb
.
DBGHELP: f:\program files\nt_dbg_symbols\ntdll.dll\4CE7B96E13c000\ntdll.dll - OK
DBGENG:  Partial symbol load found image f:\program files\nt_dbg_symbols\ntdll.dll\4CE7B96E13c000\ntdll.dll.
DBGHELP: ntdll - public symbols  
        f:\program files\nt_dbg_symbols\ntdll.pdb\120028FA453F4CD5A6A404EC37396A582\ntdll.pdb
.
DBGHELP: f:\program files\nt_dbg_symbols\kernel32.dll\4CE7B8EFd4000\kernel32.dll - OK
DBGENG:  Partial symbol load found image f:\program files\nt_dbg_symbols\kernel32.dll\4CE7B8EFd4000\kernel32.dll.
DBGHELP: kernel32 - public symbols  
        f:\program files\nt_dbg_symbols\kernel32.pdb\D4AC3906D49D487B9F69F9326A7D206A2\kernel32.pdb
.
DBGHELP: f:\program files\nt_dbg_symbols\KERNELBASE.dll\4CE7B8F04a000\KERNELBASE.dll - OK
DBGENG:  Partial symbol load found image f:\program files\nt_dbg_symbols\KERNELBASE.dll\4CE7B8F04a000\KERNELBASE.dll.
DBGHELP: KERNELBASE - public symbols  
        f:\program files\nt_dbg_symbols\kernelbase.pdb\F50B25D282504188B73063D653B7D27E2\kernelbase.pdb
.
DBGHELP: f:\program files\nt_dbg_symbols\ADVAPI32.dll\4CE7B706a0000\ADVAPI32.dll - OK
DBGENG:  Partial symbol load found image f:\program files\nt_dbg_symbols\ADVAPI32.dll\4CE7B706a0000\ADVAPI32.dll.
DBGHELP: ADVAPI32 - public symbols  
        f:\program files\nt_dbg_symbols\advapi32.pdb\3F32049F550C42B09CF114A1FB8A97E92\advapi32.pdb
.
DBGHELP: msvcrt - public symbols  
        f:\program files\nt_dbg_symbols\msvcrt.pdb\6EC79267530C45188F2A816AD59DBBF92\msvcrt.pdb
.
DBGHELP: sechost - public symbols  
        f:\program files\nt_dbg_symbols\sechost.pdb\7AF14D02D41E4CD6942745FE0E6372B11\sechost.pdb
.
DBGHELP: RPCRT4 - public symbols  
        f:\program files\nt_dbg_symbols\rpcrt4.pdb\189CC56E2D4A43DA8A269E088721F13D2\rpcrt4.pdb
.
DBGHELP: GDI32 - public symbols  
        f:\program files\nt_dbg_symbols\gdi32.pdb\96948E513A8747C58A699B8A7009DCB22\gdi32.pdb
.
DBGHELP: f:\program files\nt_dbg_symbols\USER32.dll\4CE7BA26c9000\USER32.dll - OK
DBGENG:  Partial symbol load found image f:\program files\nt_dbg_symbols\USER32.dll\4CE7BA26c9000\USER32.dll.
DBGHELP: USER32 - public symbols  
        f:\program files\nt_dbg_symbols\user32.pdb\DD74D86F12624845A42A6A5BAAB4D7A82\user32.pdb
.
DBGHELP: LPK - public symbols  
        f:\program files\nt_dbg_symbols\lpk.pdb\B99319FE4427418F9EB5432B9F6A13412\lpk.pdb
.
DBGHELP: USP10 - public symbols  
        f:\program files\nt_dbg_symbols\usp10.pdb\F49786E2C7C54EA99E7C37120CDAEB9C1\usp10.pdb
.
DBGHELP: f:\program files\nt_dbg_symbols\COMDLG32.dll\4CE7B82D7b000\COMDLG32.dll - OK
DBGENG:  Partial symbol load found image f:\program files\nt_dbg_symbols\COMDLG32.dll\4CE7B82D7b000\COMDLG32.dll.
DBGHELP: COMDLG32 - public symbols  
        f:\program files\nt_dbg_symbols\comdlg32.pdb\96BC483CDFF04D1AAFE462F093B954EC2\comdlg32.pdb
.
DBGHELP: SHLWAPI - public symbols  
        f:\program files\nt_dbg_symbols\shlwapi.pdb\E128B1CEE2EB438C8646E6967118F33E2\shlwapi.pdb
.
DBGHELP: COMCTL32 - public symbols  
        f:\program files\nt_dbg_symbols\comctl32.pdb\B4CE90AAB95E4B89A22A7711DFD7E6EF2\comctl32.pdb
.
DBGHELP: f:\program files\nt_dbg_symbols\SHELL32.dll\4CE7B9DEc4a000\SHELL32.dll - OK
DBGENG:  Partial symbol load found image f:\program files\nt_dbg_symbols\SHELL32.dll\4CE7B9DEc4a000\SHELL32.dll.
DBGHELP: SHELL32 - public symbols  
        f:\program files\nt_dbg_symbols\shell32.pdb\4555A5FB02FA4E49B65A25616CD97A6B2\shell32.pdb
.
DBGHELP: f:\program files\nt_dbg_symbols\WINSPOOL.DRV\4CE7BA4B51000\WINSPOOL.DRV - OK
DBGENG:  Partial symbol load found image f:\program files\nt_dbg_symbols\WINSPOOL.DRV\4CE7BA4B51000\WINSPOOL.DRV.
DBGHELP: WINSPOOL - public symbols  
        f:\program files\nt_dbg_symbols\winspool.pdb\B165BBE7CD8C4F39BE373C0D9DFCD77B2\winspool.pdb
.
DBGHELP: f:\program files\nt_dbg_symbols\ole32.dll\4CE7B96F15c000\ole32.dll - OK
DBGENG:  Partial symbol load found image f:\program files\nt_dbg_symbols\ole32.dll\4CE7B96F15c000\ole32.dll.
DBGHELP: ole32 - public symbols  
        f:\program files\nt_dbg_symbols\ole32.pdb\5061F11A9A57433595EA5EA75A156F4B2\ole32.pdb
.
DBGHELP: f:\program files\nt_dbg_symbols\OLEAUT32.dll\4CE7B9728f000\OLEAUT32.dll - OK
DBGENG:  Partial symbol load found image f:\program files\nt_dbg_symbols\OLEAUT32.dll\4CE7B9728f000\OLEAUT32.dll.
DBGHELP: OLEAUT32 - public symbols  
        f:\program files\nt_dbg_symbols\oleaut32.pdb\312BF231E76A450ABF027EBFB52FA2162\oleaut32.pdb
.
DBGHELP: VERSION - public symbols  
        f:\program files\nt_dbg_symbols\version.pdb\52234E5C7EC44646B62D56357B2C94872\version.pdb
.
DBGHELP: IMM32 - public symbols  
        f:\program files\nt_dbg_symbols\imm32.pdb\91A0004474E24AA89F185029E31144892\imm32.pdb
.
DBGHELP: MSCTF - public symbols  
        f:\program files\nt_dbg_symbols\msctf.pdb\173DAEF86B2548DBA6134EB74C4D2F232\msctf.pdb
.
DBGHELP: CRYPTBASE - public symbols  
        f:\program files\nt_dbg_symbols\cryptbase.pdb\E62FEAE559EE4CD995614215B01AC2102\cryptbase.pdb
.
DBGHELP: uxtheme - public symbols  
        f:\program files\nt_dbg_symbols\UxTheme.pdb\5BECAB35E7714835A6BF3DADD891BB3A2\UxTheme.pdb
.
DBGHELP: dwmapi - public symbols  
        f:\program files\nt_dbg_symbols\dwmapi.pdb\D8D91B3F339A4FDC960FC7121D146DF42\dwmapi.pdb

当中參数含义:

/f(马上载入)
Forces the debugger to immediately load the symbols. This parameter overrides lazy symbol loading. For more information, see the following
Remarks section.
/user (仅仅载入用户符号)
Reloads user symbols only. (You can use this option only during kernel-mode debugging.)

我之前下载了一个完整版的。全部基本都是本地载入。


假设没有而且网速又慢。。。

能够等到 kernel 等 pdb 下载过后按Ctrl + C终止。不然就要等到天荒地老。

。。

如今保证了符号已经没问题,就能够开心的继续咯。直到如今我们才真正開始…….
由于我们要观察 CreateFileW ,我们就在这个函数下断点

2: kd> bp kernel32!CreateFileW

为了放心。看一下断点列表:

2: kd> bl
 0 e 759ecca9     0001 (0001) kernel32!CreateFileW

我们如今继续运行:

2: kd> g
Breakpoint 0 hit
kernel32!CreateFileW:
001b:759ecca9 ff25e0199a75    jmp     dword ptr [kernel32!_imp__CreateFileW (759a19e0)]

进程断在了这里。

单步一次进入jmp的函数内部:

3: kd> t
KERNELBASE!CreateFileW:
001b:7574a850 8bff            mov     edi,edi

以函数地址開始反汇编100条:

3: kd> u KERNELBASE!CreateFileW l100
KERNELBASE!CreateFileW:
7574a850 8bff            mov     edi,edi
7574a852 55              push    ebp
7574a853 8bec            mov     ebp,esp
7574a855 8b4518          mov     eax,dword ptr [ebp+18h]
7574a858 83ec64          sub     esp,64h
7574a85b 48              dec     eax
7574a85c 0f8499e5ffff    je      KERNELBASE!CreateFileW+0x57 (75748dfb)
7574a862 48              dec     eax
7574a863 0f8468360000    je      KERNELBASE!CreateFileW+0x4e (7574ded1)
7574a869 48              dec     eax
7574a86a 0f8579360000    jne     KERNELBASE!CreateFileW+0x14 (7574dee9)
7574a870 c745fc01000000  mov     dword ptr [ebp-4],1
7574a877 53              push    ebx
7574a878 56              push    esi
7574a879 8b7508          mov     esi,dword ptr [ebp+8]
7574a87c 56              push    esi
7574a87d 8d45d8          lea     eax,[ebp-28h]
7574a880 50              push    eax
7574a881 ff15fc117475    call    dword ptr [KERNELBASE!_imp__RtlInitUnicodeStringEx (757411fc)]
7574a887 33db            xor     ebx,ebx
7574a889 3bc3            cmp     eax,ebx
7574a88b 0f8ce46a0000    jl      KERNELBASE!CreateFileW+0xc0 (75751375)
7574a891 33c0            xor     eax,eax
7574a893 40              inc     eax
7574a894 663945d8        cmp     word ptr [ebp-28h],ax
7574a898 7611            jbe     KERNELBASE!CreateFileW+0x8e (7574a8ab)
7574a89a 0fb74dd8        movzx   ecx,word ptr [ebp-28h]
7574a89e d1e9            shr     ecx,1
7574a8a0 66837c4efe5c    cmp     word ptr [esi+ecx*2-2],5Ch
7574a8a6 8945ec          mov     dword ptr [ebp-14h],eax
7574a8a9 7403            je      KERNELBASE!CreateFileW+0x91 (7574a8ae)
7574a8ab 895dec          mov     dword ptr [ebp-14h],ebx
7574a8ae 8d45b4          lea     eax,[ebp-4Ch]
7574a8b1 50              push    eax
7574a8b2 53              push    ebx
7574a8b3 8d45d8          lea     eax,[ebp-28h]
7574a8b6 50              push    eax
7574a8b7 56              push    esi
7574a8b8 895d08          mov     dword ptr [ebp+8],ebx
7574a8bb ff15fc137475    call    dword ptr [KERNELBASE!_imp__RtlDosPathNameToRelativeNtPathName_U_WithStatus (757413fc)]
7574a8c1 3bc3            cmp     eax,ebx
7574a8c3 0f8c73750100    jl      KERNELBASE!CreateFileW+0xa8 (75761e3c)
7574a8c9 8b45dc          mov     eax,dword ptr [ebp-24h]
7574a8cc 8945f0          mov     dword ptr [ebp-10h],eax
7574a8cf 8b45b4          mov     eax,dword ptr [ebp-4Ch]
7574a8d2 663bc3          cmp     ax,bx
7574a8d5 0f851c390000    jne     KERNELBASE!CreateFileW+0xdc (7574e1f7)
7574a8db 895dbc          mov     dword ptr [ebp-44h],ebx
7574a8de 8b45bc          mov     eax,dword ptr [ebp-44h]
7574a8e1 8b551c          mov     edx,dword ptr [ebp+1Ch]
7574a8e4 8945a0          mov     dword ptr [ebp-60h],eax
7574a8e7 8d45d8          lea     eax,[ebp-28h]
7574a8ea 8bca            mov     ecx,edx
7574a8ec c1e912          shr     ecx,12h
7574a8ef 8945a4          mov     dword ptr [ebp-5Ch],eax
7574a8f2 8bc2            mov     eax,edx
7574a8f4 f7d1            not     ecx
7574a8f6 83e140          and     ecx,40h
7574a8f9 2500001f00      and     eax,1F0000h
7574a8fe c7459c18000000  mov     dword ptr [ebp-64h],18h
7574a905 894da8          mov     dword ptr [ebp-58h],ecx
7574a908 895dac          mov     dword ptr [ebp-54h],ebx
7574a90b a900001000      test    eax,100000h
7574a910 0f85eb420000    jne     KERNELBASE!CreateFileW+0x11e (7574ec01)
7574a916 c645cc01        mov     byte ptr [ebp-34h],1
7574a91a c745c802000000  mov     dword ptr [ebp-38h],2
7574a921 c645cd01        mov     byte ptr [ebp-33h],1
7574a925 8d45c4          lea     eax,[ebp-3Ch]
7574a928 8945b0          mov     dword ptr [ebp-50h],eax
7574a92b 8b4514          mov     eax,dword ptr [ebp+14h]
7574a92e c745c40c000000  mov     dword ptr [ebp-3Ch],0Ch
7574a935 3bc3            cmp     eax,ebx
7574a937 0f85493a0000    jne     KERNELBASE!CreateFileW+0x178 (7574e386)
7574a93d 57              push    edi
7574a93e 895d14          mov     dword ptr [ebp+14h],ebx
7574a941 895df4          mov     dword ptr [ebp-0Ch],ebx
7574a944 395d20          cmp     dword ptr [ebp+20h],ebx
7574a947 0f8586710000    jne     KERNELBASE!CreateFileW+0x199 (75751ad3)
7574a94d 8bf2            mov     esi,edx
7574a94f c1ee04          shr     esi,4
7574a952 b800000008      mov     eax,8000000h
7574a957 23f0            and     esi,eax
7574a959 8bfa            mov     edi,edx
7574a95b 81e700000020    and     edi,20000000h
7574a961 0bf7            or      esi,edi
7574a963 d1ee            shr     esi,1
7574a965 8bfa            mov     edi,edx
7574a967 23f8            and     edi,eax
7574a969 0bf7            or      esi,edi
7574a96b c1ee08          shr     esi,8
7574a96e 8bc2            mov     eax,edx
7574a970 2500000010      and     eax,10000000h
7574a975 0bf0            or      esi,eax
7574a977 c1ee06          shr     esi,6
7574a97a 8bca            mov     ecx,edx
7574a97c 8bc2            mov     eax,edx
7574a97e c1e819          shr     eax,19h
7574a981 81e100000002    and     ecx,2000000h
7574a987 0bf1            or      esi,ecx
7574a989 f7d0            not     eax
7574a98b c1ee0b          shr     esi,0Bh
7574a98e 83e020          and     eax,20h
7574a991 0bf0            or      esi,eax
7574a993 097508          or      dword ptr [ebp+8],esi
7574a996 f7c200000004    test    edx,4000000h
7574a99c 0f85644a0000    jne     KERNELBASE!CreateFileW+0x28b (7574f406)
7574a9a2 b800002000      mov     eax,200000h
7574a9a7 85d0            test    eax,edx
7574a9a9 0f85013b0000    jne     KERNELBASE!CreateFileW+0x2a2 (7574e4b0)
7574a9af f7c200001000    test    edx,100000h
7574a9b5 0f8572420000    jne     KERNELBASE!CreateFileW+0x2ad (7574ec2d)
7574a9bb 3bcb            cmp     ecx,ebx
7574a9bd 0f8531caffff    jne     KERNELBASE!CreateFileW+0x2ed (757473f4)
7574a9c3 834d0840        or      dword ptr [ebp+8],40h
7574a9c7 6a01            push    1
7574a9c9 6814a87475      push    offset KERNELBASE!g_SbModuleTable_Scenario (7574a814)
7574a9ce 6a01            push    1
7574a9d0 68abababab      push    0ABABABABh
7574a9d5 e863feffff      call    KERNELBASE!SbSelectProcedure (7574a83d)
7574a9da 3bc3            cmp     eax,ebx
7574a9dc 7406            je      KERNELBASE!CreateFileW+0x321 (7574a9e4)
7574a9de 8d4d08          lea     ecx,[ebp+8]
7574a9e1 51              push    ecx
7574a9e2 ffd0            call    eax
7574a9e4 ff75f4          push    dword ptr [ebp-0Ch]
7574a9e7 8b4d1c          mov     ecx,dword ptr [ebp+1Ch]
7574a9ea ff7514          push    dword ptr [ebp+14h]
7574a9ed 8b450c          mov     eax,dword ptr [ebp+0Ch]
7574a9f0 ff7508          push    dword ptr [ebp+8]
7574a9f3 8b35b0107475    mov     esi,dword ptr [KERNELBASE!_imp__NtCreateFile (757410b0)]
7574a9f9 ff75fc          push    dword ptr [ebp-4]
7574a9fc 81e1a77f0000    and     ecx,7FA7h
7574aa02 ff7510          push    dword ptr [ebp+10h]
7574aa05 894d1c          mov     dword ptr [ebp+1Ch],ecx
7574aa08 51              push    ecx
7574aa09 53              push    ebx
7574aa0a 8d4de0          lea     ecx,[ebp-20h]
7574aa0d 51              push    ecx
7574aa0e 0d80001000      or      eax,100080h
7574aa13 8d4d9c          lea     ecx,[ebp-64h]
7574aa16 51              push    ecx
7574aa17 50              push    eax
7574aa18 89450c          mov     dword ptr [ebp+0Ch],eax
7574aa1b 8d45f8          lea     eax,[ebp-8]
7574aa1e 50              push    eax
7574aa1f ffd6            call    esi
7574aa21 8bd8            mov     ebx,eax
7574aa23 bf220000c0      mov     edi,0C0000022h
7574aa28 3bdf            cmp     ebx,edi
7574aa2a 0f8433690000    je      KERNELBASE!CreateFileW+0x369 (75751363)
7574aa30 8d45b4          lea     eax,[ebp-4Ch]
7574aa33 50              push    eax
7574aa34 ff15f4137475    call    dword ptr [KERNELBASE!_imp__RtlReleaseRelativeName (757413f4)]
7574aa3a ff75f0          push    dword ptr [ebp-10h]
7574aa3d 64a118000000    mov     eax,dword ptr fs:[00000018h]
7574aa43 8b4030          mov     eax,dword ptr [eax+30h]
7574aa46 8b3514107475    mov     esi,dword ptr [KERNELBASE!_imp__RtlFreeHeap (75741014)]
7574aa4c 33ff            xor     edi,edi
7574aa4e 57              push    edi
7574aa4f ff7018          push    dword ptr [eax+18h]
7574aa52 ffd6            call    esi
7574aa54 ff7514          push    dword ptr [ebp+14h]
7574aa57 64a118000000    mov     eax,dword ptr fs:[00000018h]
7574aa5d 8b4030          mov     eax,dword ptr [eax+30h]
7574aa60 57              push    edi
7574aa61 ff7018          push    dword ptr [eax+18h]
7574aa64 ffd6            call    esi
7574aa66 3bdf            cmp     ebx,edi
7574aa68 7c2f            jl      KERNELBASE!CreateFileW+0x3fe (7574aa99)
7574aa6a 837d1802        cmp     dword ptr [ebp+18h],2
7574aa6e 0f8469340000    je      KERNELBASE!CreateFileW+0x434 (7574dedd)
7574aa74 837d1804        cmp     dword ptr [ebp+18h],4
7574aa78 0f847e340000    je      KERNELBASE!CreateFileW+0x440 (7574defc)
7574aa7e 57              push    edi
7574aa7f ff1548107475    call    dword ptr [KERNELBASE!_imp__RtlSetLastWin32Error (75741048)]
7574aa85 837d1805        cmp     dword ptr [ebp+18h],5
7574aa89 0f8441d40100    je      KERNELBASE!CreateFileW+0x45a (75767ed0)
7574aa8f 8b45f8          mov     eax,dword ptr [ebp-8]
7574aa92 5f              pop     edi
7574aa93 5e              pop     esi
7574aa94 5b              pop     ebx
7574aa95 c9              leave
7574aa96 c21c00          ret     1Ch
7574aa99 53              push    ebx
7574aa9a e856c0ffff      call    KERNELBASE!BaseSetLastNTError (75746af5)
7574aa9f 81fb350000c0    cmp     ebx,0C0000035h
7574aaa5 0f844fa10000    je      KERNELBASE!CreateFileW+0x40c (75754bfa)
7574aaab 81fbba0000c0    cmp     ebx,0C00000BAh
7574aab1 0f8462a10000    je      KERNELBASE!CreateFileW+0x418 (75754c19)
7574aab7 83c8ff          or      eax,0FFFFFFFFh
7574aaba ebd6            jmp     KERNELBASE!CreateFileW+0x48f (7574aa92)
7574aabc 90              nop
7574aabd 90              nop
7574aabe 90              nop
7574aabf 90              nop
7574aac0 90              nop
KERNELBASE!AllocateAndInitializeSid:
7574aac1 8bff            mov     edi,edi
7574aac3 55              push    ebp
7574aac4 8bec            mov     ebp,esp
7574aac6 ff7530          push    dword ptr [ebp+30h]
7574aac9 ff752c          push    dword ptr [ebp+2Ch]
7574aacc ff7528          push    dword ptr [ebp+28h]
7574aacf ff7524          push    dword ptr [ebp+24h]
7574aad2 ff7520          push    dword ptr [ebp+20h]
7574aad5 ff751c          push    dword ptr [ebp+1Ch]
7574aad8 ff7518          push    dword ptr [ebp+18h]
7574aadb ff7514          push    dword ptr [ebp+14h]
7574aade ff7510          push    dword ptr [ebp+10h]
7574aae1 ff750c          push    dword ptr [ebp+0Ch]
7574aae4 ff7508          push    dword ptr [ebp+8]
7574aae7 ff1520137475    call    dword ptr [KERNELBASE!_imp__RtlAllocateAndInitializeSid (75741320)]
7574aaed 85c0            test    eax,eax
7574aaef 0f8c6d260200    jl      KERNELBASE!AllocateAndInitializeSid+0x30 (7576d162)
7574aaf5 33c0            xor     eax,eax
7574aaf7 40              inc     eax
7574aaf8 5d              pop     ebp
7574aaf9 c22c00          ret     2Ch
7574aafc 90              nop
7574aafd 90              nop
7574aafe 90              nop
7574aaff 90              nop
7574ab00 90              nop
KERNELBASE!FreeSid:
7574ab01 8bff            mov     edi,edi
7574ab03 55              push    ebp
7574ab04 8bec            mov     ebp,esp
7574ab06 5d              pop     ebp
7574ab07 ff2508137475    jmp     dword ptr [KERNELBASE!_imp__RtlFreeSid (75741308)]
7574ab0d 90              nop
7574ab0e 90              nop
7574ab0f 90              nop
7574ab10 90              nop
7574ab11 90              nop
KERNELBASE!DuplicateTokenEx:
7574ab12 8bff            mov     edi,edi
7574ab14 55              push    ebp
7574ab15 8bec            mov     ebp,esp
7574ab17 83ec24          sub     esp,24h
7574ab1a 8b4514          mov     eax,dword ptr [ebp+14h]
7574ab1d 8945f8          mov     dword ptr [ebp-8],eax
7574ab20 8b4510          mov     eax,dword ptr [ebp+10h]
7574ab23 c745f40c000000  mov     dword ptr [ebp-0Ch],0Ch
7574ab2a c645fc01        mov     byte ptr [ebp-4],1
7574ab2e c645fd00        mov     byte ptr [ebp-3],0
7574ab32 85c0            test    eax,eax
7574ab34 0f858cc40000    jne     KERNELBASE!DuplicateTokenEx+0x24 (75756fc6)
7574ab3a 33c9            xor     ecx,ecx
7574ab3c 33c0            xor     eax,eax
7574ab3e ff751c          push    dword ptr [ebp+1Ch]
7574ab41 8365e000        and     dword ptr [ebp-20h],0
7574ab45 ff7518          push    dword ptr [ebp+18h]
7574ab48 8365e400        and     dword ptr [ebp-1Ch],0
7574ab4c 8945e8          mov     dword ptr [ebp-18h],eax
7574ab4f 8d45f4          lea     eax,[ebp-0Ch]
7574ab52 6a00            push    0
7574ab54 8945f0          mov     dword ptr [ebp-10h],eax
7574ab57 8d45dc          lea     eax,[ebp-24h]
7574ab5a 50              push    eax

100条仅仅是測试,看有没有得到完整的 CreateFileW 函数的反汇编。非常明显这里面的后半部分是 KERNELBASE!AllocateAndInitializeSid 的代码。所以我们仅仅关注上半部分。


先从 call 语句 逐条来看:
从上往下各自是

7574a881 ff15fc117475    call    dword ptr [KERNELBASE!_imp__RtlInitUnicodeStringEx (757411fc)]
7574a8bb ff15fc137475    call    dword ptr [KERNELBASE!_imp__RtlDosPathNameToRelativeNtPathName_U_WithStatus (757413fc)]
7574a9d5 e863feffff      call    KERNELBASE!SbSelectProcedure (7574a83d)
7574aa1f ffd6            call    esi

这一条 esi ,所以须要往上看 esi 的值是什么,于是:(新大陆~~)

7574a9f3 8b35b0107475    mov     esi,dword ptr [KERNELBASE!_imp__NtCreateFile (757410b0)]

我们知道 CreateFileW 内部的函数确实是 NtCreateFile。


那么我们就在 call esi 处下断点:

3: kd> bp 7574aa1f
3: kd> bl
 0 e 759ecca9     0001 (0001) kernel32!CreateFileW
 1 e 7574aa1f     0001 (0001) KERNELBASE!CreateFileW+0x35c

运行:

3: kd> g
Breakpoint 1 hit
KERNELBASE!CreateFileW+0x35c:
001b:7574aa1f ffd6            call    esi

单步进入:

3: kd> t
ntdll!NtCreateFile:
001b:774d55c8 b842000000      mov     eax,42h

如今我们就来到了 ntdll 中的 NtCreateFile 函数中了。
当前地址反汇编:

3: kd> u
ntdll!NtCreateFile:
774d55c8 b842000000      mov     eax,42h
774d55cd ba0003fe7f      mov     edx,offset SharedUserData!SystemCallStub (7ffe0300)
774d55d2 ff12            call    dword ptr [edx]
774d55d4 c22c00          ret     2Ch
774d55d7 90              nop
ntdll!NtCreateIoCompletion:
774d55d8 b843000000      mov     eax,43h
774d55dd ba0003fe7f      mov     edx,offset SharedUserData!SystemCallStub (7ffe0300)
774d55e2 ff12            call    dword ptr [edx]

如今正处在过渡的关键时刻!就要用到之前的理论知识了。忘了?再来:
假设想要从 Ring3 层进入 Ring0 层,

  • 系统首先会将要调用的系统调用号(SSDT调用号)放入 EAX 中,
  • 然后将当前栈指针 ESP 的内容放入 EDX 中后 运行SYSENTER 指令;
  • SYSENTER 被运行后会将控制权传递给特殊模块寄存器IA32_SYSENTER_EIP 所指向的函数中,完毕兴许操作。

如今地址 774d55c8 处就是“将要调用的系统调用号(SSDT调用号)放入 EAX 中”。啥?什么是 SSDT 调用号?如今我们能够觉得系统函数的地址都放在一个大数组里面,仅仅要知道一个索引。就能依据它找到函数地址从而调用。
如今单步三次进入call的函数内部:

3: kd> t
ntdll!NtCreateFile+0x5:
001b:774d55cd ba0003fe7f      mov     edx,offset SharedUserData!SystemCallStub (7ffe0300)
3: kd> t
ntdll!NtCreateFile+0xa:
001b:774d55d2 ff12            call    dword ptr [edx]
3: kd> t
ntdll!KiFastSystemCall:
001b:774d70b0 8bd4            mov     edx,esp

反汇编:

3: kd> u
ntdll!KiFastSystemCall:
774d70b0 8bd4            mov     edx,esp
774d70b2 0f34            sysenter
ntdll!KiFastSystemCallRet:
774d70b4 c3              ret
774d70b5 8da42400000000  lea     esp,[esp]
774d70bc 8d642400        lea     esp,[esp]
ntdll!KiIntSystemCall:
774d70c0 8d542408        lea     edx,[esp+8]
774d70c4 cd2e            int     2Eh
774d70c6 c3              ret

774d70b0 反地址处就是 “将当前 栈指针 ESP 的内容放入 EDX ”的操作
以下一句当然就是 “运行SYSENTER 指令”咯。

主要的流程已经验证,那我们来找一下SSDT数组的基址。


so,我们如今的情况是
EAX:SSDT 调用号(当前是 0x42)
EDX:ESP 的内容
我们又知道 SYSENTER_EIP_MSR 在偏移 0x176 处,功能:切换到 Ring0 层之后的 EIP,设置目标指令。

查看一下 SYSENTER_EIP_MSR 的内容:

3: kd> rdmsr 176
msr[176] = 00000000`8404a750

所以目标指令就在 00000000`8404a750 处。


我们就在这里下个条件断点(由于sysenter仅仅是一条指令并不是函数,直接t会跳过。在用户态的代码运行了SYSENTER指令之后,处理器中的控制单元将寄存器MSR_IA32_SYSENTER_EIP的值装载到指令指针寄存器eip中)。假设断在这里时 SSDT调用号也为0x42,那么就断下来,否则继续运行

3: kd> bp 8404a750 ".if (@eax & 0x0‘ffffffff)=0x0‘42 {} .else {gc}"
3: kd> bl
 0 e 759ecca9     0001 (0001) kernel32!CreateFileW
 1 e 7574aa1f     0001 (0001) KERNELBASE!CreateFileW+0x35c
 2 e 8404a750     0001 (0001) nt!KiFastCallEntry ".if (@eax & 0x0‘ffffffff)=0x0‘42 {}

关于 gc:(从条件断点处继续运行)
The gc command resumes execution from a conditional breakpoint in the same fashion that was used to hit the breakpoint (stepping, tracing, or freely executing).

运行:

3: kd> g
Syntax error at ‘‘ffffffff)=0x0‘42 {} .else {gc}‘
nt!KiFastCallEntry:
8404a750 b923000000      mov     ecx,23h

(此时 SYSENTER 的切换操作已经完毕大部分)
反汇编来一套:

3: kd> u nt!KiFastCallEntry l50
nt!KiFastCallEntry:
8404a750 b923000000      mov     ecx,23h
8404a755 6a30            push    30h
8404a757 0fa1            pop     fs
8404a759 8ed9            mov     ds,cx
8404a75b 8ec1            mov     es,cx
8404a75d 648b0d40000000  mov     ecx,dword ptr fs:[40h]
8404a764 8b6104          mov     esp,dword ptr [ecx+4]
8404a767 6a23            push    23h
8404a769 52              push    edx
8404a76a 9c              pushfd
8404a76b 6a02            push    2
8404a76d 83c208          add     edx,8
8404a770 9d              popfd
8404a771 804c240102      or      byte ptr [esp+1],2
8404a776 6a1b            push    1Bh
8404a778 ff350403dfff    push    dword ptr ds:[0FFDF0304h]
8404a77e 6a00            push    0
8404a780 55              push    ebp
8404a781 53              push    ebx
8404a782 56              push    esi
8404a783 57              push    edi
8404a784 648b1d1c000000  mov     ebx,dword ptr fs:[1Ch]
8404a78b 6a3b            push    3Bh
8404a78d 8bb324010000    mov     esi,dword ptr [ebx+124h]
8404a793 ff33            push    dword ptr [ebx]
8404a795 c703ffffffff    mov     dword ptr [ebx],0FFFFFFFFh
8404a79b 8b6e28          mov     ebp,dword ptr [esi+28h]
8404a79e 6a01            push    1
8404a7a0 83ec48          sub     esp,48h
8404a7a3 81ed9c020000    sub     ebp,29Ch
8404a7a9 c6863a01000001  mov     byte ptr [esi+13Ah],1
8404a7b0 3bec            cmp     ebp,esp
8404a7b2 7597            jne     nt!KiFastCallEntry2+0x49 (8404a74b)
8404a7b4 83652c00        and     dword ptr [ebp+2Ch],0
8404a7b8 f64603df        test    byte ptr [esi+3],0DFh
8404a7bc 89ae28010000    mov     dword ptr [esi+128h],ebp
8404a7c2 0f8538feffff    jne     nt!Dr_FastCallDrSave (8404a600)
8404a7c8 8b5d60          mov     ebx,dword ptr [ebp+60h]
8404a7cb 8b7d68          mov     edi,dword ptr [ebp+68h]
8404a7ce 89550c          mov     dword ptr [ebp+0Ch],edx
8404a7d1 c74508000ddbba  mov     dword ptr [ebp+8],0BADB0D00h
8404a7d8 895d00          mov     dword ptr [ebp],ebx
8404a7db 897d04          mov     dword ptr [ebp+4],edi
8404a7de fb              sti
8404a7df 8bf8            mov     edi,eax
8404a7e1 c1ef08          shr     edi,8
8404a7e4 83e710          and     edi,10h
8404a7e7 8bcf            mov     ecx,edi
8404a7e9 03bebc000000    add     edi,dword ptr [esi+0BCh]
8404a7ef 8bd8            mov     ebx,eax
8404a7f1 25ff0f0000      and     eax,0FFFh
8404a7f6 3b4708          cmp     eax,dword ptr [edi+8]
8404a7f9 0f8333fdffff    jae     nt!KiBBTUnexpectedRange (8404a532)
8404a7ff 83f910          cmp     ecx,10h
8404a802 751a            jne     nt!KiFastCallEntry+0xce (8404a81e)
8404a804 8b8e88000000    mov     ecx,dword ptr [esi+88h]
8404a80a 33f6            xor     esi,esi
8404a80c 0bb1700f0000    or      esi,dword ptr [ecx+0F70h]
8404a812 740a            je      nt!KiFastCallEntry+0xce (8404a81e)
8404a814 52              push    edx
8404a815 50              push    eax
8404a816 ff152c581784    call    dword ptr [nt!KeGdiFlushUserBatch (8417582c)]
8404a81c 58              pop     eax
8404a81d 5a              pop     edx
8404a81e 64ff05b0060000  inc     dword ptr fs:[6B0h]
8404a825 8bf2            mov     esi,edx
8404a827 33c9            xor     ecx,ecx
8404a829 8b570c          mov     edx,dword ptr [edi+0Ch]
8404a82c 8b3f            mov     edi,dword ptr [edi]
8404a82e 8a0c10          mov     cl,byte ptr [eax+edx]
8404a831 8b1487          mov     edx,dword ptr [edi+eax*4]
8404a834 2be1            sub     esp,ecx
8404a836 c1e902          shr     ecx,2
8404a839 8bfc            mov     edi,esp
8404a83b 3b3504571784    cmp     esi,dword ptr [nt!MmUserProbeAddress (84175704)]
8404a841 0f832e020000    jae     nt!KiSystemCallExit2+0xa5 (8404aa75)
8404a847 f3a5            rep movs dword ptr es:[edi],dword ptr [esi]
8404a849 f6456c01        test    byte ptr [ebp+6Ch],1
8404a84d 7416            je      nt!KiFastCallEntry+0x115 (8404a865)
8404a84f 648b0d24010000  mov     ecx,dword ptr fs:[124h]

在这段代码里面系统须要依据 SSDT调用号找到所在的地址,所以必须回出现 EAX*4 这个字眼,果然。我们就在这里发现了它。

8404a831 8b1487          mov     edx,dword ptr [edi+eax*4]

那么 edi 必须就是 SSDT大数组的起始地址。
我们须要找到它是在哪里被赋值的。
往上发现:

8404a82c 8b3f            mov     edi,dword ptr [edi]

往上找 edi:

8404a7df 8bf8            mov     edi,eax
8404a7e1 c1ef08          shr     edi,8
8404a7e4 83e710          and     edi,10h
8404a7e7 8bcf            mov     ecx,edi
8404a7e9 03bebc000000    add     edi,dword ptr [esi+0BCh]

往上找 esi:

8404a78d 8bb324010000    mov     esi,dword ptr [ebx+124h]

往上找 ebx:

8404a784 648b1d1c000000  mov     ebx,dword ptr fs:[1Ch]

我们知道 fs寄存器 是专门指向 TEB 结构的。
fs:[1ch] 处:EnvironmentPointer:环境指针。

那么我们在 8404a831 处(mov edx,dword ptr [edi+eax*4])下断点。

3: kd> bp 8404a831
3: kd> bl
 0 e 759ecca9     0001 (0001) kernel32!CreateFileW
 1 e 7574aa1f     0001 (0001) KERNELBASE!CreateFileW+0x35c
 2 e 8404a750     0001 (0001) nt!KiFastCallEntry ".if (@eax & 0x0‘ffffffff)=0x0‘42 {} .else {gc}"
 3 e 8404a831     0001 (0001) nt!KiFastCallEntry+0xe1

运行:

3: kd> g
Breakpoint 3 hit
nt!KiFastCallEntry+0xe1:
8404a831 8b1487          mov     edx,dword ptr [edi+eax*4]

看一下此时 edi 的值(数组基址)

3: kd> r edi
edi=8407173c

此地址的内容:

3: kd> dd edi
8407173c  8424fa7a 8409ff84 84287e50 840cbb2e
8407174c  8426a1c1 8410b9d2 842f6d4d 842f6d96
8407175c  84273c93 84310424 8431167d 841e1f06
8407176c  84281082 842ea209 842728cb 8426e15a
8407177c  841a352d 842dc3de 841e7f2a 8421fe43
8407178c  84265890 841e00e9 84233141 8427ba08
8407179c  84273989 841fd65f 84273769 8423cfc0
840717ac  84274833 842d743f 842557da 842474a0

全部都是一些 以 84 开头的地址
曾经两个为例,反汇编看一下:

3: kd> u 8407173c
nt!KiServiceTable:(SSDT首地址)
8407173c 7afa            jp      nt!KeFlushMultipleRangeTb+0x2e9 (84071738)
8407173e 2484            and     al,84h
84071740 84ff            test    bh,bh
84071742 0984507e28842e  or      dword ptr [eax+edx*2+2E84287Eh],eax
84071749 bb0c84c1a1      mov     ebx,0A1C1840Ch
8407174e 2684d2          test    dl,dl
84071751 b910844d6d      mov     ecx,6D4D8410h
84071756 2f              das
3: kd> u 8424fa7a
nt!NtAcceptConnectPort:(第一个函数)
8424fa7a 8bff            mov     edi,edi
8424fa7c 55              push    ebp
8424fa7d 8bec            mov     ebp,esp
8424fa7f 64a124010000    mov     eax,dword ptr fs:[00000124h]
8424fa85 66ff8884000000  dec     word ptr [eax+84h]
8424fa8c 56              push    esi
8424fa8d 57              push    edi
8424fa8e 6a01            push    1

you know it. :)
从 NtCreateFile 函数中開始后的流程大致为:

  • [SharedUserData!SystemCallStub]=ntdll!KiFastSystemCall
  • sysenter
  • nt!KiFastCallEntry
  • 查找调用号在SSDT的地址

最后再来回想一下 ring3-ring0 的步骤:
1. 系统首先会将要调用的系统调用号(SSDT调用号)放入 EAX 中。
2. 然后将当前栈指针 ESP 的内容放入 EDX 中后运行SYSENTER 指令;
3. SYSENTER 被运行后会将控制权传递给特殊模块寄存器 IA32_SYSENTER_EIP 所指向的函数中,完毕兴许操作。


写完这个流水账之后发现了这篇文章 《重要》从用户模式切换到内核模式的完整过程分析。解说的更为清晰透彻。

我等文笔什么时候才干达成这样的成就。:(

跟踪 Ring3 - Ring0 的运行流程

标签:form   .dll   内存   stc   搜索   initial   symbols   ogr   pen   

原文地址:http://www.cnblogs.com/yfceshi/p/7389067.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!