📄 jiurl玩玩win2k内存篇 内存共享(二) copyonwrite.htm
字号:
00 00 00 00 00 NOTEPAD.EXE.....<BR>0023:77FCE340 00000000 00000000
00000000 00000000 ................<BR>0023:C01DFF38 0200B225 00000000
00000000 00000000 %...............<BR>NTICE: Load32 START=76AF0000
SIZE=3E000 KPEB=80D5AD40 MOD=comdlg32<BR>NTICE: Load32 START=77C50000
SIZE=4A000 KPEB=80D5AD40 MOD=SHLWAPI<BR>NTICE: Load32 START=77F40000
SIZE=3C000 KPEB=80D5AD40 MOD=gdi32<BR>NTICE: Load32 START=77E60000
SIZE=D5000 KPEB=80D5AD40 MOD=kernel32<BR>NTICE: Load32 START=77DF0000
SIZE=64000 KPEB=80D5AD40 MOD=user32<BR>NTICE: Load32 START=77D90000
SIZE=5A000 KPEB=80D5AD40 MOD=advapi32<BR>NTICE: Load32 START=77D20000
SIZE=6F000 KPEB=80D5AD40 MOD=rpcrt4<BR>NTICE: Load32 START=77B30000
SIZE=8A000 KPEB=80D5AD40 MOD=COMCTL32<BR>NTICE: Load32 START=77560000
SIZE=240000 KPEB=80D5AD40 MOD=shell32<BR>NTICE: Load32 START=78000000
SIZE=46000 KPEB=80D5AD40 MOD=MSVCRT<BR><BR>// ET=4.43
milliseconds<BR>Break due to BPX #0008:8044BE22 DO "db
((ffdff124->0)+44)->0+1fc l 10 ; dd ecx<BR>l 4 ; dd edx l 4"
(ET=4.43 milliseconds)<BR>0023:80D5AF3C 4E 4F 54 45 50 41 44 2E-45 58 45
00 00 00 00 00 NOTEPAD.EXE.....<BR>0023:78033000 0003A09A 00039BC6
00039BD2 00039BE2 ................<BR>0023:C01E00CC 00714225 00000000
00000000 00000000 %Bq.............<BR>NTICE: Load32 START=777C0000
SIZE=1D000 KPEB=80D5AD40 MOD=WINSPOOL<BR><BR>// ET=2.41
milliseconds<BR>Break due to BPX #0008:8044BE22 DO "db
((ffdff124->0)+44)->0+1fc l 10 ; dd ecx<BR>l 4 ; dd edx l 4"
(ET=2.41 milliseconds)<BR>0023:80D5AF3C 4E 4F 54 45 50 41 44 2E-45 58 45
00 00 00 00 00 NOTEPAD.EXE.....<BR>0023:77EBF060 00000000 00000000
00000000 00000000 ................<BR>0023:C01DFAFC 04B56225 00000000
00000000 00000000 %b..............<BR><BR>// ET=250.33
microseconds<BR>Break due to BPX #0008:8044BE22 DO "db
((ffdff124->0)+44)->0+1fc l 10 ; dd ecx<BR>l 4 ; dd edx l 4"
(ET=250.33 microseconds)<BR>0023:80D5AF3C 4E 4F 54 45 50 41 44 2E-45 58 45
00 00 00 00 00 NOTEPAD.EXE.....<BR>0023:77EC0800 00000000 00000000
00000000 00000000 ................<BR>0023:C01DFB00 04737225 00000000
00000000 00000000 %rs.............<BR><BR>// 几个中断之后,可以看到每个中断的 PteAddress
中的页表项的标志 ReadOnly CopyOnWrite 都被设置<BR>Break due to BPX #0008:8044BE22 DO
"db ((ffdff124->0)+44)->0+1fc l 10 ; dd ecx<BR>l 4 ; dd edx l 4"
(ET=2.07 milliseconds)<BR>0023:80D5AF3C 4E 4F 54 45 50 41 44 2E-45 58 45
00 00 00 00 00 NOTEPAD.EXE.....<BR>0023:77E484D0 00000000 00000000
00000000 00000000 ................<BR>0023:C01DF920 03B1A225 00000000
00000000 00000000 %...............<BR>// 我们看这时载入的 dll,已经载入了比刚才多的多的 dll
,这说明了刚才的判断是对的,在程序载入 dll // 时,dll 初始化时就引发了 Copy On Write<BR>:map32
-u<BR>Owner Obj Name Obj# Address Size Type<BR>NOTEPAD .text 0001
001B:01001000 000065CA CODE RO<BR>NOTEPAD .data 0002 0023:01008000
00001944 IDATA RW<BR>NOTEPAD .rsrc 0003 0023:0100A000 00005238 IDATA
RO<BR>comdlg32 .text 0001 001B:76AF1000 00029D3A CODE RO<BR>comdlg32 .data
0002 0023:76B1B000 00003668 IDATA RW<BR>comdlg32 .rsrc 0003 0023:76B1F000
0000B2A8 IDATA RO<BR>comdlg32 .reloc 0004 0023:76B2B000 000022B0 IDATA
RO<BR>shell32 .text 0001 001B:77561000 0011A686 CODE RO<BR>shell32 .data
0002 0023:7767C000 00003AE8 IDATA RW<BR>shell32 .rsrc 0003 0023:77680000
00110ED8 IDATA RO<BR>shell32 .reloc 0004 0023:77791000 0000EA90 IDATA
RO<BR>WINSPOOL .text 0001 001B:777C1000 00016B56 CODE RO<BR>WINSPOOL .data
0002 0023:777D8000 00002AF0 IDATA RW<BR>WINSPOOL .rsrc 0003 0023:777DB000
000009A8 IDATA RO<BR>WINSPOOL .reloc 0004 0023:777DC000 00000FC8 IDATA
RO<BR>COMCTL32 .text 0001 001B:77B31000 000643C2 CODE RO<BR>COMCTL32 .data
0002 0023:77B96000 000004A0 IDATA RW<BR>COMCTL32 .rsrc 0003 0023:77B97000
0001E948 IDATA RO<BR>COMCTL32 .reloc 0004 0023:77BB6000 00003784 IDATA
RO<BR>SHLWAPI .text 0001 001B:77C51000 0004243C CODE RO<BR>SHLWAPI .data
0002 0023:77C94000 00000C28 IDATA RW<BR>SHLWAPI .rsrc 0003 0023:77C95000
000010E8 IDATA RO<BR>SHLWAPI .reloc 0004 0023:77C97000 0000256C IDATA
RO<BR>rpcrt4 .text 0001 001B:77D21000 0005FABA CODE RO<BR>rpcrt4 .orpc
0002 001B:77D81000 00007CFC CODE RO<BR>rpcrt4 .data 0003 0023:77D89000
00000F5C IDATA RW<BR>rpcrt4 .rsrc 0004 0023:77D8A000 000003D0 IDATA
RO<BR>rpcrt4 .reloc 0005 0023:77D8B000 00003800 IDATA RO<BR>advapi32 .text
0001 001B:77D91000 0004F330 CODE RO<BR>advapi32 .data 0002 0023:77DE1000
00002E4C IDATA RW<BR>advapi32 .rsrc 0003 0023:77DE4000 00001250 IDATA
RO<BR>advapi32 .reloc 0004 0023:77DE6000 0000381C IDATA RO<BR>user32 .text
0001 001B:77DF1000 0005692A CODE RO<BR>user32 .data 0002 0023:77E48000
00000E60 IDATA RW<BR>user32 .rsrc 0003 0023:77E49000 0000742C IDATA
RO<BR>user32 .reloc 0004 0023:77E51000 00002ACC IDATA RO<BR>kernel32 .text
0001 001B:77E61000 0005D1AE CODE RO<BR>kernel32 .data 0002 0023:77EBF000
00001A30 IDATA RW<BR>kernel32 .rsrc 0003 0023:77EC1000 00070000 IDATA
RO<BR>kernel32 .reloc 0004 0023:77F31000 0000359C IDATA RO<BR>gdi32 .text
0001 001B:77F41000 0003649E CODE RO<BR>gdi32 .data 0002 0023:77F78000
00000CFC IDATA RW<BR>gdi32 .rsrc 0003 0023:77F79000 00000398 IDATA
RO<BR>gdi32 .reloc 0004 0023:77F7A000 0000151C IDATA RO<BR>ntdll .text
0001 001B:77F81000 00042492 CODE RO<BR>ntdll ECODE 0002 001B:77FC4000
00004371 CODE RO<BR>ntdll PAGE 0003 001B:77FC9000 00003983 CODE
RO<BR>ntdll .data 0004 0023:77FCD000 00002350 IDATA RW<BR>ntdll .rsrc 0005
0023:77FD0000 00026D08 IDATA RO<BR>ntdll .reloc 0006 0023:77FF7000
00001DA8 IDATA RO<BR>MSVCRT .text 0001 001B:78001000 0003174D CODE
RO<BR>MSVCRT .rdata 0002 0023:78033000 000075B4 IDATA RO<BR>MSVCRT .data
0003 0023:7803B000 00006D84 IDATA RW<BR>MSVCRT .rsrc 0004 0023:78042000
000003A8 IDATA RO<BR>MSVCRT .reloc 0005 0023:78043000 00002600 IDATA
RO<BR>:bd *<BR>// 还有更多的中断,不过这些对我们已经够了,所以关中断。<BR><BR>我们看到了这些 dll
的数据页初始都是设置了 CopyOnWrite 标志,只是由于在载入时,DllMain 对 dll 初始化时就向数据页中写数据,使得页表项的标志从
255 变成了 67。这就解释了为什么我们在一个进程的页表中几乎看不到设置 CopyOnWrite 标志的页。<BR><BR>下面我们用
SoftICE 观察对页表项的改变,以及找到引起异常的指令<BR>:bl<BR>00) BPX #0008:8044BE22 DO "db
((ffdff124->0)+44)->0+1fc l 10 ; dd ecx l 4 ; d<BR>// 仍然在
MiCopyOnWrite 的入口地址下断点<BR><BR>// 运行一个记事本程序,断到了<BR>NTICE: Load32
START=1000000 SIZE=10000 KPEB=8409E700 MOD=NOTEPAD<BR>NTICE: Load32
START=77F80000 SIZE=79000 KPEB=8409E700 MOD=ntdll<BR>Break due to BPX
#0008:8044BE22 DO "db ((ffdff124->0)+44)->0+1fc l 10 ; dd ecx<BR>l 4
; dd edx l 4" (ET=2.08 seconds)<BR>0023:8409E8FC 4E 4F 54 45 50 41 44
2E-45 58 45 00 00 00 00 00 NOTEPAD.EXE.....<BR>0023:77FCD34C FFFFFFFF
00000000 00000000 00000000 ................<BR>0023:C01DFF34 006AA225
00000000 00000000 00000000 %.j.............<BR>// 可以看到 BadAddress=
77FCD34C ,PteAddress=C01DFF34 ,Pte= 006AA225<BR><BR>// 我们在 PteAddress 的
4个字节内存上 下一个断点,这样,如果改变 Pte 就会被我们断到<BR>:bpmd c01dff34 w<BR><BR>//
被断到了<BR>Break due to BPMD #0023:C01DFF34 W DR3 (ET=280.80
microseconds)<BR>MSR LastBranchFromIp=80001ECA<BR>MSR
LastBranchToIp=8044BF69<BR>:bd 1<BR>// 关闭断点1<BR><BR>// 显示 Pte<BR>:dd
c01dff34 l 10<BR>0023:C01DFF34 00FEA067 00000000 00000000 00000000
g...............<BR>// 可以看到 Pte 的改变,物理页从 006AA 变成了 新的物理页 00FEA <BR>//
标志 从 225 变成了 067<BR><BR>// 反汇编向 Pte 写入新内容的指令<BR>// 使用 kd, u 8044bf6f 可以看到
MiCopyOnWrite+15c ,也就是说 MiCopyOnWrite 改变了 Pte 中的内容<BR>:u 8044bf6f l
10<BR>0008:8044BF6F MOV [EAX],ESI<BR>0008:8044BF71 MOV
EAX,[EBP-24]<BR>0008:8044BF74 INVLPG [EAX]<BR>0008:8044BF77 MOV
ECX,EBX<BR>0008:8044BF79 CALL 80449BCE<BR>0008:8044BF7E MOV
EAX,FS:[00000124]<BR><BR>// F12 (F12=^p ret;)<BR>// F12<BR><BR>// 反汇编调用
MiCopyOnWrite 的部分<BR>// 使用 kd, u 80447672 可以看到
ntoskrnl!MmAccessFault+834<BR>:u 80447672 l 10<BR>0008:80447672 CALL
8044BE21<BR>0008:80447677 MOV EBX,00000112<BR>0008:8044767C MOV
EAX,[EBP-1C]<BR>0008:8044767F MOV ECX,[EBP-20]<BR><BR>// F12<BR><BR>//
反汇编调用 MmAccessFault 的部分<BR>// 使用 kd, u 80464961 可以看到
ntoskrnl!KiTrap0E+be<BR>:u 80464961 l 10<BR>0008:80464961 CALL
80446DD4<BR>0008:80464966 CMP BYTE PTR [80471A38],00<BR>0008:8046496D JZ
8046497A<BR>0008:8046496F MOV EBX,[EBP+68]<BR><BR>// 在 KiTrap0E 中我们可以找到
CPU 压入的引起异常的指令,在 EBP+68 处<BR>:dd ebp+68 l 10<BR>0010:EBA0CDCC 77F89798
0000001B 00000246 0006FCA4 ...w....F.......<BR>// 引起异常的指令地址是
77F89798<BR><BR>// 我们向前一点反汇编就可以看到是 ntdll!RtlTryEnterCriticalSection
中的指令<BR>// 0008:77F89798 CMPXCHG [ECX+04],EDX<BR>// 写入 CopyOnWrite
页时引起的异常<BR>:u 77f89784 l 20<BR>0008:77F89784 JMP
77F8350F<BR>ntdll!RtlTryEnterCriticalSection<BR>0008:77F89789 MOV
ECX,[ESP+04]<BR>0008:77F8978D MOV EAX,FFFFFFFF<BR>0008:77F89792 MOV
EDX,00000000<BR>0008:77F89797 NOP<BR>0008:77F89798 CMPXCHG
[ECX+04],EDX<BR>0008:77F8979C JNZ 77F8F47B<BR>0008:77F897A2 MOV
EAX,FS:[00000024]<BR>:bd *<BR><BR></FONT><BR>欢迎交流,欢迎交朋友,<BR>欢迎访问 <A
href="http://jiurl.yeah.net/">http://jiurl.yeah.net/</A> <A
href="http://jiurl.cosoft.org.cn/forum">http://jiurl.cosoft.org.cn/forum</A>
<P><BR><BR><BR><BR></P></TD></TR></TBODY></TABLE></DIV></BODY></HTML>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -