公司内部文档安全软件coredump分析实例

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/xuzhina/article/details/39525345

系统: windows xp sp3 崩溃软件: 公司内部某文档安全软件 调试工具: windbg 反汇编工具: ida pro 5.5 介绍: 该文档安全软件是由公司内部vpn工具启动,当在vpn工具输入用户密码连接网络后,vpn工具会自动把文档安全软件启动, 但每次启动都会coredump. 由于电脑用了windbg作为实时调试器,每次启动windbg都会弹出来, 显示coredump位置 分析过程: coredump信息 (50c4.50d0): Access violation - code c0000005 (!!! second chance !!!) eax=00000000 ebx=01aa5c62 ecx=00000000 edx=7efefeff esi=01aa4e34 edi=0012dbe0 eip=10009ffb esp=0012d980 ebp=0012dae0 iopl=0         nv up ei pl zr na pe nc cs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000246 *** WARNING: Unable to verify checksum for C:\Program Files\MarkAny\Document SAFER\MAAgtClient.DLL *** ERROR: Symbol file could not be found.  Defaulted to export symbols for C:\Program Files\MarkAny\Document SAFER\MAAgtClient.DLL - MAAgtClient!CDRMLogin::SetDocHeaderByServerAcl+0x54a9: 10009ffb 8b01            mov     eax,dword ptr [ecx]  ds:0023:00000000=???????? 由上面可以看coredump是由于往空地址里取值. 由 *** ERROR: Symbol file could not be found.  Defaulted to export symbols for C:\Program Files\MarkAny\Document SAFER\MAAgtClient.DLL - 可知, coredump地址是位于MAAgtClient.DLL 用IDA打开MAAgtClient.DLL, 查看一下coredump地址的汇编, 看一下ecx是由哪里得到的. .text:10009FD1 loc_10009FD1:                           ; CODE XREF: _strcpy+5 j .text:10009FD1                                         ; _strcat+52 j ... .text:10009FD1                 mov     ecx, [esp+4+Source] .text:10009FD5                 test    ecx, 3 .text:10009FDB                 jz      short loc_10009FF6 .text:10009FDD .text:10009FDD loc_10009FDD:                           ; CODE XREF: _strcat+7D j .text:10009FDD                 mov     dl, [ecx] .text:10009FDF                 inc     ecx .text:10009FE0                 test    dl, dl .text:10009FE2                 jz      short loc_1000A048 .text:10009FE4                 mov     [edi], dl .text:10009FE6                 inc     edi .text:10009FE7                 test    ecx, 3 .text:10009FED                 jnz     short loc_10009FDD .text:10009FEF                 jmp     short loc_10009FF6 .text:10009FF1 ; --------------------------------------------------------------------------- .text:10009FF1 .text:10009FF1 loc_10009FF1:                           ; CODE XREF: _strcat+9E j .text:10009FF1                                         ; _strcat+B8 j .text:10009FF1                 mov     [edi], edx .text:10009FF3                 add     edi, 4 .text:10009FF6 .text:10009FF6 loc_10009FF6:                           ; CODE XREF: _strcat+6B j .text:10009FF6                                         ; _strcat+7F j .text:10009FF6                 mov     edx, 7EFEFEFFh .text:10009FFB                 mov     eax, [ecx] .text:10009FFD                 add     edx, eax .text:10009FFF                 xor     eax, 0FFFFFFFFh .text:1000A002                 xor     eax, edx .text:1000A004                 mov     edx, [ecx] .text:1000A006                 add     ecx, 4 .text:1000A009                 test    eax, 81010100h .text:1000A00E                 jz      short loc_10009FF1 .text:1000A010                 test    dl, dl .text:1000A012                 jz      short loc_1000A048 .text:1000A014                 test    dh, dh .text:1000A016                 jz      short loc_1000A03F .text:1000A018                 test    edx, 0FF0000h .text:1000A01E                 jz      short loc_1000A032 .text:1000A020                 test    edx, 0FF000000h .text:1000A026                 jz      short loc_1000A02A .text:1000A028                 jmp     short loc_10009FF1 从上面看,主要是这一行 .text:10009FD1                 mov     ecx, [esp+4+Source] 给ecx赋值的. Source这个是指代什么的数据呢? 在IDA中, 应该是这个函数开初就有定义. 由 .text:10009FD1 loc_10009FD1:                           ; CODE XREF: _strcpy+5 j .text:10009FD1                                         ; _strcat+52 j ... 可以看到 .text:10009FD1 是由_strcat, _strcpy来引用 先看一下_strcat的开始 .text:10009F70 ; char *__cdecl strcat(char *Dest, const char *Source) .text:10009F70 _strcat         proc near               ; CODE XREF: sub_1000F800+E6 p .text:10009F70                                         ; sub_1000F800+F7 p ... .text:10009F70 .text:10009F70 Dest            = dword ptr  4 .text:10009F70 Source          = dword ptr  8 和_strcpy的开始 .text:10009F60 ; char *__cdecl strcpy(char *Dest, const char *Source) .text:10009F60 _strcpy         proc near               ; CODE XREF: CDRMLogin::GetUserID(char *)+3C p .text:10009F60                                         ; CDRMLogin::GetLocalLoginPW(char *)+51 p ... .text:10009F60 .text:10009F60 Dest            = dword ptr  4 .text:10009F60 Source          = dword ptr  8 可以看到, Source是指向_strcat, _strcpy的第二个参数源字符串的地址. 当这个地址为空,就出现coredump. 那么这个空地址是从哪里传进来的? 还有, coredump的函数是_strcat还是_strcpy? 看一下堆栈: 0:000> kb ChildEBP RetAddr  Args to Child               WARNING: Stack unwind information not available. Following frames may be wrong. 0012dae0 0040bd5f 0012dbe0 0012eb4b 01aa5c56 MAAgtClient!CDRMLogin::SetDocHeaderByServerAcl+0x54a9 0012daf8 7c980d45 01aa4c14 01aa6038 01aa5c62 MADRMAgent!CAclCCF::~CAclCCF+0x2a1f 0012db54 7c937d3b 0012dc16 00000524 7c920000 ntdll!RtlWalkFrameChain+0xb3 0012dba4 7c937c02 7c920000 0012dc16 0012dc10 ntdll!LdrGetProcedureAddress+0x4b 0012dc74 7c92dfba 7c802277 7c92d34a 00000086 ntdll!RtlCompareUnicodeString+0x412 00000000 00000000 00000000 00000000 00000000 ntdll!NtWriteVirtualMemory+0xc 根据x86的调用约定, 0040bd5f是上一层的调用者返回地址. 详情请见<coredump问题原理探究>第三章. 先看一下0040bd5f是位于哪个模块 0:000> lm start    end        module name 00390000 003e1000   cipher     (deferred)              003f0000 003f9000   Normaliz   (deferred)              00400000 0053b000   MADRMAgent   (export symbols)       C:\Program Files\MarkAny\Document SAFER\MADRMAgent.exe 01540000 0157f000   Encryption   (deferred)              01fe0000 0202a000   VrvHook    (deferred)              020e0000 02108000   ImageSAFERFilter   (deferred)              10000000 10029000   MAAgtClient C (export symbols)       C:\Program Files\MarkAny\Document SAFER\MAAgtClient.DLL 13000000 1308f000   libdb41    (deferred)              1f840000 1f857000   odbcint    (deferred)              3e410000 3e4f7000   WININET    (deferred)              3eab0000 3ec9c000   iertutil   (deferred)              43ce0000 43e14000   urlmon     (deferred)              5adc0000 5adf7000   uxtheme    (deferred)              5fdd0000 5fe25000   NETAPI32   (deferred)              60fd0000 61025000   hnetcfg    (deferred)              61be0000 61bed000   MFC42LOC   (deferred)              62c20000 62c29000   LPK        (deferred)              68000000 68036000   rsaenh     (deferred)              719c0000 719fe000   mswsock    (deferred)              71a00000 71a08000   wshtcpip   (deferred)              71a10000 71a18000   WS2HELP    (deferred)              71a20000 71a37000   WS2_32     (deferred)              71a40000 71a4b000   WSOCK32    (deferred)              72240000 72245000   sensapi    (deferred)              72f70000 72f96000   WINSPOOL   (deferred)              73540000 7357d000   ODBC32     (deferred)              73640000 7366e000   msctfime   (deferred)              73d30000 73e22000   MFC42      (deferred)              73fa0000 7400b000   USP10      (deferred)              74680000 746cc000   MSCTF      (deferred)              759d0000 75a7f000   USERENV    (deferred)              75ff0000 76055000   MSVCP60    (deferred)              76060000 761b6000   setupapi   (deferred)              762f0000 762f5000   MSIMG32    (deferred)              76300000 7631d000   IMM32      (deferred)              76320000 76367000   comdlg32   (deferred)              76760000 7676c000   cryptdll   (deferred)              76990000 76ace000   ole32      (deferred)              76b10000 76b3a000   WINMM      (deferred)              76bc0000 76bcb000   psapi      (deferred)              76d30000 76d48000   iphlpapi   (deferred)              76d70000 76d92000   Apphelp    (deferred)              76e50000 76e5e000   rtutils    (deferred)              76e60000 76e72000   rasman     (deferred)              76e80000 76eaf000   TAPI32     (deferred)              76eb0000 76eec000   RASAPI32   (deferred)              76ef0000 76f17000   DNSAPI     (deferred)              76f90000 76f96000   rasadhlp   (deferred)              770f0000 7717b000   OLEAUT32   (deferred)              77180000 77283000   COMCTL32   (deferred)              77bd0000 77bd8000   VERSION    (deferred)              77be0000 77c38000   msvcrt     (deferred)              77c40000 77c65000   msv1_0     (deferred)              77d10000 77da0000   USER32     (deferred)              77da0000 77e49000   ADVAPI32   (deferred)              77e50000 77ee3000   RPCRT4     (deferred)              77ef0000 77f39000   GDI32      (deferred)              77f40000 77fb6000   SHLWAPI    (deferred)              77fc0000 77fd1000   Secur32    (deferred)              78480000 7850e000   MSVCP90    (deferred)              78520000 785c3000   MSVCR90    (deferred)              7c800000 7c91e000   kernel32   (deferred)              7c920000 7c9b6000   ntdll      (export symbols)       C:\WINDOWS\system32\ntdll.dll 7d590000 7dd84000   SHELL32    (deferred)              Unloaded modules: 71dd0000 71de5000   msapsspc.dll 78080000 78091000   MSVCRT40.dll 767c0000 767e9000   schannel.dll 765e0000 76675000   CRYPT32.dll 76db0000 76dc2000   MSASN1.dll 757f0000 75805000   digest.dll 72f10000 72f57000   msnsspc.dll 78080000 78091000   MSVCRT40.dll 02260000 0227c000   DSWrapper.dll 02280000 0228b000   MASYSID.dll 可见0040bd5f是位于C:\Program Files\MarkAny\Document SAFER\MADRMAgent.exe 用IDA打开MADRMAgent.exe , 并跳转0040bd5f的附近汇编. .text:0040BD57                 push    edx .text:0040BD58                 stosw .text:0040BD5A                 call    ?GetUserID@CDRMLogin@@QAEXPAD@Z ; CDRMLogin::GetUserID(char *) .text:0040BD5F                 lea     eax, [esp+102Ch+var_F38] 看来堆栈有一些调用没有显示.那么看一下CDRMLogin::GetUserID是在哪定义 0:000> x *!*GetUserID* 00396300 cipher!CFlexibleHeader::GetUserID (<no parameter info>) 0039bc80 cipher!CCCF::GetUserID (<no parameter info>) 003a1080 cipher!CDRMLogic::GetUserID (<no parameter info>) 10004473 MAAgtClient!CDRMLogin::GetUserID (<no parameter info>) 可见, CDRMLogin::GetUserID是在MAAgtClient.DLL定义 看一下它的汇编: .text:10004473 ; int __stdcall CDRMLogin__GetUserID(char *Dest) .text:10004473                 public ?GetUserID@CDRMLogin@@QAEXPAD@Z .text:10004473 ?GetUserID@CDRMLogin@@QAEXPAD@Z proc near ; DATA XREF: .rdata:off_1001AB68 o .text:10004473 .text:10004473 var_150         = byte ptr -150h .text:10004473 var_C           = dword ptr -0Ch .text:10004473 var_4           = dword ptr -4 .text:10004473 Dest            = dword ptr  8 .text:10004473 .text:10004473                 mov     eax, offset sub_10014714 .text:10004478                 call    __EH_prolog .text:1000447D                 sub     esp, 144h .text:10004483                 lea     ecx, [ebp+var_150] .text:10004489                 call    ds:??0CCCF@@QAE@XZ ; CCCF::CCCF(void) .text:1000448F                 and     [ebp+var_4], 0 .text:10004493                 lea     ecx, [ebp+var_150] .text:10004499                 call    ds:?CheckCCFValidity@CCCF@@QAEHXZ ; CCCF::CheckCCFValidity(void) .text:1000449F                 lea     ecx, [ebp+var_150] .text:100044A5                 call    ds:?GetUserID@CCCF@@QAEPADXZ ; CCCF::GetUserID(void) .text:100044AB                 push    eax             ; Source .text:100044AC                 push    [ebp+Dest]      ; Dest .text:100044AF                 call    _strcpy .text:100044B4                 or      [ebp+var_4], 0FFFFFFFFh .text:100044B8                 pop     ecx .text:100044B9                 pop     ecx .text:100044BA                 lea     ecx, [ebp+var_150] .text:100044C0                 call    ds:??1CCCF@@UAE@XZ ; CCCF::~CCCF(void) .text:100044C6                 mov     ecx, [ebp+var_C] .text:100044C9                 mov     large fs:0, ecx .text:100044D0                 leave .text:100044D1                 retn    4 .text:100044D1 ?GetUserID@CDRMLogin@@QAEXPAD@Z endp 从 .text:100044A5                 call    ds:?GetUserID@CCCF@@QAEPADXZ ; CCCF::GetUserID(void) .text:100044AB                 push    eax             ; Source .text:100044AC                 push    [ebp+Dest]      ; Dest .text:100044AF                 call    _strcpy

可知,coredump的地址是位于_strcpy, 而_strcpy的第二个参数是CCCF::GetUserID的返回值.

从这里可以看到, 这里的代码是没有对CCCF::GetUserID的返回值进行判空处理, 从而导致coredump

至于是否会由于strcpy而导致栈溢出, 就先不管了.

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏osc同步分享

在springBoot项目中使用activiti

http://www.jvm123.com/2019/08/springboot-activiti/

3.4K7
来自专栏c#开发者

Biztalk 调用带Soap Head WebService的方法

    前天有位网友正好也提到了类似的问题,正好以前我也作过这方面的项目;在Biztalk Orchestration中调用对方发布的WebService;但必...

3486
来自专栏iOS122-移动混合开发研究院

【YFMemoryLeakDetector】人人都能理解的 iOS 内存泄露检测工具类

背景 即使到今天,iOS 应用的内存泄露检测,仍然是一个很重要的主题。我在一年前,项目中随手写过一个简单的工具类,当时的确解决了大问题。视图和控制器相关的内存泄...

2626
来自专栏ShaoYL

XCode调试器LLDB

1616
来自专栏草根专栏

使用静态基类方案让 ASP.NET Core 实现遵循 HATEOAS Restful Web API

Hypermedia As The Engine Of Application State (HATEOAS) HATEOAS(Hypermedia as t...

4365
来自专栏葡萄城控件技术团队

如何把Excel中的单元格等对象保存成图片

对于Excel中的很多对象,比如单元格(Cell),图形(shape),图表(chart)等等,有时需要将它们保存成一张图片。就像截图一样。 最近做一个Exc...

19010

当Vert.x符合Reactive eXtensions(Vert.x简介的第5部分)

这篇文章是我介绍Eclipse Vert.x系列的第五篇文章。在上一篇文章中,我们看到了Vert.x如何与数据库交互。我们使用Future对象来驯服Vert.x...

2082
来自专栏WeTest质量开放平台团队的专栏

手游热更新方案--Unity3D下的CsToLua技术

原文链接:http://wetest.qq.com/lab/view/387.html

2342
来自专栏企鹅号快讯

Java 9 逆天的十大新特性

在介绍 Java 9 之前,我们先来看看 Java 成立到现在的所有版本。 1990 年初,最初被命名为 Oak; 1995 年 5 月 23 日,Java 语...

2365
来自专栏walterlv - 吕毅的博客

每次都要重新编译?太慢!让跨平台的 MSBuild/dotnet build 的 Target 支持差量编译

发布于 2018-05-14 07:46 更新于 2018-07...

641

扫码关注云+社区

领取腾讯云代金券