bool CmdLnBatchRead( // READ NEXT LINE IN COMMAND BUFFER VBUF *buf ) // - virtual buffer { VbufInit( buf ); for(;;) { int c = nextChar(); if( CompFlags.batch_file_eof ) break; if( c == '\n' ) break; VbufConcChr( buf, c ); } DbgVerify( VbufLen( buf ) > 0, "CmdLnReadBatch -- nothing" ); ++ CompInfo.fc_file_line; return( VbufLen( buf ) ); }
static void fmtSymScope( SCOPE scope, VBUF *pvbuf, boolean include_function ) /***************************************************************************/ { TYPE class_type; NAME name; char *sname; SYMBOL sym; VBUF prefix; while( scope != NULL ) { switch( scope->id ) { case SCOPE_FILE: sname = ScopeNameSpaceFormatName( scope ); if( sname != NULL ) { VbufConcStrRev( pvbuf, scopeSep ); VbufConcStrRev( pvbuf, sname ); } break; case SCOPE_CLASS: class_type = ScopeClass( scope ); name = SimpleTypeName( class_type ); if( name != NULL ) { VbufConcStrRev( pvbuf, scopeSep ); if( class_type->flag & TF1_INSTANTIATION ) { fmtTemplateParms( pvbuf, class_type ); } VbufConcStrRev( pvbuf, NameStr( name ) ); } break; case SCOPE_FUNCTION: if( include_function ) { VbufInit( &prefix ); sym = ScopeFunction( scope ); formatScopedSym( sym, &prefix, FF_NULL ); if( VbufLen( &prefix ) > 0 ) { VbufConcStrRev( &prefix, functionDelim ); VbufPrepVbuf( pvbuf, &prefix ); } VbufFree( &prefix ); } return; // function scope resolved on function name case SCOPE_BLOCK: case SCOPE_TEMPLATE_DECL: case SCOPE_TEMPLATE_INST: case SCOPE_TEMPLATE_PARM: case SCOPE_TEMPLATE_SPEC_PARM: break; case SCOPE_MAX: default: VbufConcStrRev( pvbuf, scopeSep ); VbufConcStrRev( pvbuf, scopeError ); break; } scope = scope->enclosing; } }
void PrintFnovResolution( FNOV_RESULT result, arg_list *args, /***********************************************************/ FNOV_LIST *match, FNOV_LIST *reject, SYMBOL sym ) // pseudo pretty display of overloaded ranking information { int length; VBUF name; if( sym != NULL ) { FormatSym( sym, &name ); } else if( match != NULL ) { FormatSym( match->sym, &name ); } else if( reject != NULL ) { FormatSym( reject->sym, &name ); } else { VbufInit( &name ); } printf( " Result: %s\n", resultNames[result] ); if( VbufLen( &name ) > 0 ) { printf( "Symbol: '%s'", VbufString( &name ) ); VbufFree( &name ); length = RingCount( match ) + RingCount( reject ); if( length > 0 ) { printf( " occurs %d time%s", length, (length != 1 ? "s " : " " ) ); } } printf( "\n" ); if( sym == NULL && args != NULL ) { printf( "Ranked Arguments:\n" ); printArgs( args ); } if( match != NULL ) { printf( "Matching Functions:\n" ); PrintFnovList( match ); } if( reject != NULL ) { printf( "Rejected Functions:\n" ); PrintFnovList( reject ); } }
static int insertFixups( VBUF *src_code ) { struct asmfixup *fix; struct asmfixup *head; struct asmfixup *chk; struct asmfixup *next; struct asmfixup **owner; unsigned char *src; unsigned char *src_start; unsigned char *src_end; unsigned char cg_fix; bool perform_fixups; byte_seq *seq; SYMBOL sym; NAME name; unsigned char *dst; byte_seq_len len; unsigned skip; int mutate_to_segment; bool uses_auto; #if _CPU == 8086 int fixup_padding; #endif VBUF out_code; uses_auto = FALSE; perform_fixups = FALSE; head = FixupHead; if( head == NULL ) { out_code = *src_code; } else { VbufInit( &out_code ); FixupHead = NULL; /* sort the fixup list in increasing fixup_loc's */ for( fix = head; fix != NULL; fix = next ) { owner = &FixupHead; for( ;; ) { chk = *owner; if( chk == NULL ) break; if( chk->fixup_loc > fix->fixup_loc ) break; owner = &chk->next; } next = fix->next; fix->next = *owner; *owner = fix; } len = 0; cg_fix = 0; sym = NULL; src_start = VbufBuffer( src_code ); src_end = src_start + VbufLen( src_code ); fix = FixupHead; owner = &FixupHead; /* insert fixup escape sequences */ for( src = src_start; src < src_end; ) { /* reserve at least ASM_BLOCK bytes in the buffer */ VbufReqd( &out_code, _RoundUp( len + ASM_BLOCK, ASM_BLOCK ) ); dst = VbufBuffer( &out_code ); if( fix != NULL && fix->fixup_loc == (src - src_start) ) { name = NULL; if( fix->name != NULL ) { name = NameCreateNoLen( fix->name ); sym = ScopeASMUseSymbol( name, &uses_auto ); if( sym == NULL ) { return( 0 ); } } /* insert fixup information */ skip = 0; dst[len++] = FLOATING_FIXUP_BYTE; mutate_to_segment = 0; #if _CPU == 8086 fixup_padding = 0; #endif switch( fix->fixup_type ) { case FIX_FPPATCH: dst[len++] = fix->offset; break; case FIX_SEG: if( name == NULL ) { // special case for floating point fixup if( ( src[0] == 0x90 ) && ( src[1] == 0x9B ) ) { // inline assembler FWAIT instruction 0x90, 0x9b dst[len++] = FIX_FPP_WAIT; } else if( src[0] == 0x9b && (src[1] & 0xd8) == 0xd8 ) { // FWAIT as first byte and FPU instruction opcode as second byte dst[len++] = FIX_FPP_NORMAL; } else if( src[0] == 0x9b && (src[2] & 0xd8) == 0xd8 ) { // FWAIT as first byte and FPU instruction opcode as third byte // second byte should be segment override prefix switch( src[1] ) { case PREFIX_ES: dst[len++] = FIX_FPP_ES; break; case PREFIX_CS: dst[len++] = FIX_FPP_CS; break; case PREFIX_SS: dst[len++] = FIX_FPP_SS; break; case PREFIX_DS: dst[len++] = FIX_FPP_DS; break; case PREFIX_GS: dst[len++] = FIX_FPP_GS; break; case PREFIX_FS: dst[len++] = FIX_FPP_FS; break; default: --len; break; // skip FP patch } } else { // skip FP patch --len; } } else { skip = 2; cg_fix = FIX_SYM_SEGMENT; } break; case FIX_RELOFF16: skip = 2; cg_fix = FIX_SYM_RELOFF; break; case FIX_RELOFF32: skip = 4; cg_fix = FIX_SYM_RELOFF; #if _CPU == 8086 fixup_padding = 1; #endif break; case FIX_PTR16: mutate_to_segment = 1; /* fall through */ case FIX_OFF16: skip = 2; cg_fix = FIX_SYM_OFFSET; break; case FIX_PTR32: mutate_to_segment = 1; /* fall through */ case FIX_OFF32: skip = 4; cg_fix = FIX_SYM_OFFSET; #if _CPU == 8086 fixup_padding = 1; #endif break; default: CErr2p( ERR_ASSEMBLER_ERROR, "cannot reach label" ); break; } if( skip != 0 ) { dst[len++] = cg_fix; *((BYTE_SEQ_SYM *)&dst[len]) = sym; len += sizeof( BYTE_SEQ_SYM ); *((BYTE_SEQ_OFF *)&dst[len]) = fix->offset; len += sizeof( BYTE_SEQ_OFF ); src += skip; } #if _CPU == 8086 if( fixup_padding ) { // add offset fixup padding to 32-bit // cg create only 16-bit offset fixup dst[len++] = 0; dst[len++] = 0; // } #endif if( mutate_to_segment ) { /* Since the CG escape sequences don't allow for FAR pointer fixups, we have to split them into two. This is done by doing the offset fixup first, then mutating the fixup structure to look like a segment fixup one near pointer size later. */ fix->fixup_type = FIX_SEG; fix->fixup_loc += skip; fix->offset = 0; } else { head = fix; fix = fix->next; if( head->external ) { *owner = fix; CMemFree( head->name ); CMemFree( head ); } else { owner = &head->next; } } } else { if( *src == FLOATING_FIXUP_BYTE ) { dst[len++] = FLOATING_FIXUP_BYTE; } dst[len++] = *src++; } VbufSetLen( &out_code, len ); } perform_fixups = TRUE; } len = VbufLen( &out_code ); seq = CMemAlloc( offsetof( byte_seq, data ) + len ); seq->relocs = perform_fixups; seq->length = len; memcpy( seq->data, VbufBuffer( &out_code ), len ); CurrInfo->code = seq; if( VbufBuffer( &out_code ) != VbufBuffer( src_code ) ) VbufFree( &out_code ); return( uses_auto ); }