process.c

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

C
1,633
字号
/****************************************************************************
*
*                            Open Watcom Project
*
*    Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
*  ========================================================================
*
*    This file contains Original Code and/or Modifications of Original
*    Code as defined in and that are subject to the Sybase Open Watcom
*    Public License version 1.0 (the 'License'). You may not use this file
*    except in compliance with the License. BY USING THIS FILE YOU AGREE TO
*    ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
*    provided with the Original Code and Modifications, and is also
*    available at www.sybase.com/developer/opensource.
*
*    The Original Code and all software distributed under the License are
*    distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
*    EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
*    ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
*    MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
*    NON-INFRINGEMENT. Please see the License for the specific language
*    governing rights and limitations under the License.
*
*  ========================================================================
*
* Description:  OMF record processing - heart of the dump utility.
*
****************************************************************************/


#include <ctype.h>
#include <time.h>
#include <string.h>

#include "dmpobj.h"

enum {
    DBG_UNKNOWN,
    DBG_CODEVIEW,
    DBG_HLL
};

int  DbgStyle = DBG_CODEVIEW;

typedef unsigned short  DOSDATE_T;

enum {
    TIME_SEC_B  = 0,
    TIME_SEC_F  = 0x001f,
    TIME_MIN_B  = 5,
    TIME_MIN_F  = 0x07e0,
    TIME_HOUR_B = 11,
    TIME_HOUR_F = 0xf800
};

enum {
    DATE_DAY_B  = 0,
    DATE_DAY_F  = 0x001f,
    DATE_MON_B  = 5,
    DATE_MON_F  = 0x01e0,
    DATE_YEAR_B = 9,
    DATE_YEAR_F = 0xfe00
};

static time_t d2t( DOSDATE_T date, DOSDATE_T time )
/*************************************************/
{
    struct tm tmbuf;

    tmbuf.tm_year = ( ( date & DATE_YEAR_F ) >> DATE_YEAR_B ) + 80;
    tmbuf.tm_mon  = ( ( date & DATE_MON_F ) >> DATE_MON_B ) - 1;
    tmbuf.tm_mday = ( date & DATE_DAY_F ) >> DATE_DAY_B;

    tmbuf.tm_hour = ( time & TIME_HOUR_F ) >> TIME_HOUR_B;
    tmbuf.tm_min  = ( time & TIME_MIN_F ) >> TIME_MIN_B;
    tmbuf.tm_sec  = ( ( time & TIME_SEC_F ) >> TIME_SEC_B ) * 2;

    tmbuf.tm_isdst= -1;

    return( mktime( &tmbuf ) );
}

void ProcEndRec( void )
/*********************/
{
    byte    typ;

    typ = GetByte();
    switch( typ & 0x3 ) {
    case 0: Output( INDENT "end of overlay" CRLF );     break;
    case 1: Output( INDENT "end of block" CRLF );       break;
    default:
        Output( BAILOUT "Unknown ENDREC type (%b)" CRLF, typ );
        longjmp( BailOutJmp, 1 );
    }
}

void ProcTHeadr( void )
/*********************/
{
    Segindex    = 0;
    Nameindex   = 0;
    Importindex = 0;
    Libindex    = 0;
    GetName();
    Output( INDENT "%N" CRLF );
}

void ProcLHeadr( void )
/*********************/
{
    GetName();
    Output( INDENT "%N" CRLF );
}

void ProcRHeadr( void )
/*********************/
{
    GetName();
    Output( INDENT "%N" CRLF );
    OutputData( (unsigned_32)RecOffset(), 0L );
}

static void doProcModel( void )
{
    byte        tmp;

    if( EndRec() ) return;
    Output( INDENT "Processor     : 80" );
    tmp = GetByte();
    if( tmp != '0' ) {
        Output( "%c", tmp );
    }
    Output( "86" CRLF );
    if( EndRec() ) return;
    Output( INDENT "Memory Model  : " );
    tmp = GetByte();
    switch( tolower( tmp ) ) {
    case 's':   Output( "Small" CRLF );     break;
    case 'm':   Output( "Medium" CRLF );    break;
    case 'c':   Output( "Compact" CRLF );   break;
    case 'l':   Output( "Large" CRLF );     break;
    case 'h':   Output( "Huge" CRLF );      break;
    case 'f':   Output( "Flat" CRLF );      break;
    default:
        Output( "Unknown(%c)" CRLF, tmp );
        break;
    }
    if( EndRec() ) return;
    tmp = GetByte();
    Output( INDENT "Optimized     : %s" CRLF, ( tmp == 'O' ) ? "Yes" : "No" );
    if( EndRec() ) return;
    Output( INDENT "Floating point: " );
    tmp = GetByte();
    switch( tmp ) {
    case 'e':   Output( "Emulated inline" CRLF );   break;
    case 'c':   Output( "Emulator calls" CRLF );    break;
    case 'p':   Output( "80x87 inline code" CRLF ); break;
    default:
        Output( "Unknown(%c)" CRLF, tmp );
        break;
    }
}

static void doWeakLazyExtern( void )
{
    byte default_resolution;
    byte extern_idx;

    for(;;) {
        if( EndRec() ) break;
        extern_idx = GetIndex();
        default_resolution = GetIndex();
         Output( INDENT INDENT "EI(%u) default: EI(%u)\n", extern_idx, default_resolution );
        if( TranslateIndex ) {
            Output( INDENT INDENT "  - '%s'   -'%s'\n", GetXname( extern_idx ),
                    GetXname( default_resolution ) );
        }
    }
}

static void doDependency( void )
{
    byte        len;
    DOSDATE_T   dos_date;
    DOSDATE_T   dos_time;
    time_t      t;
    char        *p;
    auto char buff[80];

    if( EndRec() ) {
        Output( INDENT "Last Dependency Record" CRLF );
        return;
    }
    dos_time = GetByte();
    dos_time |= GetByte() << 8;
    dos_date = GetByte();
    dos_date |= GetByte() << 8;
    Output( INDENT "File: " );
    buff[1] = '\0';
    for( len = GetByte(); len != 0; --len ) {
        buff[0] = GetByte();
        Output( buff );
    }
    Output( CRLF );
    t = d2t( dos_date, dos_time );
    p = ctime( &t );
    Output( INDENT "Time Stamp: " );
    Output( p );        // has embedded '\n'
}

static int doDisasmDirective( void )
{
    byte        ddir;
    unsigned_32 off1;
    unsigned_32 off2;
    unsigned_16 idx;
    unsigned_16 nidx;
    Segdeflist  *sd;

    ddir = GetByte();
    switch( ddir ) {
    case DDIR_SCAN_TABLE_32:
    case DDIR_SCAN_TABLE:
        idx = GetIndex();
        if( idx == 0 ) {
            /* scan table in a COMDAT */
            nidx = GetIndex();
        }
        if( ddir == DDIR_SCAN_TABLE ) {
            off1 = GetUInt();
            off2 = GetUInt();
        } else {
            off1 = GetLInt();
            off2 = GetLInt();
        }
        Output( INDENT "Scan Table: " );
        if( idx != 0 ) {
            Output( "SI(%u)", idx );
            if( TranslateIndex ) {
                sd = GetSegdef( idx );
                if( sd != NULL ) {
                    Output( " - '%s'", GetLname( sd->segind ) );
                }
            }
        } else {
            Output( "COMDAT(%u)", nidx );
        }
        Output( "  begin=%X  end+1=%X" CRLF, off1, off2 );
        return( 1 );
    }
    BackupByte();
    return( 0 );
}

static void doVirtualConditional( void )
{
    unsigned idx;
    unsigned def_idx;

    idx = GetIndex();
    def_idx = GetIndex();
    Output( INDENT "EI(%u) default: EI(%u)\n", idx, def_idx );
    if( TranslateIndex ) {
        Output( INDENT "  - '%s'   -'%s'\n", GetXname( idx ),
                GetXname( def_idx ) );
    }
    while( ! EndRec() ) {
        idx = GetIndex();
        Output( INDENT INDENT "conditional: LI(%u)\n", idx );
    }
}

static int doLinkerDirective( void )
{
    byte        ldir;
    byte        major;
    byte        minor;
    unsigned    e1;
    unsigned    s1;
    unsigned_32 stamp;
    Segdeflist  *sd;

    ldir = GetByte();
    switch( ldir ) {
    case LDIR_SOURCE_LANGUAGE:
        major = GetByte();
        minor = GetByte();
        Output( INDENT "WATCOM DBI: Version %u.%u  Language %R"
                CRLF, major, minor );
        return( 1 );
    case LDIR_DEFAULT_LIBRARY:
        major = GetByte();
        Output( INDENT "Default Library: Priority %u \"%R\"" CRLF,
            major );
        return( 1 );
    case LDIR_OPT_FAR_CALLS:
        s1 = GetIndex();
        if( TranslateIndex ) {
            sd = GetSegdef( s1 );
            Output( INDENT "Optimize Far Calls: SI(%u) - '%s'" CRLF,
                s1, GetLname( sd->segind ) );
        } else {
            Output( INDENT "Optimize Far Calls: SI(%u)" CRLF, s1 );
        }
        return( 1 );
    case LDIR_OPT_UNSAFE:
        Output( INDENT "Far Call Optimization Unsafe (Last FIXUPP)"
            CRLF );
        return( 1 );
    case LDIR_VF_TABLE_DEF:
        Output( INDENT "Virtual Function Conditional"
            CRLF );
        doVirtualConditional();
        return( 1 );
    case LDIR_VF_PURE_DEF:
        Output( INDENT "Pure Virtual Function Conditional"
            CRLF );
        doVirtualConditional();
        return( 1 );
    case LDIR_VF_REFERENCE:
        e1 = GetIndex();
        s1 = GetIndex();
        if( s1 == 0 ) {
            s1 = GetIndex();
            Output( INDENT "Virtual Function Reference EI(%u) CI(%u)"
                CRLF, e1, s1 );
        } else {
            Output( INDENT "Virtual Function Reference EI(%u) SI(%u)"
                CRLF, e1, s1 );
        }
        return( 1 );
    case LDIR_OBJ_TIMESTAMP:
        stamp = GetLInt();
        Output( INDENT "Library Timestamp: %s" CRLF,
            ctime( (time_t *)&stamp ) );
        return( 1 );
    }
    BackupByte();
    return( 0 );
}

static int doEasyOmf( byte c_bits )
{
    if( c_bits == 0x80 && memcmp( RecPtr, EASY_OMF_SIGNATURE, 5 ) == 0 ) {
        Output( INDENT "---- PharLap 80386 object deck ----" CRLF );
        IsPharLap = TRUE;
        IsIntel = FALSE;
        return( 1 );
    }
    return( 0 );
}

static int doMSOmf( void )
{
    if( RecLen < 5 ) {
        Output( INDENT "Assuming CodeView style debugging information" CRLF );
        DbgStyle = DBG_CODEVIEW;
    }
    else {
        byte    version;

        version = GetByte();
        IsIntel = FALSE;
        NamePtr = RecPtr;
        NameLen = RecLen - 3;
        RecPtr += NameLen;
        Output( INDENT "---- \"New OMF\" extensions present ----" CRLF );
        if( strncmp( NamePtr, "CV", 2 ) == 0 ) {
            Output( INDENT "Microsoft CodeView style debugging information version %b" CRLF, version );
            DbgStyle = DBG_CODEVIEW;
        } else if( strncmp( NamePtr, "HL", 2 ) == 0 ) {
            Output( INDENT "IBM HLL style debugging information version %b" CRLF, version );
            DbgStyle = DBG_HLL;
        }
        else {
            Output( INDENT "Unknown debugging information style" CRLF );
            DbgStyle = DBG_UNKNOWN;
        }
    }

    return( 1 );
}

static void doDLLImport( void )
{
    byte            ord_flag;
    unsigned_16     ordinal;

    ord_flag = GetByte();
    if( ord_flag ) {
        Output( INDENT "DLL Import by Ordinal" CRLF );
    } else {
        Output( INDENT "DLL Import by Name" CRLF );
    }
    GetName();
    Output( INDENT "%N." );
    GetName();
    Output( "%N ");
    if( ord_flag ) {
        ordinal = GetUInt();
        Output( "@%u", ordinal );
    } else {
        if( GetName() > 0)
            Output( "Imported Name: %N" CRLF );
    }
    Output( CRLF );
}

⌨️ 快捷键说明

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