module.c
来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 411 行
C
411 行
/****************************************************************************
*
* 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: WHEN YOU FIGURE OUT WHAT THIS FILE DOES, PLEASE
* DESCRIBE IT HERE!
*
****************************************************************************/
#include "plusplus.h"
#include "compcfg.h"
#include "cgfront.h"
#include "codegen.h"
#include "rtfuncod.h"
#include "label.h"
#include "fnbody.h"
#include "cgsegid.h"
#include "vstk.h"
#include "name.h"
#include "pcheader.h"
static SYMBOL module_init_func; // function to perform module-initialization
static SCOPE module_init_scope; // block scope for module-initialization
static FUNCTION_DATA module_fd; // module function information
SYMBOL StaticInitSymbol( // CREATE STATIC INITIALIZATION SYMBOL
SYMBOL sym ) // - symbol type
{
TYPE type; // - type for symbol
type_flag flags; // - modifier flags
type = sym->sym_type;
TypeModFlags( type, &flags );
if(( flags & TF1_CONST ) == 0 ) {
/* make it a constant symbol */
type = MakeModifiedType( type, TF1_CONST );
}
return SymCreateTempScope( type
, SC_STATIC
, SF_REFERENCED
, CppStaticInitName( sym ) );
}
static SYMBOL staticInitFuncVar(// DEFINE VARIABLE FOR INITIALIZATION FLAGS
void )
{
return SymCreateTempScope( MakeExpandableType( TYP_UCHAR )
, SC_STATIC
, SF_REFERENCED
, CppStaticOnceOnlyName() );
}
static void moduleInitVar( // GENERATE REFERENCE TO MODULE-INIT VAR.
SYMBOL var, // - variable
boolean base_type ) // - base_type or pointer to it
{
unsigned offset; // - offset to be tested
TYPE type; // - type for flags variable
type = var->sym_type;
offset = type->u.a.array_size - 1;
if( offset != 0 ) {
CgSetType( GetBasicType( TYP_UINT ) );
CgFrontCodeUint( IC_LEAF_CONST_INT, offset );
CgFrontSymbol( var );
CgSetType( MakePointerTo( type->of ) );
CgFrontCodeUint( IC_OPR_BINARY, CO_PLUS );
} else {
CgFrontSymbol( var );
}
if( base_type ) {
CgSetType( type->of );
} else {
CgSetType( MakePointerTo( type->of ) );
}
}
unsigned StaticInitFuncBeg( // START INITIALIZATION OF STATIC IN FUNCTION
void )
{
unsigned init_label; // - label #
INIT_VAR *init_var;
CgFrontStatInit();
init_var = FunctionBodyGetInit( NULL );
if( init_var->var == NULL ) {
init_var->var = staticInitFuncVar();
} else {
init_var->mask <<= 1;
if( init_var->mask >= 0x100 ) {
++init_var->var->sym_type->u.a.array_size;
init_var->mask = 1;
}
}
if( CompFlags.bm_switch_used ) {
SYMBOL rtf;
rtf = RunTimeCallSymbol( RTF_STATIC_INIT );
CgFrontSymbol( rtf );
CgSetType( GetBasicType( TYP_SINT ) );
CgFrontCodePtr( IC_CALL_SETUP, rtf );
CgSetType( GetBasicType( TYP_SINT ) );
CgFrontCodeUint( IC_LEAF_CONST_INT, init_var->mask );
CgFrontCode( IC_CALL_PARM );
moduleInitVar( init_var->var, FALSE );
CgFrontCode( IC_CALL_PARM );
CgFrontCode( IC_CALL_EXEC );
} else {
moduleInitVar( init_var->var, TRUE );
CgFrontCodeUint( IC_OPR_UNARY, CO_FETCH );
CgFrontCodeUint( IC_LEAF_CONST_INT, init_var->mask );
CgFrontCodeUint( IC_OPR_BINARY, CO_AND );
}
CgFrontCodeUint( IC_LEAF_CONST_INT, 0 );
CgFrontCodeUint( IC_OPR_BINARY, CO_NE );
init_label = CgFrontLabelCs();
CgFrontGotoNear( IC_LABEL_CS, O_IF_TRUE, init_label );
if( !CompFlags.bm_switch_used ) {
moduleInitVar( init_var->var, TRUE );
CgFrontCodeUint( IC_LEAF_CONST_INT, init_var->mask );
CgFrontCodeUint( IC_OPR_BINARY, CO_OR_EQUAL );
CgFrontCode( IC_EXPR_DONE );
}
return( init_label );
}
void StaticInitFuncEnd( // END INITIALIZATION OF STATIC IN FUNCTION
unsigned init_label ) // - label #
{
CgFrontLabdefCs( init_label );
CgFrontLabfreeCs( 1 );
}
static SCOPE moduleInitSave( // SAVE ENVIRONMENT BEFORE MOD-INIT.
void )
{
SCOPE save_scope;
save_scope = GetCurrScope();
LabelSwitchFunc( &module_fd.label_mem );
return( save_scope );
}
static void moduleInitRestore( // RESTORE ENVIRONMENT AFTER MOD-INIT.
SCOPE scope ) // - scope to restore to
{
SetCurrScope(scope);
LabelSwitchFunc( &module_fd.label_mem );
}
SCOPE ModuleFnScope( // SCOPE MOD-INIT FN IS DEF'D IN
void )
{
return GetFileScope();
}
void ModuleInitInit( // START MODULE-INITIALIZATION FUNCTION
void )
{
SYMBOL module_init; // - SYMBOL for mod-init. function
SCOPE curr_scope; // - current scope
TYPE fn_type; // - type for init function
curr_scope = moduleInitSave();
fn_type = TypeVoidFunOfVoid();
module_init = SymCreateFileScope( fn_type
, SC_STATIC
, 0
, CppSpecialName( SPECIAL_INIT_FUNCTION ) );
module_init_func = module_init;
SetCurrScope(GetFileScope());
ScopeBeginFunction( module_init );
FunctionBodyStartup( module_init, &module_fd, FUNC_NULL );
module_fd.retn_opt = FALSE;
module_init_scope = GetCurrScope();
ScopeKeep( module_init_scope );
moduleInitRestore( curr_scope );
}
void ModuleInitUsed( // FLAG MODULE-INITIALIZATION FUNCTION AS USED
void )
{
module_init_func->id = SC_STATIC;
module_init_func->flag |= SF_INITIALIZED | SF_REFERENCED;
}
SCOPE ModuleInitResume( // RESUME MODULE-INITIALIZATION FUNCTION
void )
{
SCOPE curr_scope;
curr_scope = moduleInitSave();
SetCurrScope(module_init_scope);
return( curr_scope );
}
void ModuleInitResumeScoped( // RESUME SCOPED MODULE-INITIALIZATION FUNC.
SCOPE scope ) // - scope before function
{
ScopeMemberModuleFunction( scope, module_init_scope );
}
void ModuleInitRestore( // UNDO MAKING MODULE-INIT FUNCTION A MEMBER FUNCTION
SCOPE restore_scope ) // - value returned by ModuleInitResume
{
ScopeRestoreModuleFunction( module_init_scope );
moduleInitRestore( restore_scope );
}
void ModuleInitFini( // COMPLETE MODULE-INITIALIZATION FUNCTION
void )
{
SCOPE save_scope;
CgFrontSwitchFile( module_init_func );
save_scope = ModuleInitResume();
FunctionBodyShutdown( module_init_func, &module_fd );
ScopeEnd( SCOPE_FUNCTION );
ModuleInitRestore( save_scope );
CgFrontModInitFini();
}
static void genInitFiniReference( // GENERATE INIT/FINI REFERENCE TO FUNCTION
SYMBOL func, // - function to be called
unsigned priority, // - priority
char *name, // - name for reference
fe_seg_id tgt_seg ) // - segment # of target segment
{
SYMBOL init_ref; // - reference to mod-init. function
TYPE type; // - used to build type
SegmentMarkUsed( tgt_seg );
type = MakePointerTo( func->sym_type );
init_ref = SymCreateFileScope( type
, SC_STATIC
, SF_INITIALIZED | SF_REFERENCED
, name );
init_ref->segid = tgt_seg;
if( tgt_seg == SEG_INIT_REF ) {
CgFrontInitRef();
} else {
CgFrontFiniRef();
}
CgFrontDataPtr( IC_DATA_LABEL, init_ref );
#if _INTEL_CPU
CgFrontDataPtr( IC_SET_TYPE, GetBasicType( TYP_UCHAR ) );
if( TargetSwitches & BIG_CODE ) {
CgFrontDataInt( IC_DATA_INT, 1 );
} else {
CgFrontDataInt( IC_DATA_INT, 0 );
}
CgFrontDataInt( IC_DATA_INT, priority );
#elif _CPU == _AXP
CgFrontDataPtr( IC_SET_TYPE, GetBasicType( TYP_UINT ) );
CgFrontDataInt( IC_DATA_INT, 0 );
CgFrontDataInt( IC_DATA_INT, priority );
#else
#error BAD _CPU
#endif
CgFrontDataPtr( IC_SET_TYPE, type );
CgFrontDataInt( IC_DATA_PTR_OFFSET, 0 );
CgFrontDataPtr( IC_DATA_PTR_SYM, func );
#if _CPU == 8086
if( 0 == ( TargetSwitches & BIG_CODE ) ) {
CgFrontDataInt( IC_DATA_INT, 0 );
}
#elif COMP_CFG_COFF == 1
CgFrontDataPtr( IC_SET_TYPE, GetBasicType( TYP_USHORT ) );
CgFrontDataInt( IC_DATA_INT, 0 );
#endif
}
void ModuleInitConnect( // CODE GENERATION FOR MODULE-INIT. CONNECTION
void )
{
genInitFiniReference( module_init_func
, CompInfo.init_priority
, CppSpecialName( SPECIAL_MODULE_INIT )
, SEG_INIT_REF );
}
SYMBOL ModuleInitFuncSym( // GET SYMBOL FOR MODULE-INITIALIZATION FUNC.
void )
{
return( module_init_func );
}
SCOPE ModuleInitScope( // GET BLOCK SCOPE FOR MODULE INITIALIZATION
void )
{
return( module_init_scope );
}
pch_status PCHWriteModuleData( void )
{
SYMBOL func;
SCOPE scope;
uint_8 has_state_table;
func = SymbolGetIndex( module_init_func );
PCHWrite( &func, sizeof( func ) );
scope = ScopeGetIndex( module_init_scope );
PCHWrite( &scope, sizeof( scope ) );
scope = ScopeGetIndex( module_fd.fn_scope );
PCHWrite( &scope, sizeof( scope ) );
has_state_table = module_fd.has_state_tab;
PCHWrite( &has_state_table, sizeof( has_state_table ) );
LabelPCHWrite( &module_fd.label_mem );
return( PCHCB_OK );
}
pch_status PCHReadModuleData( void )
{
uint_8 has_state_table;
PCHRead( &module_init_func, sizeof( module_init_func ) );
module_init_func = SymbolMapIndex( module_init_func );
PCHRead( &module_init_scope, sizeof( module_init_scope ) );
module_init_scope = ScopeMapIndex( module_init_scope );
PCHRead( &module_fd.fn_scope, sizeof( module_fd.fn_scope ) );
module_fd.fn_scope = ScopeMapIndex( module_fd.fn_scope );
PCHRead( &has_state_table, sizeof( has_state_table ) );
module_fd.has_state_tab = ( has_state_table != 0 );
LabelPCHRead( &module_fd.label_mem );
return( PCHCB_OK );
}
pch_status PCHInitModuleData( boolean writing )
{
writing = writing;
return( PCHCB_OK );
}
pch_status PCHFiniModuleData( boolean writing )
{
writing = writing;
return( PCHCB_OK );
}
boolean ModuleIsZap1( CGFILE_INS *p )
{
if( p->block != module_fd.init_state_tab.block ) {
return( FALSE );
}
if( p->offset != module_fd.init_state_tab.offset ) {
return( FALSE );
}
return( TRUE );
}
void *ModuleIsZap2( CGFILE_INS *p )
{
return( LabelBlockOpenFindZap( &module_fd.label_mem, p ) );
}
void ModuleAdjustZap1( CGFILE *cgf )
{
module_fd.init_state_tab = CgioLastWrite( cgf );
}
void ModuleAdjustZap2( CGFILE *cgf, void *h )
{
CGFILE_INS *dest;
dest = LabelBlockOpenAdjustZap( &module_fd.label_mem, h );
if( dest != NULL ) {
*dest = CgioLastWrite( cgf );
}
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?