首页 网络安全 安全学院 查看内容

Serv-U "MDTM"命令远程溢出分析

2009-2-4 05:16 607 0

摘要: 创建时间:2004-03-05文章属性:转载文章提交:peak (pe4k_at_eyou.com)Serv-U "MDTM"命令远程溢出分析     ...
关键词: nbsp text 0041 ebp eax push var loc mov call

创建时间:2004-03-05文章属性:转载文章提交:peak (pe4k_at_eyou.com)Serv-U "MDTM"命令远程溢出分析                                       czy 于 04.02.29    2月27号一早在securityfocus看到了这个漏洞的公告,上面清楚的说明了You must have a valid user account and password to exploit it, and you are not need WRITE or any other privilege.这不是比上次Serv-U那个site chmod的洞洞还利害,一想到不少电影网站都是用的Serv-U....    好不在这儿废话了以下分析基于Serv-U Server 4.0.0版,只分析"MDTM"命令溢出的情况。    事实上,Serv-U在处理MDTM命令时,很多地方都有长度判断,但是,有一个地方他遗漏了,那么,我们的机会就来了:-)漏洞函数引用关系如下:loc_434748 [0]|call    loc_41FAE8 [1]||__call    sub_59BFB8(strncpy)|__call    sub_4422A4            |            |__ jmp    sub_41FBB6 [2]                 |                 |__call    sub_59BEB1                 |__call    sub_59BDA4(strlen)                          |__call    sub_59BFB8(strncpy)\__分别调用了六次,用来把年月日时分秒放到变量中                 |__call    sub_5A4008         /                      ...........                      |__loc_41FD99[3]                         |__loc_41FDC3(strcpy) [4] 洞洞出来啦,覆盖程序自身异常处理函数地址                             |__loc_41FE16                                 |__loc_41FE30 [5]                                    |                                    |__call    sub_59BDA4(strlen)                                         |__call    sub_59BC1C(strncpy) 触发程序异常处理[0]判断是否是"MDTM"命令loc_434748:                             ; CODE XREF: .text:0043473A.text:00434748                 push    4                    //比较四个字节.text:0043474A                 push    edi                  //edi存放命令字串的首地址.text:0043474B                 lea     eax, [esi+354h].text:00434751                 push    eax                  // 得到命令列表.text:00434752                 call    near ptr unk_59C008  // 相当于Strncmp.text:00434757                 add     esp, 0Ch.text:0043475A                 test    eax, eax.text:0043475C                 jnz     short loc_43476D     //不是MDTM的话比较下一个命令SITE.text:0043475E                 push    edi                  //第二个参数是命令字串的首地址.text:0043475F                 push    ebx.text:00434760                 call    loc_41FAE8           //相同的话跳到MDTM命令处理函数.text:00434765                 add     esp, 8.text:00434768                 jmp     loc_434AC7           [1] 具体处理MDTM命令函数.text:0041FAE8 sub_41FAE8      proc near               ; CODE XREF: sub_434244+51Cp.text:0041FAE8                 push    ebp.text:0041FAE9                 mov     ebp, esp.text:0041FAEB                 add     esp, 0FFFFF004h         //为本地变量分配空间.text:0041FAF1                 push    eax.text:0041FAF2                 add     esp, 0FFFFFC74h         //为本地变量分配空间.text:0041FAF8                 mov     eax, offset unk_59C243  //重要程序自已的异常处理函数入口.text:0041FAFD                 xor     edx, edx.text:0041FAFF                 push    ebx.text:0041FB00                 push    esi.text:0041FB01                 push    edi.text:0041FB02                 mov     ebx, [ebp+8]            //处理第一个参数.text:0041FB05                 mov     dword ptr [ebp-4Ch], offset unk_5B8520   .text:0041FB0C                 mov     [ebp-48h], esp.text:0041FB0F                 mov     [ebp-50h], eax         //重要建立ERR结构的第二个成员                                   //也就是程序自已的异常处理函数入口.text:0041FB12                 mov     word ptr [ebp-44h], 0.text:0041FB18                 mov     [ebp-38h], edx.text:0041FB1B                 mov     ecx, large fs:0        //重要得到上一个ERR结构地址.text:0041FB22                 mov     [ebp-54h], ecx         //建立ERR结构的第一个成员.text:0041FB25                 lea     eax, [ebp-54h]         //得到当前ERR结构的地址(017AD280).text:0041FB28                 mov     large fs:0, eax        //放到fs:[0]中,这样如果这段代码                                  //出错的话就会执行ebp-50里的的函数.text:0041FB2E                 mov     byte ptr [ebp-55h], 0.text:0041FB32                 mov     byte ptr [ebp-56h], 0/////////////////////////////////////////////////////程序正常的栈情况如下:ebp-56 017AD27E 00ebp-55 017AD27F 00epb-54 017AD280 40ebp-53 017AD281 E2ebp-52 017AD282 7Aebp-51 017AD283 01 017AE240的值指向上一个ERR结构ebp-50 017AD284 43ebp-4F 017AD285 C2ebp-4E 017AD286 59ebp-4D 017AD287 00 0059C243是程序自已的异常处理函数入口////////////////////////////////////////////////////.text:0041FB36                 xor     edx, edx.text:0041FB38                 mov     [ebp-74h], edx.text:0041FB3B                 mov     [ebp-70h], edx.text:0041FB3E                 mov     [ebp-6Ch], edx.text:0041FB41                 mov     [ebp-68h], edx.text:0041FB44                 mov     [ebp-64h], edx.text:0041FB47                 mov     [ebp-60h], edx.text:0041FB4A                 mov     [ebp-5Ch], edx    //本地变量给初值0.text:0041FB4D                 push    7FFh.text:0041FB52                 mov     eax, [ebp+0Ch]    //处理第二个参数也就是命令字串的地址.text:0041FB55                 add     eax, 4            //去除命令字串开头的MDTM.text:0041FB58                 push    eax.text:0041FB59                 lea     ecx, [ebp-9FCh].text:0041FB5F                 push    ecx.text:0041FB60                 call    sub_59BFB8        //相当于strncpy把命令拷到本地变量ebp-9fch中                             //长度不超过2KB.text:0041FB65                 add     esp, 0Ch.text:0041FB68                 lea     eax, [ebp-9FCh].text:0041FB6E                 mov     byte ptr [ebp-1FDh], 0.text:0041FB75                 push    eax.text:0041FB76                 call    sub_4422A4        //对字串进行再一步处理去除MDTM与                             //命令中间的那个空格,命令后面的回车                                            //还要判断命令是否为空.text:0041FB7B                 cmp     byte ptr [ebp-9FCh], 0.text:0041FB82                 pop     ecx.text:0041FB83                 jnz     short loc_41FBB6  //合法的话跳[2] 对时间区域进行处理检测.text:0041FBB6 loc_41FBB6:                             ; CODE XREF: sub_41FAE8+9Bj.text:0041FBB6                 push    20h.text:0041FBB8                 lea     edx, [ebp+var_9FC]   //ebp-9fc中存放全部命令.text:0041FBBE                 push    edx.text:0041FBBF                 call    sub_59BEB1           //找命令中的空格找到后把空格后                                //的地址放在ebp-78中,也就是找文件名.text:0041FBC4                 add     esp, 8.text:0041FBC7                 mov     [ebp+var_78], eax.text:0041FBCA                 test    eax, eax.text:0041FBCC                 jz      loc_41FE6D           //没有找到文件名跳,跳过去将处理                                //mdtm autoexec.bat这类看文件时间的命令.text:0041FBD2                 lea     edx, [ebp+var_9FC].text:0041FBD8                 push    edx.text:0041FBD9                 call    sub_59BDA4           //得到命令长度.text:0041FBDE                 pop     ecx.text:0041FBDF                 cmp     eax, 10h             //命令长度小于16跳.text:0041FBE2                 jb      loc_41FE6D.text:0041FBE8                 lea     ecx, [ebp+var_9FC].text:0041FBEE                 mov     eax, [ebp+var_78].text:0041FBF1                 sub     eax, ecx             //得时间区域长度不要紧张这儿没洞洞.text:0041FBF3                 cmp     eax, 0Eh.text:0041FBF6                 jl      loc_41FE6D           //必须是大于等于14字节.text:0041FBFC                 mov     [ebp+var_88], 1.text:0041FC06                 xor     edi, edi.text:0041FC08                 lea     esi, [ebp+var_9FC].text:0041FC0E .text:0041FC0E loc_41FC0E:                             ; CODE XREF: sub_41FAE8+141j.text:0041FC0E                 movsx   eax, byte ptr [esi].text:0041FC11                 push    eax.text:0041FC12                 call    sub_5A1304.text:0041FC17                 pop     ecx.text:0041FC18                 test    eax, eax.text:0041FC1A                 jnz     short loc_41FC24.text:0041FC1C                 xor     edx, edx.text:0041FC1E                 mov     [ebp+var_88], edx.text:0041FC24 .text:0041FC24 loc_41FC24:                             ; CODE XREF: sub_41FAE8+132j.text:0041FC24                 inc     edi.text:0041FC25                 inc     esi.text:0041FC26                 cmp     edi, 0Eh.text:0041FC29                 jl      short loc_41FC0E.text:0041FC2B                 cmp     [ebp+var_88], 0.text:0041FC32                 jz      loc_41FD99             //判断时间区域的前14个字母                                                              //如果不是数字跳到41fd99//-----------------------.text:0041FC38                 push    4.text:0041FC3A                 lea     ecx, [ebp+var_9FC].text:0041FC40                 push    ecx.text:0041FC41                 lea     eax, [ebp+var_84].text:0041FC47                 push    eax.text:0041FC48                 call    sub_59BFB8.text:0041FC4D                 add     esp, 0Ch.text:0041FC50                 lea     edx, [ebp+var_84].text:0041FC56                 mov     [ebp+var_80], 0.text:0041FC5A                 push    edx.text:0041FC5B                 call    sub_5A4008.text:0041FC60                 pop     ecx.text:0041FC61                 mov     [ebp+var_5C], eax.text:0041FC64                 push    2.text:0041FC66                 lea     ecx, [ebp+var_9F8].text:0041FC6C                 push    ecx.text:0041FC6D                 lea     eax, [ebp+var_84].text:0041FC73                 push    eax.text:0041FC74                 call    sub_59BFB8.text:0041FC79                 add     esp, 0Ch.text:0041FC7C                 lea     edx, [ebp+var_84].text:0041FC82                 mov     [ebp+var_82], 0.text:0041FC89                 push    edx.text:0041FC8A                 call    sub_5A4008.text:0041FC8F                 pop     ecx.text:0041FC90                 mov     [ebp+var_60], eax.text:0041FC93                 push    2.text:0041FC95                 lea     ecx, [ebp+var_9F6].text:0041FC9B                 push    ecx.text:0041FC9C                 lea     eax, [ebp+var_84].text:0041FCA2                 push    eax.text:0041FCA3                 call    sub_59BFB8.text:0041FCA8                 add     esp, 0Ch.text:0041FCAB                 lea     edx, [ebp+var_84].text:0041FCB1                 mov     [ebp+var_82], 0.text:0041FCB8                 push    edx.text:0041FCB9                 call    sub_5A4008.text:0041FCBE                 pop     ecx.text:0041FCBF                 mov     [ebp+var_64], eax.text:0041FCC2                 push    2.text:0041FCC4                 lea     ecx, [ebp+var_9F4].text:0041FCCA                 push    ecx.text:0041FCCB                 lea     eax, [ebp+var_84].text:0041FCD1                 push    eax.text:0041FCD2                 call    sub_59BFB8.text:0041FCD7                 add     esp, 0Ch.text:0041FCDA                 lea     edx, [ebp+var_84].text:0041FCE0                 mov     [ebp+var_82], 0.text:0041FCE7                 push    edx.text:0041FCE8                 call    sub_5A4008.text:0041FCED                 pop     ecx.text:0041FCEE                 mov     [ebp+var_68], eax.text:0041FCF1                 push    2.text:0041FCF3                 lea     ecx, [ebp+var_9F2].text:0041FCF9                 push    ecx.text:0041FCFA                 lea     eax, [ebp+var_84].text:0041FD00                 push    eax.text:0041FD01                 call    sub_59BFB8.text:0041FD06                 add     esp, 0Ch.text:0041FD09                 lea     edx, [ebp+var_84].text:0041FD0F                 mov     [ebp+var_82], 0.text:0041FD16                 push    edx.text:0041FD17                 call    sub_5A4008.text:0041FD1C                 pop     ecx.text:0041FD1D                 mov     [ebp+var_6C], eax.text:0041FD20                 push    2.text:0041FD22                 lea     ecx, [ebp+var_9F0]  //得到命令中秒存放的位置.text:0041FD28                 push    ecx.text:0041FD29                 lea     eax, [ebp+var_84]   //变量地址.text:0041FD2F                 push    eax.text:0041FD30                 call    sub_59BFB8.text:0041FD35                 add     esp, 0Ch.text:0041FD38                 lea     edx, [ebp+var_84].text:0041FD3E                 mov     [ebp+var_82], 0.text:0041FD45                 push    edx.text:0041FD46                 call    sub_5A4008           //格式转化.text:0041FD4B                 pop     ecx .text:0041FD4C                 mov     [ebp+var_70], eax//---------------上面的代码把年月日时分秒放到变量中//具体如下:年 ebp-5c月 ebp-60日 ebp-64时 ebp-68分 ebp-6c秒 ebp-70//对时间的正确性进行检验.text:0041FD4F                 cmp     [ebp+var_5C], 7BCh          .text:0041FD56                 jl      short loc_41FD91           //年小于1980跳.text:0041FD58                 cmp     dword ptr [ebp-5Ch], 81Bh.text:0041FD5F                 jg      short loc_41FD91            //年大于2075跳.text:0041FD61                 cmp     dword ptr [ebp-60h], 1.text:0041FD65                 jl      short loc_41FD91.text:0041FD67                 cmp     dword ptr [ebp-60h], 0Ch  .text:0041FD6B                 jg      short loc_41FD91            //月分只能是1-12.text:0041FD6D                 cmp     dword ptr [ebp-64h], 1.text:0041FD71                 jl      short loc_41FD91.text:0041FD73                 cmp     dword ptr [ebp-64h], 1Fh.text:0041FD77                 jg      short loc_41FD91            //号数只能是1-31.text:0041FD79                 cmp     dword ptr [ebp-6Ch], 0.text:0041FD7D                 jl      short loc_41FD91.text:0041FD7F                 cmp     dword ptr [ebp-6Ch], 3Bh.text:0041FD83                 jg      short loc_41FD91.text:0041FD85                 cmp     dword ptr [ebp-70h], 0.text:0041FD89                 jl      short loc_41FD91.text:0041FD8B                 cmp     dword ptr [ebp-70h], 3Bh    //分秒只能是0-59.text:0041FD8F                 jle     short loc_41FD99            //时间都合法了跳到41FD99[3] 判断时间区域后面是否有+-号.text:0041FD99 .text:0041FD99 loc_41FD99:                             ; CODE XREF: sub_41FAE8+14Aj.text:0041FD99                                         ; sub_41FAE8+2A7j.text:0041FD99                 cmp     [ebp+var_88], 0.text:0041FDA0                 jz      loc_41FE30         //对于mdtm 20020201112233+111 autexec.bat这样的命令不跳.text:0041FDA6                 movsx   eax, [ebp+var_9EE] //处理时间区域后的一个字串.text:0041FDAD                 cmp     eax, 20h.text:0041FDB0                 jz      short loc_41FE1C   //为空格跳.text:0041FDB2                 movsx   eax, [ebp+var_9EE].text:0041FDB9                 cmp     eax, 2Dh.text:0041FDBC                 jz      short loc_41FDC3   //为减号跳!.text:0041FDBE                 cmp     eax, 2Bh.text:0041FDC1                 jnz     short loc_41FE1C   //不为加号跳到41FE1C![4] 对时间区域有+-号的情况进行处理.text:0041FDC3 loc_41FDC3:                             .text:0041FDC3                 xor     edi, edi.text:0041FDC5                 lea     eax, [ebp+var_84]    //得到时间区域的最后两位(ebp-84).text:0041FDCB                 lea     esi, [ebp+var_9EE]   //得到+号开始的地址.text:0041FDD1                 jmp     short loc_41FDDA.text:0041FDD3 loc_41FDD3:                            .text:0041FDD3                 mov     dl, [esi]            .text:0041FDD5                 inc     edi                  //edi为记数器.text:0041FDD6                 mov     [eax], dl.text:0041FDD8                 inc     eax.text:0041FDD9                 inc     esi.text:0041FDDA .text:0041FDDA loc_41FDDA:                            .text:0041FDDA                 movsx   ecx, byte ptr [esi].text:0041FDDD                 cmp     ecx, 20h.text:0041FDE0                 jnz     short loc_41FDD3           //遇到空格退出//----------------------上面就是漏洞代码程序本意是把时间区域加号后面的四个字节放在ebp-84变量中//但没有对长度进行检查,所以不但会覆盖ebp-84,如果是一个超长字串的话还会把ebp-54,ebp-78等变理覆盖!.text:0041FDE2                 mov     [ebp+edi+var_84], 0   //edi为考贝的字串长度,这儿是为拷过去的字中设置结尾符.text:0041FDEA                 lea     eax, [ebp+var_84].text:0041FDF0                 push    eax.text:0041FDF1                 call    sub_5A4008.text:0041FDF6                 pop     ecx.text:0041FDF7                 mov     [ebp+var_74], eax.text:0041FDFA                 cmp     [ebp+var_74], 0FFFFFC18h //比较+号后面的时间是否小于-1000.text:0041FE01                 jl      short loc_41FE0C.text:0041FE03                 cmp     [ebp+var_74], 3E8h.text:0041FE0A                 jle     short loc_41FE16         //是否大于等于+1000.text:0041FE0C .text:0041FE0C loc_41FE0C:                            .text:0041FE0C                 xor     eax, eax.text:0041FE0E                 mov     [ebp+var_88], eax.text:0041FE14                 jmp     short loc_41FE30.text:0041FE16 loc_41FE16:                             .text:0041FE16                 mov     [ebp+var_56], 1           //设置ebp-56为1.text:0041FE1A                 jmp     short loc_41FE30.text:0041FE1C loc_41FE1C:                             .text:0041FE1C                                         .text:0041FE1C                 movsx   edx, [ebp+var_9EE].text:0041FE23                 cmp     edx, 20h.text:0041FE26                 jz      short loc_41FE30.text:0041FE28                 xor     ecx, ecx.text:0041FE2A                 mov     [ebp+var_88], ecx[5] 拷贝要更改时间的文件名到一个变量中.text:0041FE30 loc_41FE30:                             .text:0041FE30                                         .text:0041FE30                 cmp     [ebp+var_88], 0           //设置的时间小于-1000时ebp-88为0跳.text:0041FE37                 jz      short loc_41FE6D.text:0041FE39                 mov     [ebp+var_55], 1.text:0041FE3D                 lea     eax, [ebp+var_9FC]        //得到+号后的命令长度.text:0041FE43                 push    eax.text:0041FE44                 call    sub_59BDA4.text:0041FE49                 pop     ecx.text:0041FE4A                 inc     eax.text:0041FE4B                 push    eax                       //拷贝的个数.text:0041FE4C                 mov     edx, [ebp+var_78]         //ebp-78为源地址存放文件名.text:0041FE4F                 inc     edx.text:0041FE50                 push    edx.text:0041FE51                 lea     ecx, [ebp+var_9FC]        //本来存放命令字串,现在是拷贝的目的地址.text:0041FE57                 push    ecx.text:0041FE58                 call    sub_59BC1C.text:0041FE5D                 add     esp, 0Ch.text:0041FE60                 lea     eax, [ebp+var_9FC].text:0041FE66                 push    eax.text:0041FE67                 call    sub_4422A4.text:0041FE6C                 pop     ecxQ&A:[1]为什么执行到loc_41FE30处会产生程序异常呢?   因为ebp-78这个变量的值本来是要改变文件时间的文件名的地址,但是由于在loc_41FDC3处对变量ebp-84的操作中会覆盖它的值,如果我们输入命令quote mdtm 20020102112233+aaaaaaaaaaaaaaaaaaaaaaaaaa /autoexec.bat那么这时ebp-78的值就成了61616161,而这个地址是不能仿问的,当然就产生异常了.[2]产生异常后我们怎么执行代码呢?   在分析刚开始的时候我们已经知道程序正常的异常处理程序入口在ebp-50中,那么我们只能把系统中有jmp ebx的代码的地址放到ebp-50中就可以了.然后ebp-54中放入nop nop jmp 6(9090EB04)[3]要发送多少个A才能刚好覆盖ebp-50,ebp-54呢?   84h-54h=30h=48d[4]我还不知道怎么利用SEH执行SHELLCODE怎么办?利用SEH执行shellcodehttp://www.nsfocus.net/index.php?act=magazine&do=view&mid=1964
声明:文章版权归原作者所有 部分文章转自互联网 如有侵权请联系 [邮箱地址] 删除

路过

雷人

握手

鲜花

鸡蛋

最新评论

返回顶部