/* * Dump the Nlm Executable Header, if any. */ bool Dmp_nlm_head( void ) /***********************/ { unsigned_32 offset; nlm_header_3 nlm_head3; nlm_header_4 nlm_head4; bool extend; char nlm_name[256]; Wlseek( 0 ); Wread( &Nlm_head, sizeof( Nlm_head.signature ) ); if( memcmp( Nlm_head.signature, NLM_SIGNATURE, sizeof( NLM_SIGNATURE ) - 1 ) ) { return( false ); } Wread( (char *)&Nlm_head + sizeof( Nlm_head.signature ), sizeof( nlm_header ) - sizeof( Nlm_head.signature ) ); Banner( "Novell EXE Header" ); Wdputs( "version number = " ); Puthex( Nlm_head.version, 8 ); Wdputslc( "H\n" ); Wdputs( "module name = " ); memcpy( nlm_name, &Nlm_head.moduleName[1], Nlm_head.moduleName[0] ); nlm_name[ (int)Nlm_head.moduleName[0] ] = '\0'; Wdputs( nlm_name ); Wdputslc( "\n" ); Dump_header( (char *)&Nlm_head.codeImageOffset, nlm_exe_msg ); offset = dmp_nlm_head2(); offset += sizeof( nlm_header ); Wlseek( offset ); Wread( &nlm_head3, sizeof( nlm_header_3 ) ); if( !memcmp( nlm_head3.versionSignature, VERSION_SIGNATURE, VERSION_SIGNATURE_LENGTH ) ) { Dump_header( (char *)&nlm_head3.majorVersion, nlm_date_msg ); offset += sizeof( nlm_header_3 ); } Wlseek( offset ); Wread( &nlm_head4, sizeof( nlm_header_4 ) ); if( !memcmp( nlm_head4.copyrightSignature, COPYRIGHT_SIGNATURE, COPYRIGHT_SIGNATURE_LENGTH ) ) { Wdputs( "copy right string = " ); Wdputs( nlm_head4.copyrightString ); Wdputslc( "\n" ); offset += sizeof( unsigned_8 ) + COPYRIGHT_SIGNATURE_LENGTH; offset += nlm_head4.copyrightLength; } Wlseek( offset ); extend = false; Wread( &Nlm_ext_head, sizeof( extended_nlm_header ) ); if( !memcmp( Nlm_ext_head.stamp, EXTENDED_NLM_SIGNATURE, EXTENDED_NLM_SIGNATURE_LENGTH ) ) { Dump_header( (char *)&Nlm_ext_head.languageID, nlm_ext_msg ); extend = true; } if( Nlm_head.customDataSize != 0 ) { Wdputslc( "\n" ); Banner( "Custom Data" ); Dmp_seg_data( Nlm_head.customDataOffset, Nlm_head.customDataSize ); } dmp_module_dep(); if( Options_dmp & FIX_DMP ) { dmp_reloc_fixup(); } dmp_external_ref(); dmp_public_entry(); Wdputslc( "\n" ); if( extend ) { dmp_extended(); } return( true ); }
/* * dump_locals - dump all local variable information */ static void dump_locals( mod_info *mi ) /*************************************/ { int i; unsigned_32 *offs; int cnt; unsigned_32 coff; unsigned_8 buff[256]; char name[256]; set_base *sb; set_base386 *sb386; unsigned_8 *ptr; addr32_ptr *p32; addr48_ptr *p48; unsigned_16 index; cnt = mi->di[DMND_LOCALS].u.entries; if( cnt == 0 ) { return; } Wdputslc( "\n" ); Wdputslc( " *** Locals ***\n" ); Wdputslc( " ==============\n" ); offs = alloca( (cnt+1) * sizeof( unsigned_32 ) ); if( offs == NULL ) { Wdputslc( "Error! Not enough stack.\n" ); longjmp( Se_env, 1 ); } Wlseek( Curr_sectoff + mi->di[DMND_LOCALS].info_off ); Wread( offs, (cnt+1) * sizeof( unsigned_32 ) ); for( i = 0; i < cnt; i++ ) { coff = 0; Wdputs( " Data " ); Putdec( i ); Wdputs( ": offset " ); Puthex( offs[i], 8 ); Wdputslc( "\n" ); for( ;; ) { Wlseek( coff + Curr_sectoff + offs[i] ); Wread( buff, sizeof( buff ) ); Wdputs( " " ); Puthex( coff, 4 ); Wdputs( ": " ); switch( buff[1] ) { case MODULE: Wdputslc( "MODULE\n" ); ptr = buff+2; p32 = (addr32_ptr *)ptr; ptr += sizeof( addr32_ptr ); ptr = Get_type_index( ptr, &index ); Get_local_name( name, ptr, buff ); Wdputs( " \"" ); Wdputs( name ); Wdputs( "\" addr = " ); Puthex( p32->segment, 4 ); Wdputc( ':' ); Puthex( p32->offset, 4 ); Wdputs( ", type = " ); Putdec( index ); Wdputslc( "\n" ); break; case LOCAL: Wdputslc( "LOCAL\n" ); ptr = buff+2; Wdputs( " address: " ); ptr = Dump_location_expression( ptr, " " ); ptr = Get_type_index( ptr, &index ); Get_local_name( name, ptr, buff ); Wdputs( " name = \"" ); Wdputs( name ); Wdputs( "\", type = " ); Putdec( index ); Wdputslc( "\n" ); break; case MODULE_386: Wdputslc( "MODULE_386\n" ); ptr = buff+2; p48 = (addr48_ptr *)ptr; ptr += sizeof( addr48_ptr ); ptr = Get_type_index( ptr, &index ); Get_local_name( name, ptr, buff ); Wdputs( " \"" ); Wdputs( name ); Wdputs( "\" addr = " ); Puthex( p48->segment, 4 ); Wdputc( ':' ); Puthex( p48->offset, 8 ); Wdputs( ", type = " ); Putdec( index ); Wdputslc( "\n" ); break; case MODULE_LOC: Wdputslc( "MODULE_LOC\n" ); ptr = buff+2; Wdputs( " address: " ); ptr = Dump_location_expression( ptr, " " ); ptr = Get_type_index( ptr, &index ); Get_local_name( name, ptr, buff ); Wdputs( " name = \"" ); Wdputs( name ); Wdputs( "\", type = " ); Putdec( index ); Wdputslc( "\n" ); break; case BLOCK: Wdputslc( "BLOCK\n" ); dump_block( buff, FALSE ); break; case NEAR_RTN: Wdputslc( "NEAR_RTN\n" ); dump_rtn( buff ); break; case FAR_RTN: Wdputslc( "FAR_RTN\n" ); dump_rtn( buff ); break; case BLOCK_386: Wdputslc( "BLOCK_386\n" ); dump_block( buff, TRUE ); break; case NEAR_RTN_386: Wdputslc( "NEAR_RTN_386\n" ); dump_rtn386( buff ); break; case FAR_RTN_386: Wdputslc( "FAR_RTN_386\n" ); dump_rtn386( buff ); break; case MEMBER_SCOPE: Wdputslc( "MEMBER_SCOPE\n" ); index = 5; ptr = buff+2; Wdputs( " parent offset = " ); Puthex( *ptr, 4 ); ptr += 2; if( *ptr & 0x80 ) { index = 6; } Wdputs( " class type = " ); ptr = Get_type_index( ptr, &index ); Putdec( index ); if( buff[0] > index ) { Wdputslc( "\n object ptr type = " ); Puthex( *ptr++, 2 ); Wdputs( " object loc = " ); Dump_location_expression( ptr, " " ); } Wdputslc( "\n" ); break; case ADD_PREV_SEG: Wdputslc( "ADD_PREV_SEG\n" ); Wdputs( " segment increment = " ); Puthex( *(buff+2), 4 ); Wdputslc( "\n" ); break; case SET_BASE: Wdputslc( "SET_BASE\n" ); sb = (set_base *) buff; Wdputs( " base = " ); Puthex( sb->seg, 4 ); Wdputc( ':' ); Puthex( sb->off, 4 ); Wdputslc( "\n" ); break; case SET_BASE_386: Wdputslc( "SET_BASE_386\n" ); sb386 = (set_base386 *) buff; Wdputs( " base = " ); Puthex( sb386->seg, 4 ); Wdputc( ':' ); Puthex( sb386->off, 8 ); Wdputslc( "\n" ); break; } coff += buff[0]; if( coff >= (offs[i+1] - offs[i]) ) { break; } } } } /* dump_locals */
static void dmp_symtab( unsigned long offset, unsigned long num_syms ) /********************************************************************/ { coff_symbol *symtab; coff_symbol *start; char * strtab; unsigned_32 strsize; unsigned_32 symidx; unsigned num_aux; char * name; char buff[9]; if( num_syms == 0 ) { Wdputslc( "No symbols in object file\n" ); Wdputslc( "\n" ); return; } Wlseek( Coff_off + offset ); Banner( "Symbol Table" ); start = Wmalloc( num_syms * sizeof(coff_symbol) ); symtab = start; Wread( start, num_syms * sizeof(coff_symbol) ); Wread( &strsize, sizeof(unsigned_32) ); if( strsize != 0 ) { strsize -= sizeof(unsigned_32); } if( strsize != 0 ) { strtab = Wmalloc( strsize ); Wread( strtab, strsize ); } else { strtab = NULL; } buff[8] = '\0'; for( symidx = 0; symidx < num_syms; symidx++ ) { if( symtab->name.non_name.zeros == 0 ) { name = strtab + symtab->name.non_name.offset - 4; } else if( symtab->name.name_string[8] == '\0' ) { name = symtab->name.name_string; } else { memcpy( buff, symtab->name.name_string, 8 ); name = buff; } Wdputs( "Idx: " ); Puthex( symidx, 8 ); Wdputs( " Name: " ); Wdputs( name ); Wdputslc( "\n" ); Wdputs( "Value: " ); Puthex( symtab->value, 8 ); Wdputs( " Sec #: " ); Puthex( symtab->sec_num, 4 ); Wdputs( " Type: " ); Puthex( symtab->type, 4 ); Wdputs( " Class: " ); Puthex( symtab->storage_class, 2 ); Wdputs( " # Aux Syms: " ); Putdec( symtab->num_aux ); Wdputslc( "\n" ); num_aux = symtab->num_aux; symtab++; if( num_aux > 0 ) { dmp_mult_data_line((char *)symtab, 0, num_aux * sizeof(coff_symbol)); symtab += num_aux; symidx += num_aux; } Wdputslc( "\n" ); } Wdputslc( "\n" ); if( strsize != 0 ) { Banner( "String Table" ); dmp_mult_data_line( strtab, 0, strsize ); Wdputslc( "\n" ); } free( start ); free( strtab ); }
/* * Dump the program and section headers. */ static void dmp_prog_sec( unsigned_32 start ) /*******************************************/ { Elf32_Phdr elf_prog; Elf32_Shdr elf_sec; unsigned_32 offset; char *string_table; int i; // grab the string table, if it exists if( Options_dmp & DEBUG_INFO ) { set_dwarf( start ); } if( Elf_head.e_shstrndx ) { offset = Elf_head.e_shoff + Elf_head.e_shstrndx * Elf_head.e_shentsize+start; Wlseek( offset ); Wread( &elf_sec, sizeof( Elf32_Shdr ) ); swap_shdr( &elf_sec ); string_table = Wmalloc( elf_sec.sh_size ); Wlseek( elf_sec.sh_offset + start ); Wread( string_table, elf_sec.sh_size ); } else { string_table = NULL; } if( Elf_head.e_phnum ) { Banner( "ELF Program Header" ); offset = Elf_head.e_phoff + start; for( i = 0; i < Elf_head.e_phnum; i++ ) { Wdputs( " Program Header #" ); Putdec( i + 1 ); Wdputslc( "\n" ); if( start != 0 ) { Wdputs("File Offset:"); Puthex( offset, 8 ); Wdputslc( "\n"); } Wlseek( offset ); Wread( &elf_prog, sizeof( Elf32_Phdr ) ); swap_phdr( &elf_prog ); // elf_prog.p_offset += start; //Relocate file pos offset += sizeof( Elf32_Phdr ); Data_count++; dmp_prog_type( elf_prog.p_type ); Dump_header( &elf_prog, elf_prog_msg ); dmp_prog_flgs( elf_prog.p_flags ); if( Options_dmp & (DOS_SEG_DMP | OS2_SEG_DMP) ) { if( Segspec == 0 || Segspec == Data_count ) { Dmp_seg_data( elf_prog.p_offset + start, elf_prog.p_filesz ); } } else if( elf_prog.p_type == PT_NOTE ) { dmp_sec_note( elf_prog.p_offset + start, elf_prog.p_filesz ); } Wdputslc( "\n" ); } } if( Elf_head.e_shnum ) { Banner( "ELF Section Header" ); offset = Elf_head.e_shoff+start; for( i = 0; i < Elf_head.e_shnum; i++ ) { Wlseek( offset ); Wread( &elf_sec, sizeof( Elf32_Shdr ) ); swap_shdr( &elf_sec ); // elf_sec.sh_offset += start; // relocate file pos Wdputs( " Section Header #" ); Putdec( i ); if( string_table != NULL ) { Wdputs( " \"" ); Wdputs( &(string_table[elf_sec.sh_name]) ); Wdputs( "\"" ); } Wdputslc( "\n" ); if( start != 0 ) { Wdputs( "File Offset:" ); Puthex( offset, 8 ); Wdputslc( "\n" ); } dmp_sec_type( elf_sec.sh_type ); Dump_header( &elf_sec.sh_name, elf_sec_msg ); dmp_sec_flgs( elf_sec.sh_flags ); if( Options_dmp & FIX_DMP ) { if( elf_sec.sh_type==SHT_REL || elf_sec.sh_type==SHT_RELA ) { Elf32_Shdr rel_sec; Elf32_Rela elf_rela; int loc, ctr, rel_size; Wdputs( "relocation information for section #" ); Putdec( elf_sec.sh_info ); Wlseek( Elf_head.e_shoff + start + Elf_head.e_shentsize * elf_sec.sh_info ); Wread( &rel_sec, sizeof( Elf32_Shdr ) ); swap_shdr( &rel_sec ); if( string_table != NULL ) { Wdputs( " \"" ); Wdputs( &string_table[rel_sec.sh_name] ); Wdputs( "\"" ); } else { Wdputs( " no_name (no associated string table)" ); } Wdputslc( ":\n" ); Wdputs( "symbol index refers to section #" ); Putdec( elf_sec.sh_link ); Wdputslc( "\n" ); Wdputslc( "Offset Sym Idx Addend Type Offset Sym Idx Addend Type\n" ); rel_size = (elf_sec.sh_type == SHT_REL ? sizeof( Elf32_Rel ) : sizeof( Elf32_Rela )); for( loc = 0, ctr = 0; loc < elf_sec.sh_size; loc += rel_size, ctr++ ) { Wlseek( elf_sec.sh_offset + start + loc ); Wread( &elf_rela, rel_size ); Puthex( elf_rela.r_offset, 8 ); Wdputc( ' ' ); Puthex( ELF32_R_SYM( elf_rela.r_info ), 8 ); Wdputc( ' ' ); if( elf_sec.sh_type == SHT_RELA ) { Puthex( elf_rela.r_addend, 8 ); } else { Wdputs( "n/a " ); } Wdputc( ' ' ); Puthex( ELF32_R_TYPE( elf_rela.r_info ), 2 ); if( ctr % 2 == 1 ) { Wdputslc( "\n" ); } else { Wdputs( " " ); } } if( ctr % 2 != 0 ) { Wdputslc( "\n" ); } } } if( Options_dmp & DEBUG_INFO ) { Wdputslc( "\n" ); if( string_table != NULL ) { dmp_sec_data( &(string_table[elf_sec.sh_name]), elf_sec.sh_type, elf_sec.sh_offset+start, elf_sec.sh_size ); } else { dmp_sec_data( NULL, elf_sec.sh_type, elf_sec.sh_offset+start, elf_sec.sh_size ); } } else if( Options_dmp & OS2_SEG_DMP ) { if( elf_sec.sh_size && elf_sec.sh_type != SHT_NOBITS ) { Wdputslc( "Section dump:\n" ); Dmp_seg_data( elf_sec.sh_offset + start, elf_sec.sh_size ); } } Wdputslc( "\n" ); offset += Elf_head.e_shentsize; } } if( string_table != NULL ) { free( string_table ); } }
/* * dump_hll_sstHLLSrc - dump HLL sstHLLSrc at 'offset' from 'base' * containing 'size' bytes */ static void dump_hll_sstHLLSrc( unsigned_32 base, unsigned_32 offset, unsigned_32 size ) /*******************************************************************/ { Wlseek( base + offset ); Wdputs( "==== sstHLLSrc at offset " ); Puthex( offset, 8 ); Wdputslc( "\n" ); #if 0/* FIXME: structure changes broke this. */ if( hll_level >= 0x04 ) { hl4_linnum_first_lines first_entry; unsigned_32 count = 0; while( count < size ) { Wread( &first_entry, sizeof( first_entry ) ); Dump_header( &first_entry, hl4_linnum_first_msg ); count += sizeof( first_entry ); if( first_entry.core.entry_type == 0x03 ) { hl4_filetab_entry ftab_entry; unsigned_32 index; Wread( &ftab_entry, sizeof( ftab_entry ) ); Dump_header( &ftab_entry, hl4_filetab_entry_msg ); count += sizeof( ftab_entry ); for( index = 0; index < ftab_entry.numFiles; ++index ) { Wdputs( " file index: " ); Puthex( index, 4 ); Wdputs( "H name: \"" ); count += dump_name( 0 ); Wdputslc( "\"\n" ); } Wdputslc( "\n" ); } else if( first_entry.core.entry_type == 0x00 ) { hl3_linnum_entry lnum_entry; unsigned_32 index; for( index = 0; index < first_entry.num_line_entries; ++index ) { Wread( &lnum_entry, sizeof( lnum_entry ) ); count += sizeof( lnum_entry ); Dump_header( &lnum_entry, hll_linnum_entry_msg ); } Wdputslc( "\n" ); } else { Wdputslc( "unsupported linnum table entry format\n" ); } } } else { hl2_linnum_first first_entry; unsigned_32 index; Wread( &first_entry, sizeof( first_entry ) ); Dump_header( &first_entry, hl3_linnum_first_msg ); if( first_entry.entry_type == 0x00 ) { hl3_filetab_entry ftab_entry; hl3_linnum_entry lnum_entry; for( index = 0; index < first_entry.num_entries; ++index ) { Wread( &lnum_entry, sizeof( lnum_entry ) ); Dump_header( &lnum_entry, hll_linnum_entry_msg ); } Wread( &ftab_entry, sizeof( ftab_entry ) ); Dump_header( &ftab_entry, hl3_filetab_entry_msg ); for( index = 0; index < ftab_entry.numFiles; ++index ) { Wdputs( " file index: " ); Puthex( index, 4 ); Wdputs( "H name: \"" ); dump_name( 0 ); Wdputslc( "\"\n" ); } Wdputslc( "\n" ); } else { Wdputslc( "unsupported linnum table entry format\n" ); } } #endif }
/* * dump_cv_sstSymbols - dump CV sstSymbols at 'offset' * from 'base 'containing 'size' bytes */ static void dump_cv_sstSymbols( unsigned_32 base, unsigned_32 offset, unsigned_32 size ) /*******************************************************************/ { union ssr_data { char buf[300]; cv3_ssr_all ssr; } u; unsigned_32 read = 0; Wlseek( base + offset ); Wdputs( "==== sstSymbols at offset " ); Puthex( offset, 8 ); Wdputslc( "\n" ); Wdputslc( "len/code/desc\n" ); while( read < size ) { Wread( &u.ssr, sizeof( cv3_ssr_common ) ); Wdputs( " " ); Puthex( u.ssr.common.length, 2 ); Wdputs( "/" ); Puthex( u.ssr.common.code, 2 ); Wdputs( "/" ); /* back up so we can read the common part again */ Wlseek( base + offset + read ); read += u.ssr.common.length + 1; switch( u.ssr.common.code ) { case HLL_SSR_BEGIN: Wread( &u.ssr, sizeof( cv3_ssr_begin ) ); Wdputs( "BEGIN: offset=" ); Puthex( u.ssr.begin.offset, 4 ); Wdputs( " length=" ); Puthex( u.ssr.begin.len, 4 ); Wdputslc( "\n" ); break; case HLL_SSR_PROC: Wread( &u.ssr, sizeof( cv3_ssr_proc ) ); Wread( u.ssr.proc.name, u.ssr.proc.name_len ); u.ssr.proc.name[u.ssr.proc.name_len] = '\0'; Wdputs( "PROC: ofs=" ); Puthex( u.ssr.proc.offset, 4 ); Wdputs( " type=" ); Puthex( u.ssr.proc.type, 4 ); Wdputs( " len=" ); Puthex( u.ssr.proc.len, 4 ); Wdputs( " pro=" ); Puthex( u.ssr.proc.prologue_len, 4 ); Wdputs( " epi=" ); Puthex( u.ssr.proc.prologue_body_len, 4 ); Wdputs( " flg=" ); Puthex( u.ssr.proc.flags, 2 ); Wdputslc( "\n" ); Wdputs( " name: \"" ); Wdputs( u.ssr.proc.name ); Wdputslc( "\"\n" ); break; case HLL_SSR_END: Wread( &u.ssr, sizeof( cv3_ssr_end ) ); Wdputslc( "ENDBLK:\n" ); break; case HLL_SSR_AUTO: Wread( &u.ssr, sizeof( cv3_ssr_auto ) ); Wread( u.ssr.auto_.name, u.ssr.auto_.name_len ); u.ssr.auto_.name[u.ssr.auto_.name_len] = '\0'; Wdputs( "AUTO: offset=" ); Puthex( u.ssr.auto_.offset, 4 ); Wdputs( " type=" ); Puthex( u.ssr.auto_.type, 4 ); Wdputslc( "\n" ); Wdputs( " name: \"" ); Wdputs( u.ssr.auto_.name ); Wdputslc( "\"\n" ); break; case HLL_SSR_STATIC: Wread( &u.ssr, sizeof( cv3_ssr_static ) ); Wread( u.ssr.static_.name, u.ssr.static_.name_len ); u.ssr.static_.name[u.ssr.static_.name_len] = '\0'; Wdputs( "STATIC: offset=" ); Puthex( u.ssr.static_.offset, 4 ); Wdputs( " segment=" ); Puthex( u.ssr.static_.seg, 4 ); Wdputs( " type=" ); Puthex( u.ssr.static_.type, 4 ); Wdputslc( "\n" ); Wdputs( " name: \"" ); Wdputs( u.ssr.static_.name ); Wdputslc( "\"\n" ); break; case HLL_SSR_REG: Wread( &u.ssr, sizeof( cv3_ssr_reg ) ); Wread( u.ssr.reg.name, u.ssr.reg.name_len ); u.ssr.reg.name[u.ssr.reg.name_len] = '\0'; Wdputs( "REGISTER: type=" ); Puthex( u.ssr.reg.type, 4 ); Wdputs( " no=" ); Puthex( u.ssr.reg.reg, 2 ); Wdputslc( "\n" ); Wdputs( " name: \"" ); Wdputs( u.ssr.reg.name ); Wdputslc( "\"\n" ); break; case HLL_SSR_CHANGE_SEG: Wread( &u.ssr, sizeof( cv3_ssr_change_seg ) ); Wdputs( "CHG_SEG: segment=" ); Puthex( u.ssr.change_seg.seg, 4 ); Wdputs( " reserved=" ); Puthex( u.ssr.change_seg.reserved, 4 ); Wdputslc( "\n" ); break; case HLL_SSR_TYPEDEF: Wread( &u.ssr, sizeof( cv3_ssr_typedef ) ); Wread( u.ssr.typedef_.name, u.ssr.typedef_.name_len ); u.ssr.typedef_.name[u.ssr.typedef_.name_len] = '\0'; Wread( &u.ssr, sizeof( cv3_ssr_typedef ) ); Wdputs( "TYPEDEF: type=" ); Puthex( u.ssr.typedef_.type, 4 ); Wdputslc( "\n" ); Wdputs( " name: \"" ); Wdputs( u.ssr.reg.name ); Wdputslc( "\"\n" ); break; default: Wdputs( " unknown symbol code " ); Puthex( u.ssr.common.code, 2 ); Wdputslc( "!\n" ); return; } } Wdputslc( "\n" ); }
/* * Dump_types - dump all typing information */ void Dmp_type( int cnt, unsigned_32 *offs ) /*****************************************/ { int i; addr32_ptr *p32; addr48_ptr *p48; unsigned_8 *ptr; unsigned_16 index; unsigned_16 curr_index; unsigned_32 coff; char name[256]; unsigned_8 buff[256]; for( i = 0; i < cnt; i++ ) { coff = 0; Wdputs( " Data " ); Putdec( i ); Wdputs( ": offset " ); Puthex( offs[i], 8 ); Wdputslc( "\n" ); curr_index = 0; for( ;; ) { Wlseek( coff + Curr_sectoff + offs[i] ); Wread( buff, sizeof( buff ) ); Wdputs( " " ); Puthex( coff, 4 ); Wdputs( ": " ); ptr = buff+2; switch( buff[1] ) { case SCALAR: StartType( "SCALAR", ++curr_index ); ptr = buff+3; Get_local_name( name, ptr, buff ); Wdputs( " \"" ); Wdputs( name ); Wdputs( "\" scalar type = " ); scalar_type( buff[2] ); Wdputslc( "\n" ); break; case SCOPE: StartType( "SCOPE", ++curr_index); Get_local_name( name, ptr, buff ); Wdputs( " \"" ); Wdputs( name ); Wdputslc( "\"\n" ); break; case NAME: StartType( "NAME", ++curr_index); ptr = Get_type_index( ptr, &index ); ptr = Get_type_index( ptr, &index ); Get_local_name( name, ptr, buff ); Wdputs( " \"" ); Wdputs( name ); Wdputs( "\" type idx = " ); Putdec( index ); Wdputs( " scope idx = " ); ptr = Get_type_index( buff+2, &index ); Putdec( index ); Wdputslc( "\n" ); break; case CUE_TABLE: Wdputs( "cue table offset=" ); Puthex( *(unsigned_32 *)ptr, 8 ); Wdputslc( "\n" ); break; case TYPE_EOF: return; case BYTE_INDEX: StartType( "BYTE_INDEX ARRAY", ++curr_index); array_index( ptr, 1 ); break; case WORD_INDEX: StartType( "WORD_INDEX ARRAY", ++curr_index); array_index( ptr, 2 ); break; case LONG_INDEX: StartType( "LONG_INDEX ARRAY", ++curr_index); array_index( ptr, 4 ); break; case TYPE_INDEX: StartType( "TYPE_INDEX ARRAY", ++curr_index); Wdputs( " index type = " ); ptr = Get_type_index( ptr, &index ); Putdec( index ); base_type_index( ptr ); break; case DESC_INDEX: StartType( "DESC_INDEX ARRAY", ++curr_index); desc_array( ptr, false ); break; case DESC_INDEX_386: StartType( "DESC_INDEX ARRAY", ++curr_index); desc_array( ptr, true ); break; case BYTE_RANGE: StartType( "BYTE_RANGE", ++curr_index); range( ptr, 1 ); break; case WORD_RANGE: StartType( "WORD_RANGE", ++curr_index); range( ptr, 2 ); break; case LONG_RANGE: StartType( "LONG_RANGE", ++curr_index); range( ptr, 4 ); break; case PTR_NEAR: StartType( "NEAR PTR", ++curr_index); Wdputs( " " ); near_ptr( buff ); break; case PTR_FAR: StartType( "FAR PTR", ++curr_index); Wdputs( " " ); base_type_index( ptr ); break; case PTR_HUGE: StartType( "HUGE PTR", ++curr_index); Wdputs( " " ); base_type_index( ptr ); break; case PTR_NEAR_DEREF: StartType( "NEAR_DEREF PTR", ++curr_index); Wdputs( " " ); near_ptr( buff ); break; case PTR_FAR_DEREF: StartType( "FAR_DEREF PTR", ++curr_index); Wdputs( " " ); base_type_index( ptr ); break; case PTR_HUGE_DEREF: StartType( "HUGE_DEREF PTR", ++curr_index); Wdputs( " " ); base_type_index( ptr ); break; case PTR_NEAR386: StartType( "NEAR386 PTR", ++curr_index); Wdputs( " " ); near_ptr( buff ); break; case PTR_FAR386: StartType( "FAR386 PTR", ++curr_index); Wdputs( " " ); base_type_index( ptr ); break; case PTR_NEAR386_DEREF: StartType( "NEAR386_DEREF PTR", ++curr_index); Wdputs( " " ); near_ptr( buff ); break; case PTR_FAR386_DEREF: StartType( "FAR386_DEREF PTR", ++curr_index); Wdputs( "\n " ); base_type_index( ptr ); break; case CLIST: StartType( "ENUM_LIST", ++curr_index); Wdputs( " number of consts = " ); Puthex( *ptr, 4 ); Wdputs( " scalar type = " ); scalar_type( buff[4] ); Wdputslc( "\n" ); break; case CONST_BYTE: Wdputslc( "CONST_BYTE\n" ); enum_const( buff, 1 ); break; case CONST_WORD: Wdputslc( "CONST_WORD\n" ); enum_const( buff, 2 ); break; case CONST_LONG: Wdputslc( "CONST_LONG\n" ); enum_const( buff, 4 ); break; case FLIST: StartType( "FIELD_LIST", ++curr_index); Wdputs( " number of fields = " ); Puthex( *ptr, 4 ); if( buff[0] > 4 ) { Wdputs( " size = " ); ptr += 2; Puthex( *ptr, 8 ); } Wdputslc( "\n" ); break; case FIELD_BYTE: Wdputslc( "FIELD_BYTE\n" ); bit_field_struct( buff, 1, false ); break; case FIELD_WORD: Wdputslc( "FIELD_WORD\n" ); bit_field_struct( buff, 2, false ); break; case FIELD_LONG: Wdputslc( "FIELD_LONG\n" ); bit_field_struct( buff, 4, false ); break; case BIT_BYTE: Wdputslc( "BIT_BYTE\n" ); bit_field_struct( buff, 1, true ); break; case BIT_WORD: Wdputslc( "BIT_WORD\n" ); bit_field_struct( buff, 2, true ); break; case BIT_LONG: Wdputslc( "BIT_LONG\n" ); bit_field_struct( buff, 4, true ); break; case FIELD_CLASS: Wdputslc( "FIELD_CLASS\n" ); bit_field_class( buff, false ); break; case BIT_CLASS: Wdputslc( "BIT_CLASS\n" ); bit_field_class( buff, true ); break; case INHERIT_CLASS: Wdputslc( "INHERIT_CLASS\n" ); Wdputs( " adjust locator = " ); ptr = Dump_location_expression( ptr, " " ); Wdputs( " ancestor type = " ); Get_type_index( ptr, &index ); Putdec( index ); Wdputslc( "\n" ); break; case PNEAR: StartType( "NEAR PROC", ++curr_index); near_far_proc( buff ); break; case PFAR: StartType( "FAR PROC", ++curr_index); near_far_proc( buff ); break; case PNEAR386: StartType( "NEAR386 PROC", ++curr_index); near_far_proc( buff ); break; case PFAR386: StartType( "FAR386 PROC", ++curr_index); near_far_proc( buff ); break; case EXT_PARMS: Wdputslc( "EXT_PARMS\n" ); param_type_index( (unsigned_8)buff[0]-2, ptr ); break; case CHAR_BYTE: StartType( "CHAR_BYTE", ++curr_index); Wdputs( " length = " ); Puthex( *ptr, 2 ); Wdputslc( "\n" ); break; case CHAR_WORD: StartType( "CHAR_WORD", ++curr_index); Wdputs( " length = " ); Puthex( *ptr, 4 ); Wdputslc( "\n" ); break; case CHAR_LONG: StartType( "CHAR_LONG", ++curr_index); Wdputs( " length = " ); Puthex( *ptr, 8 ); Wdputslc( "\n" ); break; case CHAR_IND: StartType( "CHAR_IND", ++curr_index); Wdputs( " scalar type = " ); scalar_type( buff[2] ); p32 = (addr32_ptr *)ptr; Puthex( p32->segment, 4 ); Wdputc( ':' ); Puthex( p32->offset, 4 ); Wdputslc( "\n" ); break; case CHAR_IND_386: StartType( "CHAR_IND_386", ++curr_index); Wdputs( " scalar type = " ); scalar_type( buff[2] ); p48 = (addr48_ptr *)ptr; Puthex( p48->segment, 4 ); Wdputc( ':' ); Puthex( p48->offset, 8 ); Wdputslc( "\n" ); break; case CHAR_LOCATION: StartType( "CHAR_LOC", ++curr_index); Wdputs( " scalar type = " ); scalar_type( buff[2] ); Wdputs( " size locator = " ); ptr = Dump_location_expression( ptr + 1, " " ); Wdputslc( "\n" ); break; } coff += buff[0]; if( coff >= (offs[i+1] - offs[i]) ) { break; } } } } /* Dmp_type */