static const bfd_target * os9k_object_p (bfd *abfd) { struct internal_exec anexec; mh_com exec_bytes; if (bfd_bread ((PTR) &exec_bytes, (bfd_size_type) MHCOM_BYTES_SIZE, abfd) != MHCOM_BYTES_SIZE) { if (bfd_get_error () != bfd_error_system_call) bfd_set_error (bfd_error_wrong_format); return 0; } anexec.a_info = H_GET_16 (abfd, exec_bytes.m_sync); if (N_BADMAG (anexec)) { bfd_set_error (bfd_error_wrong_format); return 0; } if (! os9k_swap_exec_header_in (abfd, &exec_bytes, &anexec)) { if (bfd_get_error () != bfd_error_system_call) bfd_set_error (bfd_error_wrong_format); return NULL; } return aout_32_some_aout_object_p (abfd, &anexec, os9k_callback); }
/* Swaps the information in an executable header taken from a raw byte stream memory image, into the internal exec_header structure. */ static bfd_boolean os9k_swap_exec_header_in (bfd *abfd, mh_com *raw_bytes, struct internal_exec *execp) { mh_com *bytes = (mh_com *) raw_bytes; unsigned int dload, dmemsize, dmemstart; /* Now fill in fields in the execp, from the bytes in the raw data. */ execp->a_info = H_GET_16 (abfd, bytes->m_sync); execp->a_syms = 0; execp->a_entry = H_GET_32 (abfd, bytes->m_exec); execp->a_talign = 2; execp->a_dalign = 2; execp->a_balign = 2; dload = H_GET_32 (abfd, bytes->m_idata); execp->a_data = dload + 8; if (bfd_seek (abfd, (file_ptr) dload, SEEK_SET) != 0 || (bfd_bread (&dmemstart, (bfd_size_type) sizeof (dmemstart), abfd) != sizeof (dmemstart)) || (bfd_bread (&dmemsize, (bfd_size_type) sizeof (dmemsize), abfd) != sizeof (dmemsize))) return FALSE; execp->a_tload = 0; execp->a_dload = H_GET_32 (abfd, (unsigned char *) &dmemstart); execp->a_text = dload - execp->a_tload; execp->a_data = H_GET_32 (abfd, (unsigned char *) &dmemsize); execp->a_bss = H_GET_32 (abfd, bytes->m_data) - execp->a_data; execp->a_trsize = 0; execp->a_drsize = 0; return TRUE; }
static bfd_boolean oasys_slurp_symbol_table (bfd *const abfd) { oasys_record_union_type record; oasys_data_type *data = OASYS_DATA (abfd); bfd_boolean loop = TRUE; asymbol *dest_defined; asymbol *dest; char *string_ptr; bfd_size_type amt; if (data->symbols != NULL) return TRUE; /* Buy enough memory for all the symbols and all the names. */ amt = abfd->symcount; amt *= sizeof (asymbol); data->symbols = bfd_alloc (abfd, amt); amt = data->symbol_string_length; #ifdef UNDERSCORE_HACK /* Buy 1 more char for each symbol to keep the underscore in. */ amt += abfd->symcount; #endif data->strings = bfd_alloc (abfd, amt); if (!data->symbols || !data->strings) return FALSE; dest_defined = data->symbols + abfd->symcount - 1; string_ptr = data->strings; if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0) return FALSE; while (loop) { if (! oasys_read_record (abfd, &record)) return FALSE; switch (record.header.type) { case oasys_record_is_header_enum: break; case oasys_record_is_local_enum: case oasys_record_is_symbol_enum: { int flag = record.header.type == (int) oasys_record_is_local_enum ? (BSF_LOCAL) : (BSF_GLOBAL | BSF_EXPORT); size_t length = oasys_string_length (&record); switch (record.symbol.relb & RELOCATION_TYPE_BITS) { case RELOCATION_TYPE_ABS: dest = dest_defined--; dest->section = bfd_abs_section_ptr; dest->flags = 0; break; case RELOCATION_TYPE_REL: dest = dest_defined--; dest->section = OASYS_DATA (abfd)->sections[record.symbol.relb & RELOCATION_SECT_BITS]; if (record.header.type == (int) oasys_record_is_local_enum) { dest->flags = BSF_LOCAL; if (dest->section == (asection *) (~0)) { /* It seems that sometimes internal symbols are tied up, but still get output, even though there is no section */ dest->section = 0; } } else dest->flags = flag; break; case RELOCATION_TYPE_UND: dest = data->symbols + H_GET_16 (abfd, record.symbol.refno); dest->section = bfd_und_section_ptr; break; case RELOCATION_TYPE_COM: dest = dest_defined--; dest->name = string_ptr; dest->the_bfd = abfd; dest->section = bfd_com_section_ptr; break; default: dest = dest_defined--; BFD_ASSERT (FALSE); break; } dest->name = string_ptr; dest->the_bfd = abfd; dest->udata.p = NULL; dest->value = H_GET_32 (abfd, record.symbol.value); #ifdef UNDERSCORE_HACK if (record.symbol.name[0] != '_') { string_ptr[0] = '_'; string_ptr++; } #endif memcpy (string_ptr, record.symbol.name, length); string_ptr[length] = 0; string_ptr += length + 1; } break; default: loop = FALSE; } } return TRUE; }