git-svn: trunk@2418
aCaB authored on 2006/10/20 03:29:04... | ... |
@@ -1892,7 +1892,19 @@ int cli_scanpe(int desc, cli_ctx *ctx) |
1892 | 1892 |
EC32(optional_hdr32.AddressOfEntryPoint) < EC32(section_hdr[nsections - 1].VirtualAddress) + EC32(section_hdr[nsections - 1].SizeOfRawData) - 0x3217 - 4 && |
1893 | 1893 |
memcmp(buff+4, "\xe8\x00\x00\x00\x00\x8b\x1c\x24\x83\xc3", 10) == 0) { |
1894 | 1894 |
|
1895 |
- char *spinned; |
|
1895 |
+ char *spinned; |
|
1896 |
+ int spinres; |
|
1897 |
+ |
|
1898 |
+ if(ctx->limits && ctx->limits->maxfilesize && fsize > ctx->limits->maxfilesize) { |
|
1899 |
+ cli_dbgmsg("PEspin: Size exceeded (fsize: %u, max: %lu)\n", fsize, ctx->limits->maxfilesize); |
|
1900 |
+ free(section_hdr); |
|
1901 |
+ if(BLOCKMAX) { |
|
1902 |
+ *ctx->virname = "PE.Pespin.ExceededFileSize"; |
|
1903 |
+ return CL_VIRUS; |
|
1904 |
+ } else { |
|
1905 |
+ return CL_CLEAN; |
|
1906 |
+ } |
|
1907 |
+ } |
|
1896 | 1908 |
|
1897 | 1909 |
if((spinned = (char *) cli_malloc(fsize)) == NULL) { |
1898 | 1910 |
free(section_hdr); |
... | ... |
@@ -1921,36 +1933,47 @@ int cli_scanpe(int desc, cli_ctx *ctx) |
1921 | 1921 |
return CL_EIO; |
1922 | 1922 |
} |
1923 | 1923 |
|
1924 |
- if(!unspin(spinned, fsize, section_hdr, nsections - 1, EC32(optional_hdr32.AddressOfEntryPoint), ndesc)) { |
|
1924 |
+ switch(unspin(spinned, fsize, section_hdr, nsections - 1, EC32(optional_hdr32.AddressOfEntryPoint), ndesc, ctx)) { |
|
1925 |
+ case 0: |
|
1925 | 1926 |
free(spinned); |
1926 |
- cli_dbgmsg("PESpin: Unpacked and rebuilt executable saved in %s\n", tempfile); |
|
1927 |
+ if(cli_leavetemps_flag) |
|
1928 |
+ cli_dbgmsg("PESpin: Unpacked and rebuilt executable saved in %s\n", tempfile); |
|
1929 |
+ else |
|
1930 |
+ cli_dbgmsg("PESpin: Unpacked and rebuilt executable\n"); |
|
1927 | 1931 |
fsync(ndesc); |
1928 | 1932 |
lseek(ndesc, 0, SEEK_SET); |
1929 |
- |
|
1930 | 1933 |
if(cli_magic_scandesc(ndesc, ctx) == CL_VIRUS) { |
1931 |
- free(section_hdr); |
|
1932 | 1934 |
close(ndesc); |
1933 |
- if(!cli_leavetemps_flag) { |
|
1935 |
+ if(!cli_leavetemps_flag) |
|
1934 | 1936 |
unlink(tempfile); |
1935 |
- free(tempfile); |
|
1936 |
- } else { |
|
1937 |
- free(tempfile); |
|
1938 |
- } |
|
1937 |
+ free(tempfile); |
|
1938 |
+ free(section_hdr); |
|
1939 | 1939 |
return CL_VIRUS; |
1940 | 1940 |
} |
1941 |
- |
|
1942 |
- } else { |
|
1941 |
+ close(ndesc); |
|
1942 |
+ if(!cli_leavetemps_flag) |
|
1943 |
+ unlink(tempfile); |
|
1944 |
+ break; |
|
1945 |
+ case 1: |
|
1943 | 1946 |
free(spinned); |
1947 |
+ close(ndesc); |
|
1948 |
+ unlink(tempfile); |
|
1944 | 1949 |
cli_dbgmsg("PESpin: Rebuilding failed\n"); |
1945 |
- } |
|
1946 |
- |
|
1947 |
- close(ndesc); |
|
1948 |
- if(!cli_leavetemps_flag) { |
|
1950 |
+ break; |
|
1951 |
+ case 2: |
|
1952 |
+ free(spinned); |
|
1953 |
+ close(ndesc); |
|
1949 | 1954 |
unlink(tempfile); |
1950 |
- free(tempfile); |
|
1951 |
- } else { |
|
1952 |
- free(tempfile); |
|
1955 |
+ cli_dbgmsg("PESpin: Size exceeded\n"); |
|
1956 |
+ if(BLOCKMAX) { |
|
1957 |
+ free(tempfile); |
|
1958 |
+ free(section_hdr); |
|
1959 |
+ *ctx->virname = "PE.Pespin.ExceededFileSize"; |
|
1960 |
+ return CL_VIRUS; |
|
1961 |
+ } |
|
1953 | 1962 |
} |
1963 |
+ free(tempfile); |
|
1964 |
+ |
|
1954 | 1965 |
} |
1955 | 1966 |
|
1956 | 1967 |
|
... | ... |
@@ -155,7 +155,7 @@ static uint32_t summit (char *src, int size) |
155 | 155 |
} |
156 | 156 |
|
157 | 157 |
|
158 |
-int unspin(char *src, int ssize, struct pe_image_section_hdr *sections, int sectcnt, uint32_t nep, int desc) { |
|
158 |
+int unspin(char *src, int ssize, struct pe_image_section_hdr *sections, int sectcnt, uint32_t nep, int desc, cli_ctx *ctx) { |
|
159 | 159 |
char *curr, *emu, *ep, *spinned; |
160 | 160 |
char **sects; |
161 | 161 |
int blobsz=0, j; |
... | ... |
@@ -371,6 +371,21 @@ int unspin(char *src, int ssize, struct pe_image_section_hdr *sections, int sect |
371 | 371 |
|
372 | 372 |
bitmap = cli_readint32(ep+0x3061); |
373 | 373 |
bitman = bitmap; |
374 |
+ |
|
375 |
+ if(ctx->limits && ctx->limits->maxfilesize) { |
|
376 |
+ unsigned long int filesize = 0; |
|
377 |
+ |
|
378 |
+ for (j=0; j<sectcnt; j++) { |
|
379 |
+ if (bitmap&1) { |
|
380 |
+ if ( filesize > ctx->limits->maxfilesize || (uint32_t)EC32(sections[j].VirtualSize) > ctx->limits->maxfilesize - filesize ) return 2; |
|
381 |
+ filesize += (uint32_t)EC32(sections[j].VirtualSize); |
|
382 |
+ } |
|
383 |
+ bitmap>>=1; |
|
384 |
+ } |
|
385 |
+ |
|
386 |
+ bitmap = bitman; |
|
387 |
+ } |
|
388 |
+ |
|
374 | 389 |
cli_dbgmsg("spin: Compression bitmap is %x\n", bitmap); |
375 | 390 |
if ( (sects= (char **) cli_malloc(sectcnt*sizeof(char *))) == NULL ) |
376 | 391 |
return 1; |
... | ... |
@@ -395,7 +410,7 @@ int unspin(char *src, int ssize, struct pe_image_section_hdr *sections, int sect |
395 | 395 |
sects[j] = src + EC32(sections[j].PointerToRawData); |
396 | 396 |
cli_dbgmsg("spin: Not growing sect%d\n", j); |
397 | 397 |
} |
398 |
- bitmap = bitmap >>1 & 0x7fffffff; |
|
398 |
+ bitmap>>=1; |
|
399 | 399 |
} |
400 | 400 |
|
401 | 401 |
cli_dbgmsg("spin: decompression complete\n"); |