⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 pass2.c

📁 开放源码的编译器open watcom 1.6.0版的源代码
💻 C
📖 第 1 页 / 共 3 页
字号:

    error = AllocAndReadOS2SegTables( &err_code );
    if( error != RS_OK ) goto HANDLE_ERROR;
    if( StopInvoked ) goto STOP_ERROR;

    error = seekPastResTable( &err_code );
    if( error != RS_OK ) goto HANDLE_ERROR;
    if( StopInvoked ) goto STOP_ERROR;

    error = copyOtherTables( &err_code );
    if( error != RS_OK ) goto HANDLE_ERROR;
    if( StopInvoked ) goto STOP_ERROR;

    error = copyOS2Body();
    if( error ) return( FALSE );
    if( StopInvoked ) goto STOP_ERROR;

    error = copyDebugInfo();
    if( error != RS_OK ) {
        err_code = errno;
        goto HANDLE_ERROR;
    }
    if( StopInvoked ) goto STOP_ERROR;

    error = writeOS2HeadAndTables( &err_code );
    if( error != RS_OK ) goto HANDLE_ERROR;
    if( StopInvoked ) goto STOP_ERROR;
    return( TRUE );

HANDLE_ERROR:
    switch( error ) {
    case RS_READ_ERROR:
        RcError( ERR_READING_EXE, Pass2Info.OldFile.name,
                 strerror( err_code ) );
        break;
    case RS_READ_INCMPLT:
        RcError( ERR_UNEXPECTED_EOF, Pass2Info.OldFile.name );
        break;
    case RS_WRITE_ERROR:
        RcError( ERR_WRITTING_TMP, Pass2Info.TmpFile.name,
                 strerror( err_code ) );
        break;
    case RS_NO_MEM:
        break;
    default:
       RcError( ERR_INTERNAL, INTERR_UNKNOWN_RCSTATUS );
    }
    return( FALSE );

STOP_ERROR:
    RcFatalError( ERR_STOP_REQUESTED );
#if !defined( __WATCOMC__ )
    return( FALSE );
#endif
} /* MergeResExeOS2NE */


extern RcStatus updateDebugDirectory( void )
{
    ExeFileInfo         *tmp;
    ExeFileInfo         *old;
    pe_va               old_rva;
    pe_va               tmp_rva;
    unsigned_32         debug_size;
    unsigned_32         old_offset;
    unsigned_32         tmp_offset;
    long int            io_rc;
    unsigned            debug_cnt;
    unsigned            read_cnt;
    unsigned            read_size;
    unsigned            i;
    debug_directory     *entry;


    tmp = &Pass2Info.TmpFile;
    old = &Pass2Info.OldFile;

    debug_size = old->u.PEInfo.WinHead->table[PE_TBL_DEBUG].size;
    old_rva = old->u.PEInfo.WinHead->table[PE_TBL_DEBUG].rva;
    tmp_rva = tmp->u.PEInfo.WinHead->table[PE_TBL_DEBUG].rva;

    if( old_rva == 0 ) return( RS_OK );
    old_offset = OffsetFromRVA( old, old_rva );
    tmp_offset = OffsetFromRVA( tmp, tmp_rva );
    if( old_offset == 0xFFFFFFFF || tmp_offset == 0xFFFFFFFF ) {
        return( RS_BAD_FILE_FMT );
    }
    io_rc = RcSeek( tmp->Handle, tmp_offset, SEEK_SET );
    if( io_rc == -1 ) return( RS_WRITE_ERROR );
    io_rc = RcSeek( old->Handle, old_offset, SEEK_SET );
    if( io_rc == -1 ) return( RS_READ_ERROR );
    debug_cnt = debug_size /sizeof( debug_directory );
    while( debug_cnt > 0 ) {
        read_cnt = min( IO_BUFFER_SIZE / sizeof( debug_directory), debug_cnt );
        read_size = read_cnt * sizeof( debug_directory );
        io_rc = RcRead( old->Handle, Pass2Info.IoBuffer, read_size );
        if( io_rc == -1 ) return( RS_READ_ERROR );
        if( io_rc != read_size ) return( RS_READ_INCMPLT );
        entry = Pass2Info.IoBuffer;
        for( i=0; i < read_cnt; i++ ) {
            if( entry[i].data_seek >= old->DebugOffset ) {
                entry[i].data_seek += tmp->DebugOffset - old->DebugOffset;
            }
        }
        io_rc = RcWrite( tmp->Handle, Pass2Info.IoBuffer, read_size );
        if( io_rc != read_size ) return( RS_WRITE_ERROR );
        debug_cnt -= read_cnt;
    }
    return( RS_OK );
} /* updateDebugDirectory */


extern int MergeResExePE( void )
{
    RcStatus    error;
    int         err_code;

    error = copyStubFile( &err_code );
    if( error != RS_OK ) goto REPORT_ERROR;
    if( StopInvoked ) goto STOP_ERROR;

    error = CopyExeObjects();
    if( error ) goto HANDLE_ERROR;
    if( StopInvoked ) goto STOP_ERROR;

    error = RcBuildResourceObject();
    if( error ) goto HANDLE_ERROR;
    if( StopInvoked ) goto STOP_ERROR;

    error = copyDebugInfo();
    if( error != RS_OK ) {
        err_code = errno;
        goto REPORT_ERROR;
    }
    if( StopInvoked ) goto STOP_ERROR;

    error = writePEHeadAndObjTable();
    if( error != RS_OK ) {
        err_code = errno;
        goto REPORT_ERROR;
    }
    if( StopInvoked ) goto STOP_ERROR;

    error = updateDebugDirectory();
    if( error != RS_OK ) {
        err_code = errno;
        goto REPORT_ERROR;
    }
    if( StopInvoked ) goto STOP_ERROR;

    return( TRUE );

REPORT_ERROR:
    switch( error ) {
    case RS_READ_ERROR:
        RcError( ERR_READING_EXE, Pass2Info.OldFile.name,
                 strerror( err_code )  );
        break;
    case RS_READ_INCMPLT:
        RcError( ERR_UNEXPECTED_EOF, Pass2Info.OldFile.name );
        break;
    case RS_WRITE_ERROR:
        RcError( ERR_WRITTING_TMP, Pass2Info.TmpFile.name,
                 strerror( err_code ) );
        break;
    case RS_BAD_FILE_FMT:
        RcError( ERR_NOT_VALID_EXE, Pass2Info.OldFile.name );
        break;
    case RS_NO_MEM:
        break;
    default:
       RcError( ERR_INTERNAL, INTERR_UNKNOWN_RCSTATUS );
    }
   /* fall through */
HANDLE_ERROR:
    return( FALSE );

STOP_ERROR:
    RcFatalError( ERR_STOP_REQUESTED );
#if !defined( __WATCOMC__ )
    return( FALSE );
#endif
} /* MergeResExePE */


/*
 * writeLXHeadAndTables
 * NB when an error occurs this function must return without altering errno
 */
static RcStatus writeLXHeadAndTables( void )
{
    ExeFileInfo     *tmp;
    LXExeInfo       *lx_info;
    long            seek_rc;
    int_32          num_wrote;
    int_32          length;
    uint_32         offset;
    int             i;

    tmp = &Pass2Info.TmpFile;
    lx_info = &tmp->u.LXInfo;

    offset = sizeof( os2_flat_header );
    seek_rc = RcSeek( tmp->Handle, tmp->WinHeadOffset + offset, SEEK_SET );
    if( seek_rc == -1 )
        return( RS_WRITE_ERROR );

    // write object table
    length = lx_info->OS2Head.num_objects * sizeof( object_record );
    num_wrote = RcWrite( tmp->Handle, lx_info->Objects, length );
    if( num_wrote != length )
        return( RS_WRITE_ERROR );

    // write page table
    offset += length;
    length = lx_info->OS2Head.num_pages * sizeof( lx_map_entry );
    num_wrote = RcWrite( tmp->Handle, lx_info->Pages, length );
    if( num_wrote != length )
        return( RS_WRITE_ERROR );

    // write resource table
    offset += length;
    length = sizeof( flat_res_table );
    for( i = 0; i < lx_info->OS2Head.num_rsrcs; ++i ) {
        num_wrote = RcWrite( tmp->Handle, &lx_info->Res.resources[i].resource, length );
        if( num_wrote != length )
            return( RS_WRITE_ERROR );
    }

    // finally write LX header
    seek_rc = RcSeek( tmp->Handle, tmp->WinHeadOffset, SEEK_SET );
    if( seek_rc == -1 )
        return( RS_WRITE_ERROR );

    length = sizeof( os2_flat_header );
    num_wrote = RcWrite( tmp->Handle, &lx_info->OS2Head, length );
    if( num_wrote != length )
        return( RS_WRITE_ERROR );

    return( RS_OK );
} /* writeLXHeadAndTables */


/*
 * copyLXDebugInfo
 * NB when an error occurs this function must return without altering errno
 */
static RcStatus copyLXDebugInfo( void )
{
    long                seek_rc;
    ExeFileInfo         *old;
    ExeFileInfo         *tmp;
    os2_flat_header     *old_head;
    os2_flat_header     *new_head;

    old = &(Pass2Info.OldFile);
    tmp = &(Pass2Info.TmpFile);
    old_head = &old->u.LXInfo.OS2Head;
    new_head = &tmp->u.LXInfo.OS2Head;

    if( old_head->debug_len == 0 ) {
        new_head->debug_off = 0;
        new_head->debug_len = 0;
        return( RS_OK );
    }
    new_head->debug_off = tmp->DebugOffset;
    new_head->debug_len = old_head->debug_len;

    seek_rc = RcSeek( old->Handle, old_head->debug_off, SEEK_SET );
    if( seek_rc == -1)
        return( RS_READ_ERROR );
    seek_rc = RcSeek( tmp->Handle, tmp->DebugOffset, SEEK_SET );
    if( seek_rc == -1)
        return( RS_WRITE_ERROR );
    return( CopyExeDataTilEOF( old->Handle, tmp->Handle ) );
} /* copyLXDebugInfo */


extern int MergeResExeLX( void )
{
    RcStatus    error;
    int         err_code;

    error = copyStubFile( &err_code );
    if( error != RS_OK ) goto REPORT_ERROR;
    if( StopInvoked ) goto STOP_ERROR;

    error = RcBuildLXResourceObjects();
    if( error ) goto HANDLE_ERROR;
    if( StopInvoked ) goto STOP_ERROR;

    error = CopyLXExeObjects();
    if( error ) goto HANDLE_ERROR;
    if( StopInvoked ) goto STOP_ERROR;

    error = RcWriteLXResourceObjects();
    if( error != RS_OK ) {
        err_code = errno;
        goto REPORT_ERROR;
    }

    error = copyLXDebugInfo();
    if( error != RS_OK ) {
        err_code = errno;
        goto REPORT_ERROR;
    }
    if( StopInvoked ) goto STOP_ERROR;

    error = writeLXHeadAndTables();
    if( error != RS_OK ) {
        err_code = errno;
        goto REPORT_ERROR;
    }
    if( StopInvoked ) goto STOP_ERROR;

    return( TRUE );

REPORT_ERROR:
    switch( error ) {
    case RS_READ_ERROR:
        RcError( ERR_READING_EXE, Pass2Info.OldFile.name,
                 strerror( err_code )  );
        break;
    case RS_READ_INCMPLT:
        RcError( ERR_UNEXPECTED_EOF, Pass2Info.OldFile.name );
        break;
    case RS_WRITE_ERROR:
        RcError( ERR_WRITTING_TMP, Pass2Info.TmpFile.name,
                 strerror( err_code ) );
        break;
    case RS_BAD_FILE_FMT:
        RcError( ERR_NOT_VALID_EXE, Pass2Info.OldFile.name );
        break;
    case RS_NO_MEM:
        break;
    default:
       RcError( ERR_INTERNAL, INTERR_UNKNOWN_RCSTATUS );
    }
   /* fall through */
HANDLE_ERROR:
    return( FALSE );

STOP_ERROR:
    RcFatalError( ERR_STOP_REQUESTED );
#if !defined( __WATCOMC__ )
    return( FALSE );
#endif
} /* MergeResExeLX */

⌨️ 快捷键说明

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