//-------------------------------------------------------------------------- //lint -e{1764} could be declared const ref static int handle_symbol( reader_t &reader, int shndx, int _info, uint32 st_name, uval_t st_value, int namsec, symbol_visitor_t &sv) { if ( shndx == SHN_UNDEF || shndx == SHN_LOPROC || shndx == SHN_HIPROC || shndx == SHN_ABS ) { return 0; } int type = ELF_ST_TYPE(_info); if ( type != STT_OBJECT && type != STT_FUNC ) return 0; if ( st_name == 0 ) return 0; if ( imagebase != uval_t(-1) ) st_value -= imagebase; qstring name; reader.sections.get_name(&name, namsec, st_name); return sv.visit_symbol(st_value, name.c_str()); }
//-------------------------------------------------------------------------- //parse a mach-o file image in memory and enumerate its segments and symbols bool parse_macho(ea_t start, linput_t *li, symbol_visitor_t &sv, bool in_mem) { macho_file_t mfile(li); if ( !mfile.parse_header() || !mfile.select_subfile(CPUTYPE) ) { msg("Warning: bad file or could not find a member with matching cpu type\n"); return false; } // load sections const secvec_t §ions = mfile.get_sections(); const segcmdvec_t &segcmds = mfile.get_segcmds(); ea_t expected_base = BADADDR; for ( size_t i=0; i < segcmds.size(); i++ ) { const segment_command_64 &sg = segcmds[i]; if ( is_text_segment(sg) && expected_base == BADADDR ) { expected_base = sg.vmaddr; break; } } if ( expected_base == BADADDR ) return false; sval_t slide = start - expected_base; // msg("%a: expected base is %a; in_mem = %d\n", start, expected_base, in_mem); if ( (sv.velf & VISIT_SEGMENTS) != 0 ) { for ( size_t i=0; i < segcmds.size(); i++ ) { const segment_command_64 &sg = segcmds[i]; if ( sg.nsects == 0 ) sv.visit_segment(sg.vmaddr + slide, sg.vmsize, sg.segname); } for ( size_t i=0; i < sections.size(); i++ ) { const section_64 § = sections[i]; sv.visit_segment(sect.addr + slide, sect.size, sect.sectname); } } if ( (sv.velf & VISIT_SYMBOLS) != 0 ) { nlistvec_t symbols; qstring strings; mfile.get_symbol_table_info(symbols, strings, in_mem); // msg("%a: loaded %ld symbols and %ld string bytes\n", start, symbols.size(), strings.size()); for ( size_t i=0; i < symbols.size(); i++ ) { const struct nlist_64 &nl = symbols[i]; if ( nl.n_un.n_strx > strings.size() ) continue; const char *name = &strings[nl.n_un.n_strx]; ea_t ea; int type = nl.n_type & N_TYPE; switch ( type ) { case N_UNDF: case N_PBUD: case N_ABS: break; case N_SECT: case N_INDR: ea = nl.n_value + slide; if ( name[0] != '\0' ) { if ( (nl.n_type & (N_EXT|N_PEXT)) == N_EXT ) // exported { sv.visit_symbol(ea, name); } else if ( type == N_SECT && nl.n_sect != NO_SECT ) // private symbols { sv.visit_symbol(ea, name); } } break; } } } return true; }