watlcl.c
来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 979 行 · 第 1/3 页
C
979 行
break;
}
return( DS_OK );
}
static address DefnAddr( lcl_defn *defn, lclinfo *local )
{
location_list ll;
if( DefnLocation( defn, NULL, &ll, local ) == DS_OK
&& ll.num == 1
&& ll.e[0].type == LT_ADDR ) {
return( ll.e[0].u.addr );
} else {
return( NilAddr );
}
}
search_result SearchLclMod( imp_image_handle *ii, imp_mod_handle im,
lookup_item *li, void *d )
{
lcl_defn defn;
int (*compare)();
byte *ptr;
byte *next;
char *name;
unsigned len;
imp_sym_handle *is;
search_result sr;
lclinfo lclld;
lclinfo *local = &lclld;
if( li->scope.start != NULL ) return( SR_NONE );
if( LoadLocalSyms( ii, im, &lclld ) != DS_OK ) return( SR_NONE );
if( li->case_sensitive ) {
compare = &memcmp;
} else {
compare = &memicmp;
}
name = li->name.start;
len = li->name.len;
sr = SR_NONE;
ptr = local->start;
for( ;; ) {
ptr = ModAddrLkupVar( ptr, local );
if( ptr == NULL ) break;
next = ProcDefn( ptr, &defn, local );
if( len == defn.i.namelen && compare( name, defn.i.name, len ) == 0 ) {
is = DCSymCreate( ii, d );
LclCreate( is, ptr, defn.i.name, local );
sr = SR_EXACT;
}
ptr = next;
}
PopLoad( local );
return( sr );
}
static search_result DoLclScope( imp_image_handle *ii, imp_mod_handle im,
address addr, lookup_item *li,
void *d, lclinfo *local )
{
lcl_defn blk;
lcl_defn defn;
byte *ptr;
byte *next;
unsigned parent;
int (*compare)();
char *name;
unsigned len;
search_result sr;
lookup_item li_type;
imp_type_handle it;
imp_sym_handle *is;
if( li->case_sensitive ) {
compare = memcmp;
} else {
compare = memicmp;
}
name = li->name.start;
len = li->name.len;
if( li->scope.start != NULL ) {
li_type.name = li->scope;
li_type.file_scope = li->file_scope;
li_type.case_sensitive = li->case_sensitive;
li_type.scope.start = NULL;
li_type.type = ST_TYPE;
sr = LookupTypeName( ii, im, &li_type, &it );
if( sr == SR_NONE ) return( SR_NONE );
return( SearchMbr( ii, &it, li, d ) );
}
ptr = local->start;
for( ;; ) {
ptr = FindBlockRout( ptr, local );
if( ptr == NULL ) return( SR_NONE );
ptr = ProcDefn( ptr, &blk, local );
if( DCSameAddrSpace( blk.b.start, addr ) == DS_OK
&& (blk.b.start.mach.offset <= addr.mach.offset)
&& (blk.b.start.mach.offset + blk.b.size > addr.mach.offset ) ) {
break;
}
}
sr = SR_NONE;
for( ;; ) {
if( blk.i.class == (CODE_SYMBOL | CODE_MEMBER_SCOPE) ) {
if( FindTypeHandle( ii, im, blk.i.type_index, &it ) == DS_OK ) {
sr = SearchMbr( ii, &it, li, d );
}
} else {
for( ;; ) {
ptr = FindLclVar( ptr, local );
if( ptr == NULL ) break;
next = ProcDefn( ptr, &defn, local );
if( len == defn.i.namelen
&& compare( name, defn.i.name, len ) == 0 ) {
is = DCSymCreate( ii, d );
LclCreate( is, ptr, defn.i.name, local );
sr = SR_EXACT;
}
ptr = next;
}
}
if( sr != SR_NONE ) break;
parent = blk.b.parent_block;
if( parent == 0 ) break;
ptr = ProcDefn( local->start + parent, &blk, local );
}
return( sr );
}
search_result SearchLclScope( imp_image_handle *ii, imp_mod_handle im,
address *addr, lookup_item *li, void *d )
{
search_result sr;
lclinfo lclld;
lclinfo *local = &lclld;
if( LoadLocalSyms( ii, im, &lclld ) != DS_OK ) return( SR_NONE );
sr = DoLclScope( ii, im, *addr, li, d, local );
PopLoad( local );
return( sr );
}
search_result LookupLclAddr( imp_image_handle *ii, address addr,
imp_sym_handle *is )
{
lcl_defn defn;
address mod_addr;
address close_addr;
byte *ptr;
byte *next;
search_result sr;
lclinfo lclld;
lclinfo *local = &lclld;
if( LoadLocalSyms( ii, is->im, &lclld ) != DS_OK ) return( SR_NONE );
sr = SR_NONE;
next = local->start;
for( ;; ) {
ptr = ModAddrLkupVar( next, local );
if( ptr == NULL ) break;
next = ProcDefn( ptr, &defn, local );
mod_addr = DefnAddr( &defn, local );
if( DCSameAddrSpace( addr, mod_addr ) == DS_OK ) {
if( addr.mach.offset >= mod_addr.mach.offset ) {
/* possible */
if( sr == SR_NONE
|| close_addr.mach.offset <= mod_addr.mach.offset ) {
LclCreate( is, ptr, defn.i.name, local );
close_addr = mod_addr;
if( addr.mach.offset == mod_addr.mach.offset ) {
sr = SR_EXACT;
break;
}
sr = SR_CLOSEST;
}
}
}
}
PopLoad( local );
return( sr );
}
unsigned SymHdl2LclName( imp_image_handle *ii, imp_sym_handle *is,
char *name, unsigned max )
{
byte *ptr;
unsigned len;
lclinfo lclld;
lclinfo *local = &lclld;
if( LoadLocalSyms( ii, is->im, &lclld ) != DS_OK ) return( 0 );
ptr = local->start + is->u.lcl.offset;
len = *ptr - is->name_off;
if( max > 0 ) {
--max;
if( max > len ) max = len;
ptr += is->name_off;
memcpy( name, ptr, max );
name[max] = '\0';
}
PopLoad( local );
return( len );
}
static void SetBase( imp_sym_handle *is, lclinfo *local )
{
local->base_off = is->u.lcl.base;
if( is->u.lcl.base != NO_BASE ) {
NewBase( local->start + is->u.lcl.base, local );
}
}
dip_status SymHdl2LclLoc( imp_image_handle *ii, imp_sym_handle *is,
location_context *lc, location_list *ll )
{
lcl_defn defn;
dip_status ret;
lclinfo lclld;
lclinfo *local = &lclld;
ret = LoadLocalSyms( ii, is->im, &lclld );
if( ret != DS_OK ) return( ret );
SetBase( is, local );
ProcDefn( local->start + is->u.lcl.offset, &defn, local );
ret = DefnLocation( &defn, lc, ll, local );
PopLoad( local );
return( ret );
}
dip_status SymHdl2LclType( imp_image_handle *ii, imp_sym_handle *is,
imp_type_handle *it )
{
lcl_defn defn;
dip_status ret;
lclinfo lclld;
lclinfo *local = &lclld;
ret = LoadLocalSyms( ii, is->im, &lclld );
if( ret != DS_OK ) return( ret );
local->base_off = 0;
ProcDefn( local->start + is->u.lcl.offset, &defn, local );
ret = FindTypeHandle( ii, is->im, defn.i.type_index, it );
PopLoad( local );
return( ret );
}
void SetGblLink( imp_sym_handle *is, void *link )
{
is->u.lcl.gbl_link = link;
}
dip_status Lcl2GblHdl( imp_image_handle *ii,
imp_sym_handle *lcl_is, imp_sym_handle *gbl_is )
{
lcl_defn defn;
dip_status ret;
location_list ll;
lclinfo lclld;
lclinfo *local = &lclld;
if( lcl_is->u.lcl.gbl_link != NULL ) {
return( Link2GblHdl( ii, lcl_is->u.lcl.gbl_link, gbl_is ) );
}
ret = LoadLocalSyms( ii, lcl_is->im, &lclld );
if( ret != DS_OK ) return( ret );
SetBase( lcl_is, local );
ProcDefn( local->start + lcl_is->u.lcl.offset, &defn, local );
ret = DefnLocation( &defn, NULL, &ll, local );
if( ret != DS_OK ) goto done;
ret = DS_FAIL;
if( ll.num != 1 || ll.e[0].type != LT_ADDR ) goto done;
gbl_is->im = lcl_is->im;
if( LookupGblAddr( ii, ll.e[0].u.addr, gbl_is ) != SR_EXACT ) goto done;
ret = DS_OK;
done:
PopLoad( local );
return( ret );
}
dip_status SymHdl2LclInfo( imp_image_handle *ii, imp_sym_handle *is,
sym_info *si )
{
lcl_defn defn;
byte *p;
dip_status ret;
lclinfo lclld;
lclinfo *local = &lclld;
imp_sym_handle gbl_is;
ret = LoadLocalSyms( ii, is->im, &lclld );
if( ret != DS_OK ) return( ret );
if( Lcl2GblHdl( ii, is, &gbl_is ) == DS_OK ) {
SymHdl2GblInfo( ii, &gbl_is, si ); /* get the global bit set */
}
SetBase( is, local );
ProcDefn( local->start + is->u.lcl.offset, &defn, local );
switch( defn.i.class & CLASS_MASK ) {
case VAR_SYMBOL:
si->kind = SK_DATA;
break;
case CODE_SYMBOL:
si->kind = SK_PROCEDURE; /* never get handled a block */
switch( defn.i.class & SUBCLASS_MASK ) {
case CODE_FAR_ROUT:
case CODE_FAR_ROUT386:
si->rtn_far = 1;
break;
default:
si->rtn_far = 0;
break;
}
si->rtn_calloc = 0;
si->ret_modifier = TM_NONE;
si->ret_size = 0;
switch( *defn.i.unparsed ) {
case IND_REG+IR_RALLOC_NEAR:
si->ret_modifier = TM_NEAR;
break;
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?