mapio.c

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

C
678
字号

/****************************************************************************
*
*                            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:  Map file formatting routines
*
****************************************************************************/


#include <limits.h>
#include <stdio.h>
#include <string.h>
#include <time.h>
#include "linkstd.h"
#include "pcobj.h"
#include "newmem.h"
#include "msg.h"
#include "alloc.h"
#include "wlnkmsg.h"
#include "objnode.h"
#include "loadfile.h"
#include "fileio.h"
#include "overlays.h"
#include "ring.h"
#include "mapio.h"

#undef pick
#define pick( num, string ) string

static char *MsgStrings[] = {
#include "msg.h"

typedef struct symrecinfo {
    struct symrecinfo * next;
    symbol *            sym;
    mod_entry *         mod;
} symrecinfo;

static symrecinfo *     UndefList;
static symrecinfo *     SymTraceList;
static  int             MapCol;
static  time_t          StartT;
static  clock_t         ClockTicks;
static  bool            Absolute_Seg;
static bool             Buffering;  // buffering on/off.
static int              BufferSize;          // # of chars in buffer.


extern void ResetMapIO( void )
/****************************/
{
    MapFlags = 0;
    UndefList = NULL;
    SymTraceList = NULL;
}

extern void StartTime( void )
/***************************/
{
    StartT = time( NULL );
    ClockTicks = clock();
}


static char * PutDec( char *ptr, unsigned num )
/*********************************************/
{
    *ptr++ = ( num / 10 ) % 10 + '0';
    *ptr++ = num % 10 + '0';
    return( ptr );
}

extern void StartMapBuffering( void )
/***********************************/
{
    Buffering = TRUE;
    BufferSize = 0;
}

extern void StopMapBuffering( void )
/**********************************/
// flush buffer & shut buffering off.
{
    if( BufferSize != 0 ) {
        QWrite( MapFile, TokBuff, BufferSize, MapFName );
    }
    Buffering = FALSE;
    BufferSize = 0;
}

extern void MapInit( void )
/*************************/
{
    char                tim[ 8 + 1 ];
    char                dat[ 8 + 1 ];
    char                *ptr;
    struct tm           *localt;
    char                *msg;

    Absolute_Seg = FALSE;
    Buffering = FALSE;  // buffering on/off.
    if( ( MapFlags & MAP_FLAG ) == 0 )
        return;
    MapFile = QOpenRW( MapFName );
    StartMapBuffering();
    localt = localtime( &StartT );
    MapCol = 0;
    msg = MsgStrings[ PRODUCT ];
    BufWrite( msg, strlen( msg ) );
    WriteMapNL( 1 );
    msg = MsgStrings[ COPYRIGHT ];
    BufWrite( msg, strlen( msg ) );
    WriteMapNL( 1 );
    ptr = tim;
    ptr = PutDec( ptr, localt->tm_hour );
    *ptr++ = ':';
    ptr = PutDec( ptr, localt->tm_min );
    *ptr++ = ':';
    ptr = PutDec( ptr, localt->tm_sec );
    *ptr = '\0';

    ptr = dat;
    ptr = PutDec( ptr, localt->tm_year );
    *ptr++ = '/';
    ptr = PutDec( ptr, localt->tm_mon + 1 );
    *ptr++ = '/';
    ptr = PutDec( ptr, localt->tm_mday );
    *ptr = '\0';

    LnkMsg( MAP+MSG_CREATED_ON, "12", dat, tim );
    StopMapBuffering();
}

static void WriteBox( unsigned int msgnum )
/*****************************************/
{
    char        box_buff[RESOURCE_MAX_SIZE];
    char        msg_buff[RESOURCE_MAX_SIZE];
    int         i;

    Msg_Get( msgnum, msg_buff );
    WriteMapNL( 2 );
    box_buff[0] = '+';
    for( i = 2; i < strlen( msg_buff ); i++ ) {
        box_buff[i-1] = '-';
    }
    box_buff[i-1] = '+';
    box_buff[i] = '\0';
    WriteMap( "%t24%s", "", box_buff );
    WriteMap( "%t24%s", "", msg_buff );
    WriteMap( "%t24%s", "", box_buff );
    WriteMapNL( 1 );
}

extern void WriteGroups( void )
/*****************************/
{
    group_entry *   currgrp;

    if( Groups != NULL ) {
        WriteBox( MSG_MAP_BOX_GROUP );
        Msg_Write_Map( MSG_MAP_TITLE_GROUP_0 );
        Msg_Write_Map( MSG_MAP_TITLE_GROUP_1 );
        WriteMapNL( 1 );
        currgrp = Groups;
        while( currgrp != NULL ) {
            if( !currgrp->isautogrp ) { /* if not an autogroup */
                WriteFormat( 0, currgrp->sym->name );
                WriteFormat( 32, "%a", &currgrp->grp_addr );
                WriteFormat( 53, "%h", currgrp->totalsize );
                WriteMapNL( 1 );
            }
            currgrp = currgrp->next_group;
        }
    }
}

static void WriteAbsSeg( void *_leader )
/**************************************/
{
    seg_leader *leader = _leader;

    if( leader->info & SEG_ABSOLUTE ) {
        WriteFormat( 0, leader->segname );
        WriteFormat( 24, leader->class->name );
        WriteFormat( 40, "%a", &leader->seg_addr );
        WriteFormat( 60, "%h", leader->size );
        WriteMapNL( 1 );
    }
}

static void WriteAbsSegs( class_entry *cl )
/*****************************************/
/* write absolute segment info into mapfile */
{
    WriteBox( MSG_MAP_BOX_ABS_SEG );
    Msg_Write_Map( MSG_MAP_TITLE_ABS_SEG_0 );
    Msg_Write_Map( MSG_MAP_TITLE_ABS_SEG_1 );
    WriteMapNL( 1 );
    while( cl != NULL ) {
        if( ( cl->flags & CLASS_DEBUG_INFO ) == 0 ) {
            RingWalk( cl->segs, WriteAbsSeg );
        }
        cl = cl->next_class;
    }
}

static void WriteNonAbsSeg( void *_seg )
/**************************************/
{
    seg_leader *seg = _seg;

    if( !( seg->info & SEG_ABSOLUTE ) ) {
        WriteFormat( 0, seg->segname );
        WriteFormat( 23, seg->class->name );
        if( seg->group != NULL ) {
            WriteFormat( 38, seg->group->sym->name );
        }
        WriteFormat( 53, "%a", &seg->seg_addr );
        WriteFormat( 69, "%h", seg->size );
        WriteMapNL( 1 );
    } else {
        Absolute_Seg = TRUE;
    }
}

extern void WriteSegs( class_entry *firstcl )
/*******************************************/
/* write segment info into mapfile */
{
    class_entry         *cl;

    cl = firstcl;
    if( cl != NULL ) {
        WriteBox( MSG_MAP_BOX_SEGMENTS );
        Msg_Write_Map( MSG_MAP_TITLE_SEGMENTS_0 );
        Msg_Write_Map( MSG_MAP_TITLE_SEGMENTS_1 );
        WriteMapNL( 1 );
        while( cl != NULL ) {
            if( ( cl->flags & CLASS_DEBUG_INFO ) == 0 ) {
                RingWalk( cl->segs, WriteNonAbsSeg );
            }
            cl = cl->next_class;
        }
        if( Absolute_Seg ) {
            WriteAbsSegs( firstcl );
        }
    }
}

extern void WritePubHead( void )
/******************************/
{
    WriteBox( MSG_MAP_BOX_MEMORY_MAP );
    Msg_Write_Map( MSG_MAP_UNREF_SYM );
    Msg_Write_Map( MSG_MAP_REF_LOCAL_SYM );
    if( MapFlags & MAP_STATICS ) {
        Msg_Write_Map( MSG_MAP_SYM_STATIC );
    }
    WriteMapNL( 1 );
    Msg_Write_Map( MSG_MAP_TITLE_MEMORY_MAP_0 );
    Msg_Write_Map( MSG_MAP_TITLE_MEMORY_MAP_1 );
    WriteMapNL( 1 );
}

extern void WritePubModHead( void )
/*********************************/
{
    char        full_name[ PATH_MAX ];

    if ( CurrMod->f.source == NULL ) {
        strcpy( full_name , CurrMod->name );
    } else {
        char *  path_ptr;
        path_ptr = CurrMod->f.source->file->prefix;
        if( path_ptr != NULL ) {
            QMakeFileName( &path_ptr, CurrMod->f.source->file->name, full_name );
        } else {
            strcpy( full_name, CurrMod->f.source->file->name );
        }
    }
    Msg_Write_Map( MSG_MAP_DEFINING_MODULE, full_name, CurrMod->name );
}

extern void WriteOvlHead( void )
/******************************/
{
    WriteBox( MSG_MAP_BOX_OVERLAY_VECTOR );
}

static void WriteModSegHead( void )
/*********************************/
{
    WriteBox( MSG_MAP_BOX_MOD_SEG );
    if( Absolute_Seg ) {
        Msg_Write_Map( MSG_MAP_ABS_ADDR );
    }
    Msg_Write_Map( MSG_MAP_32BIT_SEG );
    Msg_Write_Map( MSG_MAP_COMDAT );
    WriteMapNL( 1 );
    Msg_Write_Map( MSG_MAP_TITLE_MOD_SEG_0 );
    Msg_Write_Map( MSG_MAP_TITLE_MOD_SEG_1 );
    WriteMapNL( 1 );
}

static void WriteImports( void )
/******************************/
{
    if( FmtData.type & ( MK_NOVELL | MK_OS2 | MK_PE ) ) {
        WriteBox( MSG_MAP_BOX_IMP_SYM );
        if( FmtData.type & ( MK_NOVELL | MK_ELF ) ) {
            Msg_Write_Map( MSG_MAP_TITLE_IMP_SYM_0 );
            Msg_Write_Map( MSG_MAP_TITLE_IMP_SYM_1 );
        } else {
            Msg_Write_Map( MSG_MAP_TITLE_IMP_SYM_2 );
            Msg_Write_Map( MSG_MAP_TITLE_IMP_SYM_3 );

⌨️ 快捷键说明

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