📄 cgen2.c
字号:
SymGet( &sym, sym_handle );
sym.flags |= SYM_EMITTED;
SymReplace( &sym, sym_handle );
}
}
} else if( sym.stg_class != SC_EXTERN &&
sym.stg_class != SC_TYPEDEF ) { /* 25-nov-94 */
if( sym.flags & SYM_ADDR_TAKEN ) {
emit_extra_info = 1;
}
typ = sym.sym_type;
while( typ->decl_type == TYPE_TYPEDEF ) typ = typ->object;
switch( typ->decl_type ) {
case TYPE_UNION:
case TYPE_STRUCT:
case TYPE_ARRAY:
case TYPE_FCOMPLEX:
case TYPE_DCOMPLEX:
case TYPE_LDCOMPLEX:
emit_extra_info = 1;
break;
}
dtype = CGenType( typ );
if( sym.flags & SYM_FUNC_RETURN_VAR ) {
sym.info.return_var = CGTemp( dtype );
SymReplace( &sym, sym_handle );
} else {
CGAutoDecl( sym_handle, dtype );
}
}
#if _CPU != 370
if( ! CompFlags.debug_info_some ) emit_extra_info = 0;
#endif
if( emit_debug_info != 0 || emit_extra_info != 0 ) {
if( Saved_CurFunc == 0 ) { /* if we are not inlining */
if( GenSwitches & DBG_LOCALS ) {
if( !(sym.flags & SYM_TEMP) ) {
DBLocalSym( sym_handle, TY_DEFAULT );
}
}
}
}
sym_handle = sym.handle;
}
}
local void FreeSymBackInfo( SYM_ENTRY *sym, SYM_HANDLE sym_handle )
{
if( sym->info.backinfo != NULL ) {
BEFiniBack( sym->info.backinfo );
BEFreeBack( sym->info.backinfo );
sym->info.backinfo = NULL;
SymReplace( sym, sym_handle );
}
}
#ifdef __SEH__
static void FreeTrySymBackInfo( void )
{
SYM_ENTRY sym;
SymGet( &sym, TrySymHandle );
FreeSymBackInfo( &sym, TrySymHandle );
}
static void FreeTryTableBackHandles( void )
{
struct try_table_back_handles *try_backinfo;
for(;;) {
try_backinfo = TryTableBackHandles;
if( try_backinfo == NULL ) break;
TryTableBackHandles = try_backinfo->next;
BEFreeBack( try_backinfo->try_table_back_handle );
CMemFree( try_backinfo );
}
}
#endif
local void FreeLocalVars( SYM_HANDLE sym_list )
{
SYM_HANDLE sym_handle;
auto SYM_ENTRY sym;
for( ; sym_handle = sym_list; ) {
SymGet( &sym, sym_handle );
sym_list = sym.handle;
if( sym.stg_class != SC_EXTERN ) {
if( ! (sym.flags & SYM_FUNC_RETURN_VAR) ) {
if( sym.sym_type->decl_type != TYPE_VOID ) {
FreeSymBackInfo( &sym, sym_handle );
}
}
}
}
}
local void FreeGblVars( SYM_HANDLE sym_handle )
{
SYMPTR sym;
for( ; sym_handle; ) {
sym = SymGetPtr( sym_handle );
sym_handle = sym->handle;
if( sym->info.backinfo != NULL ) {
// BEFiniBack( sym->info.backinfo );
BEFreeBack( sym->info.backinfo );
}
}
}
local void RelExtVars( SYM_HANDLE sym_handle )
{
SYMPTR sym;
for( ; sym_handle; ) {
sym = SymGetPtr( sym_handle );
sym_handle = sym->handle;
if( !(sym->flags & SYM_FUNC_RETURN_VAR) ) {
if( sym->stg_class == SC_EXTERN || sym->stg_class == SC_STATIC ||
sym->sym_type->decl_type == TYPE_VOID ) {
if( sym->info.backinfo != NULL ) {
BEFreeBack( sym->info.backinfo );
}
}
}
}
}
local void FreeExtVars() /* 02-apr-92 */
{
SYM_LISTS *sym_list;
SYM_LISTS *next_sym;
for( sym_list = SymListHeads; sym_list; ) {
RelExtVars( sym_list->sym_head );
next_sym = sym_list->next;
CMemFree( sym_list );
sym_list = next_sym;
}
}
int CGenType( TYPEPTR typ )
{
int dtype;
int flags;
int align;
while( typ->decl_type == TYPE_TYPEDEF ) typ = typ->object;
switch( typ->decl_type ) {
case TYPE_FCOMPLEX:
case TYPE_DCOMPLEX:
case TYPE_LDCOMPLEX:
case TYPE_STRUCT:
case TYPE_UNION:
if( typ->object != NULL ) { /* 15-jun-94 */
/* structure has a zero length array as last field */
dtype = NewRefno();
align = GetTypeAlignment( typ );
BEDefType( dtype, align, TypeSize(typ) );
} else if( typ->u.tag->refno == 0 ) {
dtype = NewRefno();
align = GetTypeAlignment( typ );
BEDefType( dtype, align, TypeSize(typ) );
typ->u.tag->refno = dtype;
} else {
dtype = typ->u.tag->refno;
}
break;
case TYPE_ARRAY:
if( typ->u.array->refno == 0 ) {
dtype = NewRefno();
align = GetTypeAlignment( typ );
BEDefType( dtype, align, SizeOfArg( typ ) );
typ->u.array->refno = dtype;
}
dtype = typ->u.array->refno;
break;
case TYPE_FIELD:
case TYPE_UFIELD:
dtype = CGDataType[ typ->u.f.field_type ];
break;
case TYPE_FUNCTION:
dtype = CodePtrType( FLAG_NONE ); /* 20-nov-87 */
break;
case TYPE_POINTER:
flags = typ->u.p.decl_flags;
dtype = PtrType( typ->object, flags );
break;
case TYPE_ENUM:
typ = typ->object;
default:
dtype = CGDataType[ typ->decl_type ];
}
return( dtype );
}
local int CodePtrType( int flags )
{
#if _MACHINE == _PC
int dtype;
if( flags & FLAG_FAR ) {
dtype = T_LONG_CODE_PTR;
} else if( flags & FLAG_NEAR ) {
dtype = T_NEAR_CODE_PTR;
} else {
dtype = T_CODE_PTR;
}
return( dtype );
#else
return( T_CODE_PTR );
#endif
}
extern int PtrType( TYPEPTR typ, int flags )
{
int dtype;
while( typ->decl_type == TYPE_TYPEDEF ) typ = typ->object;/*03-dec-91*/
if( typ->decl_type == TYPE_FUNCTION ) {
dtype = CodePtrType( flags );
} else {
#if _MACHINE == _PC
if( flags & FLAG_FAR ) {
dtype = T_LONG_POINTER;
} else if( flags & FLAG_HUGE ) {
dtype = T_HUGE_POINTER;
} else if( flags & FLAG_NEAR ) {
dtype = T_NEAR_POINTER;
} else {
dtype = T_POINTER;
}
#else
dtype = T_POINTER;
#endif
}
return( dtype );
}
local int StringSegment( STR_HANDLE strlit )
{
#if _MACHINE == _PC
if( strlit->flags & FLAG_FAR )
return( FarStringSegment );
#endif
if( strlit->flags & FLAG_CONST )
return( SEG_CODE ); /* 01-sep-89*/
return( SEG_CONST );
}
void EmitStrPtr( STR_HANDLE str_handle, int pointer_type )
{
str_handle->ref_count++;
Emit1String( str_handle );
DGBackPtr( str_handle->cg_back_handle, StringSegment( str_handle ),
0, pointer_type );
}
local void Emit1String( STR_HANDLE str_handle )
{
if( str_handle->cg_back_handle == 0 ) {
str_handle->cg_back_handle = BENewBack( NULL );
if( ! (str_handle->flags & FLAG_CONST) ) {
EmitLiteral( str_handle );
}
}
}
int EmitBytes( STR_HANDLE strlit )
{
DGBytes( strlit->length, strlit->literal );
return( strlit->length );
}
local void EmitLiteral( STR_HANDLE strlit )
{
segment_id old_segment;
old_segment = BESetSeg( StringSegment( strlit ) );
if( strlit->flags & STRLIT_WIDE ) {
DGAlign( TARGET_SHORT ); /* NT requires word aligned wide strings */
}
DGLabel( strlit->cg_back_handle );
EmitBytes( strlit );
BESetSeg( old_segment );
}
local void FreeStrings( void )
{
STR_HANDLE strlit, next;
int i;
for( i = 0; i < STRING_HASH_SIZE; ++i ) {
for( strlit = StringHash[i]; strlit; ) {
if( strlit->cg_back_handle != 0 ) {
BEFiniBack( strlit->cg_back_handle );
BEFreeBack( strlit->cg_back_handle );
strlit->cg_back_handle = 0;
}
next = strlit->next_string;
FreeLiteral( strlit );
strlit = next;
}
StringHash[i] = 0;
}
}
local void DumpCS_Strings( STR_HANDLE strlit )
{
while( strlit != NULL ) {
if( strlit->flags & FLAG_CONST &&
strlit->ref_count != 0 ) { /* 17-aug-91 */
strlit->cg_back_handle = BENewBack( NULL );
EmitLiteral( strlit );
}
strlit = strlit->next_string;
}
}
local void EmitCS_Strings( void )
{
int i;
if( CompFlags.strings_in_code_segment ) {
for( i = STRING_HASH_SIZE - 1; i >= 0; --i ) {
DumpCS_Strings( StringHash[i] );
}
}
}
#ifdef __SEH__
static void GenerateTryBlock( TREEPTR tree )
{
TREEPTR stmt;
int try_index;
int max_try_index;
try_index = 0;
max_try_index = -1;
for(;;) {
stmt = tree->right;
if( stmt->op.opr == OPR_FUNCEND ) break;
switch( stmt->op.opr ) {
case OPR_TRY:
try_index = stmt->op.try_index;
if( try_index > max_try_index ) max_try_index = try_index;
break;
case OPR_EXCEPT:
case OPR_FINALLY:
ValueStack[ try_index ] = (TREEPTR)stmt->op.try_sym_handle;
Class[ try_index ] = stmt->op.parent_scope;
Token[ try_index ] = stmt->op.opr;
break;
}
tree = tree->left;
if( tree == NULL ) break; // should never happen
}
if( max_try_index != -1 ) {
segment_id old_segment;
back_handle except_label;
back_handle except_table;
struct try_table_back_handles *try_backinfo;
old_segment = BESetSeg( SEG_DATA );
except_table = BENewBack( NULL );
try_backinfo = (struct try_table_back_handles *)
CMemAlloc( sizeof( struct try_table_back_handles ) );
try_backinfo->try_table_back_handle = except_table;
try_backinfo->next = TryTableBackHandles;
TryTableBackHandles = try_backinfo;
DGLabel( except_table );
for( try_index = 0; try_index <= max_try_index; try_index++ ) {
DGInteger( Class[ try_index ], T_UINT_1 ); // parent index
if( Token[ try_index ] == OPR_EXCEPT ) {
DGInteger( 0, T_UINT_1 );
} else {
DGInteger( 1, T_UINT_1 );
}
except_label = FEBack( (SYM_HANDLE)ValueStack[ try_index ] );
DGBackPtr( except_label, FESegID( CurFuncHandle ), 0,
T_CODE_PTR );
}
BESetSeg( old_segment );
SetTryTable( except_table );
BEFiniBack( except_table );
}
}
#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -