static void NearToFar( stack_entry *entry ) { addr_off near_off; near_off = entry->v.addr.mach.offset; if( entry->th == NULL || TypePtrAddrSpace( entry->th, entry->lc, &entry->v.addr ) != DS_OK ) { if( near_off == 0 ) { entry->v.addr = NilAddr; } else if( IsCodePointer( entry ) ) { entry->v.addr = Context.execution; } else if( entry->th != NULL ) { entry->v.addr = DefAddrSpaceForMod( TypeMod( entry->th ) ); } else { entry->v.addr = DefAddrSpaceForAddr( Context.execution ); } entry->v.addr.mach.offset = 0; } else { entry->info.modifier = TM_FAR; entry->info.size += sizeof( addr_seg ); } entry->v.addr.mach.offset += near_off; if( entry->th == NULL ) { entry->info.kind = TK_ADDRESS; } }
void DefAddr( memory_expr def_seg, address *addr ) { switch( def_seg ) { case EXPR_CODE: *addr = Context.execution; addr->mach.offset = 0; break; case EXPR_DATA: *addr = DefAddrSpaceForAddr( Context.execution ); break; } }
void DoAPoints( stack_entry *stk, type_kind def ) { stack_flags was_imp_addr; addr_off off; LRValue( stk ); was_imp_addr = stk->flags & SF_IMP_ADDR; switch( stk->info.kind ) { case TK_BOOL: case TK_ENUM: case TK_CHAR: case TK_INTEGER: //NYI: 64 bit offsets off = U32FetchTrunc( stk->v.uint ); stk->v.addr = DefAddrSpaceForAddr( Context.execution ); stk->v.addr.mach.offset = off; stk->info.modifier = TM_NEAR; /* fall through */ case TK_POINTER: case TK_ADDRESS: if( stk->th != NULL ) { LocationCreate( &stk->v.loc, LT_ADDR, &stk->v.addr ); DIPTypeBase( stk->th, stk->th, stk->lc, &stk->v.loc ); ClassifyEntry( stk, &stk->info ); if( stk->info.kind == TK_VOID ) { Error( ERR_NONE, LIT_ENG( ERR_VOID_BASE ) ); } } else { if( def == TK_NONE ) def = TK_INTEGER; stk->info.kind = def; switch( def ) { case TK_INTEGER: stk->info.modifier = TM_UNSIGNED; stk->info.size = DefaultSize( DK_INT ); break; case TK_ADDRESS: ExprSetAddrInfo( stk, false ); break; } LocationCreate( &stk->v.loc, LT_ADDR, &stk->v.addr ); } stk->flags |= SF_LOCATION | was_imp_addr; break; default: Error( ERR_NONE, LIT_ENG( ERR_ILL_TYPE ) ); break; } stk->flags &= ~SF_CONST; }
OVL_EXTERN bool ConvFP6( stack_entry *entry, conv_class from ) { address tmp; tmp = DefAddrSpaceForAddr( Context.execution ); switch( from ) { case U1: case U2: case U4: case U8: if( (entry->flags & SF_CONST) && U64Test( &entry->v.uint ) == 0 ) tmp = NilAddr; //NYI: 64 bit offsets tmp.mach.offset = U32FetchTrunc( entry->v.uint ); break; case I1: case I2: case I4: case I8: if( (entry->flags & SF_CONST) && I64Test( &entry->v.sint ) == 0 ) tmp = NilAddr; //NYI: 64 bit offsets tmp.mach.offset = U32FetchTrunc( entry->v.sint ); break; case NP2: case NP4: /* near pointers already have correct segment information filled in */ tmp = entry->v.addr; break; case FP4: case FP6: case HP4: tmp = entry->v.addr; break; default: return( FALSE ); } entry->v.addr = tmp; return( TRUE ); }
OVL_EXTERN bool ConvNP4( stack_entry *entry, conv_class from ) { addr48_off tmp; switch( from ) { case U1: case U2: case U4: case U8: //NYI: 64 bit offsets tmp = U32FetchTrunc( entry->v.uint ); break; case I1: case I2: case I4: case I8: //NYI: 64 bit offsets tmp = I32FetchTrunc( entry->v.sint ); break; case NP2: case NP4: case FP4: case FP6: tmp = entry->v.addr.mach.offset; break; default: return( FALSE ); } if( (entry->flags & SF_CONST) && tmp == 0 ) { entry->v.addr = NilAddr; } else { entry->v.addr = DefAddrSpaceForAddr( Context.execution ); } entry->v.addr.mach.offset = tmp; return( TRUE ); }