mirror of
https://github.com/radareorg/radare2.git
synced 2025-02-12 17:48:33 +00:00
Fix #2455 - several ASAN crashes in the PE parser
This commit is contained in:
parent
55809a1bd3
commit
79b4820eaf
@ -411,8 +411,9 @@ static struct r_bin_pe_export_t* parse_symbol_table(struct PE_(r_bin_pe_obj_t)*
|
||||
} else {
|
||||
char *longname, name[128];
|
||||
ut32 *idx = (ut32 *) (buf+I+4) ;
|
||||
if (r_buf_read_at (bin->b, off+ *idx+shsz, (ut8*)name, 128)) {
|
||||
if (r_buf_read_at (bin->b, off+ *idx+shsz, (ut8*)name, 128)) {// == 128) {
|
||||
longname = name;
|
||||
name[sizeof(name)-1] = 0;
|
||||
D printf ("0x%08"PFMT64x" %s\n", text + sr->value, longname);
|
||||
strncpy ((char*)exp[symctr].name, longname, PE_NAME_LENGTH-1);
|
||||
} else {
|
||||
@ -542,8 +543,8 @@ static int PE_(r_bin_pe_init_imports)(struct PE_(r_bin_pe_obj_t) *bin) {
|
||||
bin->import_directory = NULL;
|
||||
if (import_dir_paddr != 0) {
|
||||
if (import_dir_size<1 || import_dir_size>maxidsz) {
|
||||
eprintf ("Warning: Invalid import directory size: 0x%x\n",
|
||||
import_dir_size);
|
||||
eprintf ("Warning: Invalid import directory size: 0x%x is now 0x%x\n",
|
||||
import_dir_size, maxidsz);
|
||||
import_dir_size = maxidsz;
|
||||
}
|
||||
bin->import_directory_offset = import_dir_offset;
|
||||
@ -1927,13 +1928,28 @@ struct r_bin_pe_import_t* PE_(r_bin_pe_get_imports)(struct PE_(r_bin_pe_obj_t) *
|
||||
if (!bin)
|
||||
return NULL;
|
||||
|
||||
if (bin->import_directory_offset+32 >= bin->b->length) {
|
||||
return NULL;
|
||||
}
|
||||
if (bin->import_directory_offset < bin->size && bin->import_directory_offset > 0) {
|
||||
void *last;
|
||||
curr_import_dir = (PE_(image_import_directory)*)(bin->b->buf + bin->import_directory_offset);
|
||||
dll_name_offset = curr_import_dir->Name;
|
||||
void *last = curr_import_dir + bin->import_directory_size;
|
||||
while (curr_import_dir->FirstThunk != 0 || curr_import_dir->Name != 0 ||
|
||||
if (bin->import_directory_offset<1) {
|
||||
return NULL;
|
||||
}
|
||||
if (bin->import_directory_size<1) {
|
||||
return NULL;
|
||||
}
|
||||
if (bin->import_directory_offset+bin->import_directory_size > bin->b->length) {
|
||||
eprintf ("Error: read (import directory too big)\n");
|
||||
bin->import_directory_size = bin->b->length - bin->import_directory_offset;
|
||||
}
|
||||
last = curr_import_dir + bin->import_directory_size;
|
||||
while (((void*)curr_import_dir+sizeof (*curr_import_dir)) < last && (
|
||||
curr_import_dir->FirstThunk != 0 || curr_import_dir->Name != 0 ||
|
||||
curr_import_dir->TimeDateStamp != 0 || curr_import_dir->Characteristics != 0 ||
|
||||
curr_import_dir->ForwarderChain != 0) {
|
||||
curr_import_dir->ForwarderChain != 0)) {
|
||||
dll_name_offset = curr_import_dir->Name;
|
||||
int rr = r_buf_read_at (bin->b,
|
||||
PE_(r_bin_pe_vaddr_to_paddr)(bin, dll_name_offset),
|
||||
@ -1944,10 +1960,11 @@ struct r_bin_pe_import_t* PE_(r_bin_pe_get_imports)(struct PE_(r_bin_pe_obj_t) *
|
||||
}
|
||||
if (!PE_(r_bin_pe_parse_imports)(bin, &imports, &nimp, dll_name,
|
||||
curr_import_dir->Characteristics,
|
||||
curr_import_dir->FirstThunk))
|
||||
curr_import_dir->FirstThunk)) {
|
||||
break;
|
||||
}
|
||||
curr_import_dir++;
|
||||
if ((void*)curr_import_dir>= last) {
|
||||
if (curr_import_dir+2 >= last) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -2008,17 +2025,35 @@ struct r_bin_pe_lib_t* PE_(r_bin_pe_get_libs)(struct PE_(r_bin_pe_obj_t) *bin) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (bin->import_directory_offset + bin->import_directory_size > bin->b->length) {
|
||||
eprintf ("import directory offset bigger than file\n");
|
||||
bin->import_directory_size = bin->b->length - bin->import_directory_offset;
|
||||
return NULL;
|
||||
}
|
||||
RStrHT *lib_map = r_strht_new();
|
||||
if (bin->import_directory_offset < bin->size && bin->import_directory_offset > 0) {
|
||||
void *last = NULL;
|
||||
// normal imports
|
||||
curr_import_dir = (PE_(image_import_directory)*)(
|
||||
bin->b->buf + bin->import_directory_offset);
|
||||
while (curr_import_dir->FirstThunk != 0 || curr_import_dir->Name != 0 ||
|
||||
if (bin->import_directory_offset+bin->import_directory_size > bin->b->length) {
|
||||
// chop
|
||||
bin->import_directory_size = bin->b->length - bin->import_directory_offset;
|
||||
eprintf ("Warning: read libs (import directory too big) %d %d size %d\n",
|
||||
bin->import_directory_offset, bin->import_directory_size, bin->b->length);
|
||||
//return NULL;
|
||||
}
|
||||
last = curr_import_dir + bin->import_directory_size;
|
||||
while ((void*)(curr_import_dir+1) < last && (
|
||||
curr_import_dir->FirstThunk != 0 || curr_import_dir->Name != 0 ||
|
||||
curr_import_dir->TimeDateStamp != 0 || curr_import_dir->Characteristics != 0 ||
|
||||
curr_import_dir->ForwarderChain != 0) {
|
||||
curr_import_dir->ForwarderChain != 0)) {
|
||||
name_off = PE_(r_bin_pe_vaddr_to_paddr)(bin, curr_import_dir->Name);
|
||||
len = r_buf_read_at (bin->b, name_off, (ut8*)libs[index].name, PE_STRING_LENGTH);
|
||||
if (len <2) { // minimum string length
|
||||
if (libs[index].name[0] == 0) { // minimum string length
|
||||
break;
|
||||
}
|
||||
if (len <2 || libs[index].name[0] == 0) { // minimum string length
|
||||
eprintf ("Error: read (libs - import dirs) %d\n", len);
|
||||
break;
|
||||
}
|
||||
@ -2038,6 +2073,10 @@ struct r_bin_pe_lib_t* PE_(r_bin_pe_get_libs)(struct PE_(r_bin_pe_obj_t) *bin) {
|
||||
}
|
||||
}
|
||||
curr_import_dir++;
|
||||
if ((void*)curr_import_dir >= last) {
|
||||
eprintf ("eof in imports dir\n");
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1551,7 +1551,13 @@ static int bin_libs (RCore *r, int mode) {
|
||||
r_cons_printf ("%s\n", lib);
|
||||
i++;
|
||||
}
|
||||
if (!mode) r_cons_printf ("\n%i libraries\n", i);
|
||||
if (!mode) {
|
||||
if (i==1) {
|
||||
r_cons_printf ("\n%i library\n", i);
|
||||
} else {
|
||||
r_cons_printf ("\n%i libraries\n", i);
|
||||
}
|
||||
}
|
||||
}
|
||||
return R_TRUE;
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user