福昕pdf阅读器和编辑器区别 福昕pdf阅读器 福昕高级pdf编辑器( 二 )


0:007> r r11,rdx,r8r11=00007ff873cdea80 rdx=ffff800792b063c0 r8=0000000000000206rdx的最初值为ffff800792b063c0+00007ff873cdea80=00000000`067e4e40可得三个参数如下:Dst:00007ff873cdea80Src:00000000`067e4e40Size:0000000000000206下边来看下 , 当前这两个内存区的数据:
0:007> du 00007ff873cdea8000007ff8`73cdea80&34;所有的组合电路都是不..可信的 。是的 , 往往有很多的毛刺啊 , 或者中&34;00007ff8`73cdeac0&34;间过程啊不可避免的出现 , 这&34;0:007> du 00000000`067e4e4000000000`067e4e40&34;所有的组合电路都是不..可信的 。是的 , 往往有很多的毛刺啊 , 或者中&34;00000000`067e4e80&34;间过程啊不可避免的出现 , 这&34;当前已经复制的长度如下:
0:007> ?rcx-r11Evaluate expression: 516 = 00000000`00000204而触发Crash的那个内存地址相对于Src的地址的偏移如下:
00007ff8`7380cb21 mov ax,word ptr [rdx+rcx] ds:00000000`067e5044=????0:007> ?00000000`067e5044-00000000`067e4e40Evaluate expression: 516 = 00000000`00000204 这两个是吻合的上的 , 现在看来 , 导致Crash的原因可能如下:
1、Size有问题 , 即传入的Size超过了Src的那块内存区的大小了 , 访问了后边不该访问的虚拟内存;
2、Size没问题 , 待访问的那块虚拟内存某些区间被释放掉了;
要知道这个答案 , 就需要溯源到上一级 , 因为memmove这个库函数出问题的几率是在太低了 。溯源到上一级有两种方法 , 栈回溯或者IDA的交叉引用 。我喜欢栈回溯 , 因为他“一锤定音” , 不存在多个可能 。根据上一小节的栈回溯可知 , caller的返回地址为:00007ff8`737d1c83 , 其汇编代码如下:
0:007> ub 00007ff8`737d1c83frdvpr_drv+0x11c5d:00007ff8`737d1c5d jefrdvpr_drv+0x11c8c (00007ff8`737d1c8c)00007ff8`737d1c5f callqword ptr [frdvpr_drv!DrvQueryDriverInfo+0x2dc158 (00007ff8`73abc5f8)]00007ff8`737d1c65 movrcx,rbx00007ff8`737d1c68 callqword ptr [frdvpr_drv!DrvQueryDriverInfo+0x2dc130 (00007ff8`73abc5d0)]00007ff8`737d1c6e learcx,[frdvpr_drv!DrvQueryDriverInfo+0x4fe5e0 (00007ff8`73cdea80)]00007ff8`737d1c75 movr8d,206h00007ff8`737d1c7b movrdx,rax00007ff8`737d1c7e callfrdvpr_drv!DrvQueryDriverInfo+0x2c4b0 (00007ff8`7380c950) ;memmove(0x00007ff8`73cdea80,rax,0x206)上边这段代码翻译完就是memmove(0x00007ff8`73cdea80,rax,0x206);我第一眼看到就感觉好奇怪 , 为啥把这个Size写死了 , 为啥要硬编码?带着疑问我们在往上翻一下 , 看看这个rax的值哪来的 。

福昕pdf阅读器和编辑器区别 福昕pdf阅读器 福昕高级pdf编辑器

文章插图
1 , 2 , 3号函数分别如下:
福昕pdf阅读器和编辑器区别 福昕pdf阅读器 福昕高级pdf编辑器

文章插图
即:
1—->调用的是hClipboard = USER32!GetClipboardData() , 而且传入的 uFormat参数由图可知是0x0D,即CF_UNICODETEXT;
2—->调用的是KERNEL32!GetLastErrorStub();
3—->调用的是lpMem = KERNEL32!GlobalLock(hClipboard);
4—–>memmove(0x00007ff8`73cdea80,lpMem,0x206)
都清楚了 , 原来是从剪贴板中读取UNICODE字符串 , 然后硬编码的Size为0x206;下边我们去IDA中看下 , 是不是这个逻辑 , 如下图:
福昕pdf阅读器和编辑器区别 福昕pdf阅读器 福昕高级pdf编辑器

文章插图
完全一样 , 好了 , 看一下unk_18051EA80这个全局变量 , 他的大小估计也是在0x206附近 , 确认下 , 如下图:
福昕pdf阅读器和编辑器区别 福昕pdf阅读器 福昕高级pdf编辑器

文章插图
现在可以完全推导出当时这个源码了 , 应该是这样的:
unk_18051EA80[0x208]={0};memmove(unk_18051EA80,lpMem,sizeof(unk_18051EA80)-sizeof(WCHAR)); 3、定因在第2节中提出来的两个原因 , 基本可以确定为Size过大了 , 下边简单看下后边的那块内存的属性 。如下:
福昕pdf阅读器和编辑器区别 福昕pdf阅读器 福昕高级pdf编辑器

文章插图

福昕pdf阅读器和编辑器区别 福昕pdf阅读器 福昕高级pdf编辑器

文章插图
【福昕pdf阅读器和编辑器区别 福昕pdf阅读器 福昕高级pdf编辑器】到此 , 便结束了 。实在是不该出现这样的问题 。