parsems.c
来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 604 行 · 第 1/2 页
C
604 行
// read in microsoft linker commands
{
char hmm;
bool sameprompt;
bool gottoken;
int prompt;
char * sect;
sameprompt = TRUE;
gottoken = FALSE;
prompt = 0; // object files.
while( CmdFile->where != ENDOFCMD ) {
switch( CmdFile->where ) {
case MIDST:
EatWhite();
hmm = *CmdFile->current;
switch( hmm ) {
case '\0':
if( CmdFile->how == BUFFERED ) {
CmdFile->where = ENDOFFILE;
sameprompt = TRUE;
break;
} else if( CmdFile->how == NONBUFFERED ){
CmdFile->where = ENDOFLINE;
sameprompt = TRUE;
break;
} // note the possible fall through.
case '\n':
if( CmdFile->how == BUFFERED ) {
CmdFile->current++;
} else {
CmdFile->where = ENDOFLINE;
}
if( !sameprompt ) {
NextPrompt( &prompt );
}
sameprompt = FALSE;
gottoken = FALSE;
break;
case '@':
CmdFile->current++;
if( !MakeToken( SEP_NO, TRUE ) ) {
Error( "file name not recognized" );
}
StartNewFile( ToString() );
break;
case '+':
CmdFile->current++;
if( !gottoken ) {
Warning( "unexpected + sign found ... ignoring", prompt );
} else {
sameprompt = TRUE;
}
gottoken = FALSE;
break;
case ',':
CmdFile->current++;
if( prompt >= 5 ) {
Warning( "unexpected comma found ... ignoring", prompt );
} else {
NextPrompt( &prompt );
}
gottoken = FALSE;
break;
case ';':
CmdFile->where = ENDOFCMD;
break;
case '/':
CmdFile->current++;
if( !ProcessOptions() ) {
DirectiveError();
}
gottoken = TRUE;
break;
case '(':
CmdFile->current++;
if( prompt != 0 ) {
Warning( "can only overlay object files", prompt );
break;
}
if( OverlayLevel > 0 ) {
Warning( "overlay nesting ignored since it's not allowed by Microsoft",
OVERLAY_SLOT );
} else { // need a section keyword.
sect = MemAlloc( 8 );
memcpy( sect, "section", 8 );
AddCommand( sect , OVERLAY_SLOT, TRUE );
}
OverlayLevel++; // so spurious errors not produced.
break;
case ')':
CmdFile->current++;
if( prompt == 0 ) { // warning already printed otherwise.
if( OverlayLevel <= 0 ){
Warning("unexpected ) found ... ignoring",OVERLAY_SLOT);
} else {
OverlayLevel--;
}
}
break;
default: // must be a file name
ProcessFileName( prompt );
gottoken = TRUE;
sameprompt = FALSE;
break;
}
break;
case ENDOFLINE:
GetNewLine( prompt );
break;
case ENDOFFILE:
RestoreCmdLine();
break;
}
}
ProcessDefFile();
}
extern bool MakeToken( sep_type separator, bool include_fn )
/**********************************************************/
// include_fn == TRUE if '.' and ':' are allowed to be part of the token
// (include filename).
{
int quit;
char hmm;
char matchchar;
int len;
bool forcematch;
bool hitmatch;
EatWhite();
hmm = *CmdFile->current;
CmdFile->token = CmdFile->current;
if( hmm == '\0' || hmm == '\n' ) {
CmdFile->len = 0;
return( FALSE );
}
CmdFile->len = 1; // for error reporting.
switch( separator ){
case SEP_QUOTE:
if( hmm != '\'' && hmm != '"' ) {
return( FALSE );
}
matchchar = hmm;
break;
case SEP_AT:
if( hmm != '@' ) {
return( FALSE );
}
break;
case SEP_COLON:
if( hmm != ':' ) {
return( FALSE );
}
break;
case SEP_EQUALS:
if( hmm != '=' ) {
return( FALSE );
}
break;
case SEP_PERIOD:
if( hmm != '.' ) {
return( FALSE );
}
break;
default:
CmdFile->current--; // no separator wanted.
}
CmdFile->current++; // skip separator.
CmdFile->token = CmdFile->current;
hmm = *CmdFile->current;
if( hmm == '\0' || hmm == '\n' ) {
CmdFile->len = 0;
return( FALSE );
}
len = 0;
quit = FALSE;
forcematch = (separator == SEP_QUOTE );
hitmatch = FALSE;
while( !quit ) {
len++;
CmdFile->current++;
hmm = *CmdFile->current;
switch( hmm ) {
case '\'':
case '"':
if( separator == SEP_QUOTE && hmm == matchchar ) {
CmdFile->current++; // don't include end quote in next token.
hitmatch = TRUE;
quit = TRUE;
}
break;
case '+': // break a token on any of these.
case ',':
case ';':
case '=':
case '@':
case '(':
case ')':
if( separator == SEP_SPACE ) break; // NOTE: possible fall through
case '/':
case ' ':
case '\t':
if( !forcematch ) {
quit = TRUE;
}
break;
case '.':
case ':':
if( !forcematch && !include_fn ) {
quit = TRUE;
}
break;
case '\0':
case '\r':
case '\n':
quit = TRUE;
break;
}
}
CmdFile->len = len;
if( forcematch && !hitmatch ) {
return( FALSE );
}
return( TRUE );
}
extern bool GetNumber( unsigned long * pnt )
/******************************************/
{
char * p;
int len;
unsigned long value;
unsigned radix;
bool isvalid;
bool isdig;
char ch;
p = CmdFile->token;
len = CmdFile->len;
value = 0ul;
radix = 10;
if( *p == '0' ) {
--len;
radix = 8;
if( tolower(*++p) == 'x') {
radix = 16;
++p;
--len;
}
}
for( ; len != 0; --len ) {
ch = tolower( *p++ );
if( ch == 'k' ) { // constant of the form 64k
if( len > 1 ) {
return( FALSE );
} else {
value <<= 10; // value = value * 1024;
}
} else {
isdig = isdigit( ch );
if( radix == 10 ) {
isvalid = isdig;
} else if( radix == 8 ) {
if( ch == '8' || ch == '9' || !isdig ) {
isvalid = FALSE;
} else {
isvalid = TRUE;
}
} else {
isvalid = isxdigit( ch );
}
if( !isvalid ) {
return( FALSE );
}
value *= radix;
if( isdig ) {
value += ch - '0';
} else {
value += ch - 'a' + 10;
}
}
}
*pnt = value;
return( TRUE );
}
extern char * ToString( void )
/****************************/
{
char * src;
int len;
char * str;
src = CmdFile->token;
len = CmdFile->len;
str = MemAlloc( len + 1 );
memcpy( str, src, len );
str[ len ] = '\0';
return( str );
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?