... | ... |
@@ -2093,23 +2093,23 @@ int cli_scanpe(cli_ctx *ctx) |
2093 | 2093 |
!memcmp(epbuff+0x63+offset, "\xaa\xe2\xcc", 3) && |
2094 | 2094 |
(fsize >= exe_sections[nsections-1].raw + 0xC6 + ecx + offset)) { |
2095 | 2095 |
|
2096 |
- char *spinned; |
|
2096 |
+ char *spinned; |
|
2097 | 2097 |
|
2098 |
- if((spinned = (char *) cli_malloc(fsize)) == NULL) { |
|
2099 |
- free(exe_sections); |
|
2100 |
- return CL_EMEM; |
|
2101 |
- } |
|
2098 |
+ if((spinned = (char *) cli_malloc(fsize)) == NULL) { |
|
2099 |
+ free(exe_sections); |
|
2100 |
+ return CL_EMEM; |
|
2101 |
+ } |
|
2102 | 2102 |
|
2103 |
- if((size_t) fmap_readn(map, spinned, 0, fsize) != fsize) { |
|
2104 |
- cli_dbgmsg("yC: Can't read %lu bytes\n", (unsigned long)fsize); |
|
2105 |
- free(spinned); |
|
2106 |
- free(exe_sections); |
|
2107 |
- return CL_EREAD; |
|
2108 |
- } |
|
2103 |
+ if((size_t) fmap_readn(map, spinned, 0, fsize) != fsize) { |
|
2104 |
+ cli_dbgmsg("yC: Can't read %lu bytes\n", (unsigned long)fsize); |
|
2105 |
+ free(spinned); |
|
2106 |
+ free(exe_sections); |
|
2107 |
+ return CL_EREAD; |
|
2108 |
+ } |
|
2109 | 2109 |
|
2110 |
- cli_dbgmsg("%d,%d,%d,%d\n", nsections-1, e_lfanew, ecx, offset); |
|
2111 |
- CLI_UNPTEMP("yC",(spinned,exe_sections,0)); |
|
2112 |
- CLI_UNPRESULTS("yC",(yc_decrypt(spinned, fsize, exe_sections, nsections-1, e_lfanew, ndesc, ecx, offset)),0,(spinned,0)); |
|
2110 |
+ cli_dbgmsg("%d,%d,%d,%d\n", nsections-1, e_lfanew, ecx, offset); |
|
2111 |
+ CLI_UNPTEMP("yC",(spinned,exe_sections,0)); |
|
2112 |
+ CLI_UNPRESULTS("yC",(yc_decrypt(spinned, fsize, exe_sections, nsections-1, e_lfanew, ndesc, ecx, offset)),0,(spinned,0)); |
|
2113 | 2113 |
} |
2114 | 2114 |
} |
2115 | 2115 |
|
... | ... |
@@ -40,7 +40,7 @@ |
40 | 40 |
/* ========================================================================== */ |
41 | 41 |
/* "Emulates" the poly decryptors */ |
42 | 42 |
|
43 |
-static int yc_poly_emulator(char* decryptor_offset, char* code, unsigned int ecx) |
|
43 |
+static int yc_poly_emulator(char* decryptor_offset, char* code, unsigned int ecx, uint32_t max_emu) |
|
44 | 44 |
{ |
45 | 45 |
|
46 | 46 |
/* |
... | ... |
@@ -64,7 +64,7 @@ static int yc_poly_emulator(char* decryptor_offset, char* code, unsigned int ecx |
64 | 64 |
unsigned char cl = ecx & 0xff; |
65 | 65 |
unsigned int j,i; |
66 | 66 |
|
67 |
- for(i=0;i<ecx;i++) /* Byte looper - Decrypts every byte and write it back */ |
|
67 |
+ for(i=0;i<ecx&&i<max_emu;i++) /* Byte looper - Decrypts every byte and write it back */ |
|
68 | 68 |
{ |
69 | 69 |
al = code[i]; |
70 | 70 |
|
... | ... |
@@ -168,7 +168,7 @@ int yc_decrypt(char *fbuf, unsigned int filesize, struct cli_exe_section *sectio |
168 | 168 |
unsigned int i; |
169 | 169 |
struct pe_image_file_hdr *pe = (struct pe_image_file_hdr*) (fbuf + peoffset); |
170 | 170 |
char *sname = (char *)pe + EC16(pe->SizeOfOptionalHeader) + 0x18; |
171 |
- |
|
171 |
+ uint32_t max_emu; |
|
172 | 172 |
/* |
173 | 173 |
|
174 | 174 |
First layer (decryptor of the section decryptor) in last section |
... | ... |
@@ -180,7 +180,7 @@ int yc_decrypt(char *fbuf, unsigned int filesize, struct cli_exe_section *sectio |
180 | 180 |
*/ |
181 | 181 |
cli_dbgmsg("yC: offset: %x, length: %x\n", offset, ecx); |
182 | 182 |
cli_dbgmsg("yC: decrypting decryptor on sect %d\n", sectcount); |
183 |
- if (yc_poly_emulator(fbuf + ycsect + 0x93, fbuf + ycsect + 0xc6, ecx)) |
|
183 |
+ if (yc_poly_emulator(fbuf + ycsect + 0x93, fbuf + ycsect + 0xc6, ecx, ecx)) |
|
184 | 184 |
return 1; |
185 | 185 |
filesize-=sections[sectcount].ursz; |
186 | 186 |
|
... | ... |
@@ -190,31 +190,38 @@ int yc_decrypt(char *fbuf, unsigned int filesize, struct cli_exe_section *sectio |
190 | 190 |
|
191 | 191 |
Start offset for analyze: Start of yC Section + 0x457 |
192 | 192 |
End offset for analyze: Start of yC Section + 0x487 |
193 |
- Lenght to decrypt - ECX = Raw Size of Section |
|
193 |
+ Length to decrypt - ECX = Raw Size of Section |
|
194 | 194 |
|
195 | 195 |
*/ |
196 | 196 |
|
197 | 197 |
|
198 | 198 |
/* Loop through all sections and decrypt them... */ |
199 |
- for(i=0;i<sectcount;i++) |
|
200 |
- { |
|
201 |
- uint32_t name = (uint32_t) cli_readint32(sname+i*0x28); |
|
202 |
- if (!sections[i].raw || |
|
203 |
- !sections[i].rsz || |
|
204 |
- name == 0x63727372 || /* rsrc */ |
|
205 |
- name == 0x7273722E || /* .rsr */ |
|
206 |
- name == 0x6F6C6572 || /* relo */ |
|
207 |
- name == 0x6C65722E || /* .rel */ |
|
208 |
- name == 0x6164652E || /* .eda */ |
|
209 |
- name == 0x6164722E || /* .rda */ |
|
210 |
- name == 0x6164692E || /* .ida */ |
|
211 |
- name == 0x736C742E || /* .tls */ |
|
212 |
- (name&0xffff) == 0x4379 /* yC */ |
|
199 |
+ for(i=0;i<sectcount;i++) { |
|
200 |
+ uint32_t name = (uint32_t) cli_readint32(sname+i*0x28); |
|
201 |
+ if (!sections[i].raw || |
|
202 |
+ !sections[i].rsz || |
|
203 |
+ name == 0x63727372 || /* rsrc */ |
|
204 |
+ name == 0x7273722E || /* .rsr */ |
|
205 |
+ name == 0x6F6C6572 || /* relo */ |
|
206 |
+ name == 0x6C65722E || /* .rel */ |
|
207 |
+ name == 0x6164652E || /* .eda */ |
|
208 |
+ name == 0x6164722E || /* .rda */ |
|
209 |
+ name == 0x6164692E || /* .ida */ |
|
210 |
+ name == 0x736C742E || /* .tls */ |
|
211 |
+ (name&0xffff) == 0x4379 /* yC */ |
|
213 | 212 |
) continue; |
214 |
- cli_dbgmsg("yC: decrypting sect%d\n",i); |
|
215 |
- if (yc_poly_emulator(fbuf + ycsect + (offset == -0x18 ? 0x3ea : 0x457), fbuf + sections[i].raw, sections[i].ursz)) |
|
216 |
- return 1; |
|
213 |
+ cli_dbgmsg("yC: decrypting sect%d\n",i); |
|
214 |
+ max_emu = filesize - sections[i].raw; |
|
215 |
+ if (max_emu > filesize) { |
|
216 |
+ cli_dbgmsg("yC: bad emulation length limit %u\n", max_emu); |
|
217 |
+ return 1; |
|
217 | 218 |
} |
219 |
+ if (yc_poly_emulator(fbuf + ycsect + (offset == -0x18 ? 0x3ea : 0x457), |
|
220 |
+ fbuf + sections[i].raw, |
|
221 |
+ sections[i].ursz, |
|
222 |
+ max_emu)) |
|
223 |
+ return 1; |
|
224 |
+ } |
|
218 | 225 |
|
219 | 226 |
/* Remove yC section */ |
220 | 227 |
pe->NumberOfSections=EC16(sectcount); |