wdtab.c

来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 611 行 · 第 1/2 页

C
611
字号

/*
 * allocate a new int_entry_pnt structure
 */
static struct int_entry_pnt *new_ent_pnt( void )
/**********************************************/
{
    struct int_entry_pnt    *new_ent;

    new_ent = Wmalloc( sizeof( struct int_entry_pnt ) );
    new_ent->next = Entry_pnts;
    Entry_pnts = new_ent;
    return( new_ent );
}

static void *dmp_fixed_seg_ent_pnts( unsigned_16 num_ent_pnts,
        void *ent_pnts, unsigned_16 ent_pnt_index, unsigned_16 seg_num )
/**********************************************************************/
{
    struct fixed_record             *fix_ent;
    struct int_entry_pnt            *new;

    fix_ent = ent_pnts;
    for( ; num_ent_pnts != 0; num_ent_pnts-- ) {
        new = new_ent_pnt();
        new->ordinal = ent_pnt_index++;
        new->seg_num = seg_num;
        new->offset = fix_ent->entry;
        new->ent_flag = fix_ent->info;
        ++fix_ent;
    }
    return( fix_ent );
}

static void *dmp_movable_seg_ent_pnts( unsigned_16 num_ent_pnts,
                        void *ent_pnts, unsigned_16 ent_pnt_index )
/*****************************************************************/
{
    struct movable_record           *mov_ent;
    struct int_entry_pnt            *new;

    mov_ent = ent_pnts;
    for( ; num_ent_pnts != 0; num_ent_pnts-- ) {
        new = new_ent_pnt();
        new->ordinal = ent_pnt_index++;
        new->ent_flag = mov_ent->info;
        new->seg_num = mov_ent->entrynum;
        new->offset = mov_ent->entry;
        ++mov_ent;
    }
    return( mov_ent );
}

/*
 * Parse the Entry Table
 */
static void prs_ent_tab( unsigned_32 ent_tab, unsigned_16 ent_tab_len )
/*********************************************************************/
{
    struct bundle_prefix    *ent_bund;
    struct bundle_prefix    *init_ent_bund;
    unsigned_16             ent_pnt_index;
    unsigned_16             num_ent_pnts;

    if( ent_tab_len == 0 ) {
        return;
    }
    Wlseek( ent_tab );
    ent_bund = Wmalloc( ent_tab_len );
    init_ent_bund = ent_bund;
    Wread( ent_bund, ent_tab_len );
    ent_pnt_index = 1;
    for( ; ent_bund->number != 0; ) {
        num_ent_pnts = ent_bund->number;
        switch( ent_bund->type ) {
        case 0:                   /* just incrementing entry table index */
            ++ent_bund;
            break;
        case MOVABLE_ENTRY_PNT:       /* movable segment                 */
            ent_bund = dmp_movable_seg_ent_pnts( num_ent_pnts,
                ++ent_bund, ent_pnt_index );
            break;
        default:                  /* fixed segment                       */
            ent_bund = dmp_fixed_seg_ent_pnts( num_ent_pnts,
                ++ent_bund, ent_pnt_index, ent_bund->type );
            break;
        }
        ent_pnt_index += num_ent_pnts;
    }
    free( init_ent_bund );
}

static void dmp_an_ord( struct int_entry_pnt *find )
/**************************************************/
{
    unsigned_16     flag;

    Wdputc( '.' );
    Putdec( find->ordinal );
    Wdputs( " seg " );
    Puthex( find->seg_num, 4 );
    Wdputs( " off " );
    Puthex( find->offset, 4 );
    Wdputs( " parm " );
    flag = find->ent_flag;
    Puthex( flag >> IOPL_WORD_SHIFT, 4 );
    if( flag & ENTRY_EXPORTED ) {
        Wdputs( " EXPORTED" );
    }
    if( flag & ENTRY_SHARED ) {
        Wdputs( "|SHAREDATA" );
    }
}

/*
 * dump an ordinal entry point
 */
void Dmp_ordinal( unsigned_16 ord )
/*********************************/
{
    struct int_entry_pnt    *find;

    for( find = Entry_pnts; find != NULL; find = find->next ) {
        if( find->ordinal == ord ) {
            dmp_an_ord( find );
            return;
        }
    }
    Wdputs( " unknown ordinal " );
    Puthex( ord, 4 );
}

/*
 * dump the entry point table
 */
static void dmp_entry_tab( void )
/*******************************/
{
    struct int_entry_pnt    *find;

    if( Entry_pnts == NULL ) {
        return;
    }
    Wdputslc( "\n" );
    Banner( "Entry Point Table" );
    for( find = Entry_pnts; find != NULL; find = find->next ) {
        dmp_an_ord( find );
        Wdputslc( "\n" );
    }
}

/*
 * Dump the tables
 */
void Dmp_ne_tbls( void )
/**********************/
{
    prs_ent_tab( New_exe_off + Os2_head.entry_off, Os2_head.entry_size );
    Banner( "Resident Names Table" );
    dmp_res_nonres_tab( New_exe_off + Os2_head.resident_off );
    dmp_mod_ref_tab( New_exe_off + Os2_head.module_off, Os2_head.modrefs );
    if( Os2_head.import_off != Os2_head.entry_off )
        dmp_import_tab( New_exe_off + Os2_head.import_off );
    dmp_entry_tab();
    Wdputslc( "\n" );
    Banner( "Nonresident Names Table" );
    dmp_res_nonres_tab( Os2_head.nonres_off );
    Dmp_relocs();
}

/*
 * Dump the tables
 */
void Dmp_le_lx_tbls( void )
/*************************/
{
    unsigned_32     size;

    Banner( "Resident Names Table" );
    dmp_res_nonres_tab( New_exe_off + Os2_386_head.resname_off );
    Dmp_fixpage_tab( New_exe_off + Os2_386_head.fixpage_off,
                    Os2_386_head.fixrec_off - Os2_386_head.fixpage_off );
    Dmp_fixrec_tab( New_exe_off + Os2_386_head.fixrec_off );
    size = Os2_386_head.impproc_off - Os2_386_head.impmod_off;
    if( size > 1 ) {
        Wdputslc( "\n" );
        Banner( "Import Module Name Table" );
        dmp_imp_tab( New_exe_off + Os2_386_head.impmod_off, size );
    }
    size = Os2_386_head.fixup_size + Os2_386_head.fixpage_off
                    - Os2_386_head.impproc_off;
    if( size > 1 ) {
        Wdputslc( "\n" );
        Banner( "Import Procedure Name Table" );
        dmp_imp_tab( New_exe_off + Os2_386_head.impproc_off, size );
    }
    dmp_ent_tab( New_exe_off + Os2_386_head.entry_off );
    Wdputslc( "\n" );
    Banner( "Nonresident Names Table" );
    dmp_res_nonres_tab( Os2_386_head.nonres_off );
}

static void dump_exports( void )
/******************************/
{
    unsigned_8      string_len;
    char            name[256];
    unsigned_16     ordinal;

    while( (string_len = read_res_nonres_nam( name, &ordinal )) != 0 ) {
        Wdputs( "    " );
        Wdputs( name );
        while( string_len++ < 43 ) {
            Wdputc( ' ' );
        }
        Wdputs( " @" );
        Putdec( ordinal );
        Wdputslc( "\n" );
    }
}

/*
 * Dump the NE/LE/LX exports table
 */
bool Dmp_os2_exports( void )
/**************************/
{
    unsigned_32     res_nam_tab;
    char            name[256];
    unsigned_16     ordinal;

    /* Check executable format; handle stubless modules */
    Wread( &Dos_head, sizeof( Dos_head ) );
    if( Dos_head.signature == DOS_SIGNATURE ) {
        if( Dos_head.reloc_offset != OS2_EXE_HEADER_FOLLOWS ) {
            return( 0 );
        }
        Wlseek( OS2_NE_OFFSET );
        Wread( &New_exe_off, sizeof( New_exe_off ) );
    } else if( Dos_head.signature == OSF_FLAT_LX_SIGNATURE
      || Dos_head.signature == OSF_FLAT_SIGNATURE
      || Dos_head.signature == OS2_SIGNATURE_WORD ) {
        New_exe_off = 0;
    }

    /* Read appropriate header */
    Wlseek( New_exe_off );
    Wread( &Os2_386_head, sizeof( Os2_386_head ) );
    if( Os2_386_head.signature == OS2_SIGNATURE_WORD ) {
        Form = FORM_NE;
        Wlseek( New_exe_off );
        Wread( &Os2_head, sizeof( Os2_head ) );
    } else {
        if( Os2_386_head.signature == OSF_FLAT_SIGNATURE ) {
            Form = FORM_LE;
        } else if( Os2_386_head.signature == OSF_FLAT_LX_SIGNATURE ) {
            Form = FORM_LX;
        } else {
            return( 0 );
        }
    }

    if( Form == FORM_NE ) {
        res_nam_tab = New_exe_off + Os2_head.resident_off;
    } else {
        res_nam_tab = New_exe_off + Os2_386_head.resname_off;
    }
    if( res_nam_tab == 0 ) return( 0 );

    /* Read and print module name */
    Wlseek( res_nam_tab );
    if( read_res_nonres_nam( name, &ordinal ) == 0 ) {
        return( 0 );
    }
    Wdputs( "LIBRARY " );
    Wdputs( name );
    Wdputslc( "\n" );
    Wdputslc( "EXPORTS\n" );

    /* Print exports in resident table */
    dump_exports();

    /* Seek to non-resident table */
    if( Form == FORM_NE ) {
        res_nam_tab = Os2_head.nonres_off;
    } else {
        res_nam_tab = Os2_386_head.nonres_off;
    }
    if( res_nam_tab == 0 ) return( 1 );
    Wlseek( res_nam_tab );

    /* See if there is comment */
    if( read_res_nonres_nam( name, &ordinal ) == 0 ) {
        return( 1 );
    }
    if( ordinal != 0 ) {
        Wlseek( res_nam_tab );  /* No comment, seek back */
    }

    /* Print exports in non-resident table */
    dump_exports();

    return( 1 );
}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?