前面已经有过几篇压缩壳的文章,接下来还是对于压缩壳的一点个人分析,
壳开始代码的其中一部分
代码:
loc_46B003: ; CODE XREF: startj .depack:0046B003 pusha .depack:0046B004 push offset dword_401000 ; .text .depack:0046B009 push 0A181h .depack:0046B00E call DePack .depack:0046B013 push offset unk_44B000 ; .rdata .depack:0046B018 push 0C81h .depack:0046B01D call DePack .depack:0046B022 push offset unk_457000 ; .data .depack:0046B027 push 581h .depack:0046B02C call DePack .depack:0046B031 nop .depack:0046B032 jmp short loc_46B035
代码:
push ebp mov ebp, esp pusha push ebp mov esi, [ebp+arg_0] mov edi, [ebp+arg_4] ; 401000 call sub_46B04F jmp short loc_46B053 DePack endp
add ebx, 200h
push ebx ; 46b24d
push edi ; 401000
发现其实壳是将压缩后的区块放到46b24d中进行处理的
DataCopy: ; 将数据段中数据转移出来,到:46b24d
mov eax, [edi]
mov [ebx], eax
add edi, 4 ; 下一DWORD
add ebx, 4
dec esi ; a181
jnz short DataCopy ; 将数据段中数据转移出来,到:46b24d
; ---------------------------------------------------------------------------
.depack:0046B11B
.depack:0046B11B loc_46B11B: ; CODE XREF: DePack+B4j
.depack:0046B11B dec eax
.depack:0046B11C shl eax, 8 ; offs <<= 8;
.depack:0046B11F mov al, [esi] ; offs += *ud.source;
.depack:0046B121 inc esi ; *ud.source++
.depack:0046B122 mov ebp, eax
.depack:0046B124 mov ecx, 1
.depack:0046B129
.depack:0046B129 loc_46B129: ; CODE XREF: DePack:loc_46B13Dj
.depack:0046B129 add dl, dl
.depack:0046B12B jnz short loc_46B132
.depack:0046B12D mov dl, [esi]
.depack:0046B12F inc esi
.depack:0046B130 adc dl, dl
.depack:0046B132
.depack:0046B132 loc_46B132: ; CODE XREF: DePack+EEj
.depack:0046B132 adc ecx, ecx
.depack:0046B134 add dl, dl
.depack:0046B136 jnz short loc_46B13D
.depack:0046B138 mov dl, [esi]
.depack:0046B13A inc esi
.depack:0046B13B adc dl, dl
.depack:0046B13D
.depack:0046B13D loc_46B13D: ; CODE XREF: DePack+F9j
.depack:0046B13D jb short loc_46B129
.depack:0046B13F cmp eax, 7D00h ; 32000
.depack:0046B144 jnb short loc_46B160 ; if (offs >= 32000) len++;
.depack:0046B146 cmp eax, 500h ; if (offs >= 1280) len++;
.depack:0046B14B jb short loc_46B15B ; if (offs < 128) len += 2;
.depack:0046B14D inc ecx
.depack:0046B14E push esi
.depack:0046B14F mov esi, edi
.depack:0046B151 sub esi, eax
.depack:0046B153 rep movsb
.depack:0046B155 pop esi
.depack:0046B156 jmp nexttag ; call getbit
.depack:0046B15B ; ---------------------------------------------------------------------------
.depack:0046B15B
.depack:0046B15B loc_46B15B: ; CODE XREF: DePack+10Ej
.depack:0046B15B cmp eax, 7Fh ; if (offs < 128) len += 2;
.depack:0046B15E ja short loc_46B163
.depack:0046B160
.depack:0046B160 loc_46B160: ; CODE XREF: DePack+107j
.depack:0046B160 add ecx, 2 ; len += 2;
.depack:0046B163
.depack:0046B163 loc_46B163: ; CODE XREF: DePack+121j
.depack:0046B163 push esi
.depack:0046B164 mov esi, edi
.depack:0046B166 sub esi, eax
.depack:0046B168 rep movsb
.depack:0046B16A pop esi
.depack:0046B16B jmp nexttag ; call getbit
.depack:0046B170 ; ---------------------------------------------------------------------------
.depack:0046B170
.depack:0046B170 loc_46B170: ; CODE XREF: DePack:loc_46B094j
.depack:0046B170 mov al, [esi]
.depack:0046B172 inc esi
.depack:0046B173 xor ecx, ecx
.depack:0046B175 shr al, 1
.depack:0046B178 jz short loc_46B18C
.depack:0046B17A adc ecx, 2
.depack:0046B17D mov ebp, eax
.depack:0046B17F push esi ; domatch
.depack:0046B180 mov esi, edi
.depack:0046B182 sub esi, eax
.depack:0046B184 rep movsb
.depack:0046B186 pop esi
.depack:0046B187 jmp nexttag ; call getbit
.depack:0046B18C ; ---------------------------------------------------------------------------
.depack:0046B18C
.depack:0046B18C loc_46B18C: ; CODE XREF: DePack+13Bj
.depack:0046B18C pop ebp
.depack:0046B18D sub edi, [ebp+arg_4]
.depack:0046B190 mov [ebp+var_4], edi
.depack:0046B193 popa
.depack:0046B194 pop ebp
.depack:0046B195 retn
一个和经典压缩算法了
getbit:
代码:
/* check if tag is empty */ if (!ud->bitcount--) { /* load next tag */ ud->tag = *ud->source++; ud->bitcount = 7; } /* shift bit out of tag */ bit = (ud->tag >> 7) & 0x01; ud->tag <<= 1; return bit[color=#008000];
代码:
if (aP_getbit(&ud)) { if (aP_getbit(&ud)) { if (aP_getbit(&ud)) { offs = 0; for (i = 4; i; i--) offs = (offs << 1) + aP_getbit(&ud); if (offs) { *ud.destination = *(ud.destination - offs); ud.destination++; } else { *ud.destination++ = 0x00; } LWM = 0; } else { offs = *ud.source++; len = 2 + (offs & 0x0001); offs >>= 1; if (offs) { for (; len; len--) { *ud.destination = *(ud.destination - offs); ud.destination++; } } else done = 1; R0 = offs; LWM = 1; } } else { offs = aP_getgamma(&ud); if ((LWM == 0) && (offs == 2)) { offs = R0; len = aP_getgamma(&ud); for (; len; len--) { *ud.destination = *(ud.destination - offs); ud.destination++; } } else { if (LWM == 0) offs -= 3; else offs -= 2; offs <<= 8; offs += *ud.source++; len = aP_getgamma(&ud); if (offs >= 32000) len++; if (offs >= 1280) len++; if (offs < 128) len += 2; for (; len; len--) { *ud.destination = *(ud.destination - offs); ud.destination++; } R0 = offs; } LWM = 1; } } else { *ud.destination++ = *ud.source++; LWM = 0; }
好好学习,天天进步!