⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 cscan.c

📁 Open Watcom 的 C 编译器源代码
💻 C
📖 第 1 页 / 共 4 页
字号:
    if( token == T_BAD_TOKEN ) {
        BadTokenInfo = ERR_INV_CHAR_CONSTANT;
    } else {
        NextChar();
        if( error != 0 ) {                      /* 16-nov-94 */
            BadTokenInfo = ERR_INVALID_HEX_CONSTANT;
            token = T_BAD_TOKEN;
        }
    }
    Buffer[TokenLen] = '\0';
    ConstType = char_type;
    if( CompFlags.signed_char ) {
        if( (value & 0xFFFFFF80) == 0x80 ) {    /* if sign bit is on */
            value |= 0xFFFFFF00;                /* - sign extend it */
        }
    }
    Constant = value;
    return( token );
}

int ScanCharConst()
{
    Buffer[0] = '\'';
    TokenLen = 1;
    return( CharConst( TYPE_CHAR ) );
}

static int ScanString( void )
{
    int         c;
    int         ok;
    char        error;
    ok = 0;
    error = 0;
    CompFlags.wide_char_string = 0;
    CompFlags.trigraph_alert = 0;
    c = NextChar();
    Buffer[0] = c;
    TokenLen = 1;
    for( ;; ) {
        if( c == '\n' ){
            TokenLine = SrcFileLineNum-1; /* place error at site */
            if( NestLevel == SkipLevel ) {  /* 10-sep-92 */
                CErr1( ERR_MISSING_LINE_CONTINUE );
            }else{
                CWarn1( WARN_CONSTANT_TOO_BIG, ERR_MISSING_LINE_CONTINUE  );
            }
        }
        if( c == EOF_CHAR ) break;
        if( c == '"' ) {
            NextChar();
            ok = 1;
            break;
        }

        if( c == '\\' ) {               /* 23-mar-90 */
            if( TokenLen > BufSize - 32 ) {
                EnlargeBuffer( TokenLen * 2 );
            }
            c = NextChar();
            Buffer[TokenLen++] = c;
            if( (CharSet[c] & C_WS) == 0 ) {    /* 04-nov-88 */
                ESCChar( c, NULL, &error );
            }
            c = CurrChar;
        } else {
            /* if first character of a double-byte character, then
               save it and get the next one.    10-nov-89  */
            if( CharSet[c] & C_DB ) SaveNextChar();
            if( TokenLen > BufSize - 32 ) {
                EnlargeBuffer( TokenLen * 2 );
            }
            c = NextChar();
            Buffer[TokenLen++] = c;
        }
    }
    Buffer[TokenLen-1] = '\0';
    CLitLength = TokenLen;
    if( CompFlags.trigraph_alert ){
        CWarn1( WARN_LEVEL_1, ERR_EXPANDED_TRIGRAPH );
    }
    if( ok ) return( T_STRING );
    --TokenLen;         /* '\n' or EOF_CHAR don't print nicely */
    Buffer[TokenLen-1] = '\0';
    BadTokenInfo = ERR_MISSING_QUOTE;
    return( T_BAD_TOKEN );
}

int ESCChar( int c, const char **pbuf, char *error )
{
    int n, i;

    if( c >= '0'  &&  c <= '7' ) {          /* get octal escape sequence */
        n = 0;
        i = 3;
        while( c >= '0'  &&  c <= '7' ) {
            n = n * 8 + c - '0';
            if( pbuf == NULL ) {
                c = SaveNextChar();
            } else {
                c = *++*pbuf;
            }
            --i;
            if( i == 0 ) break;
        }
    } else if( c == 'x' ) {         /* get hex escape sequence */
        if( ScanHex( 127, pbuf ) ) {
            n = Constant;
        } else {                        /*  '\xz' where z is not a hex char */
            *error = 1;
            n = 'x';
        }
    } else {
        switch( c ) {
        case 'a':
            c = ESCAPE_a;
            break;
        case 'b':
            c = ESCAPE_b;
            break;
        case 'f':
            c = ESCAPE_f;
            break;
        case 'n':
            c = ESCAPE_n;
            break;
        case 'r':
            c = ESCAPE_r;
            break;
        case 't':
            c = ESCAPE_t;
            break;
        case 'v':
            c = ESCAPE_v;
            break;
#if _OS == _QNX
        case 'l':
            /* for lazy QNX programmers */
            if( CompFlags.extensions_enabled ) {
                c = ESCAPE_n;
            }
            break;
#endif
        }
        _ASCIIOUT( c );
        n = c;
        if( pbuf == NULL ) {
            SaveNextChar();
        } else {
            ++*pbuf;
        }
    }
    return( n );
}

int ScanWhiteSpace()
{
    char        *scanptr;
    union {
    int         c;
    unsigned char uc;
    } u;

    if( NextChar == getCharAfterBackSlash ) {
        for(;;) {
            u.c = NextChar();
            if( (CharSet[u.c] & C_WS) == 0 ) break;
        }
    } else {
        u.c = 0;
        for(;;) {
            scanptr = ScanCharPtr;
            for(;;) {
                u.uc = *scanptr++;
                if( (CharSet[u.c] & C_WS) == 0 ) break;
                u.uc = *scanptr++;
                if( (CharSet[u.c] & C_WS) == 0 ) break;
                u.uc = *scanptr++;
                if( (CharSet[u.c] & C_WS) == 0 ) break;
                u.uc = *scanptr++;
                if( (CharSet[u.c] & C_WS) == 0 ) break;
                u.uc = *scanptr++;
                if( (CharSet[u.c] & C_WS) == 0 ) break;
                u.uc = *scanptr++;
                if( (CharSet[u.c] & C_WS) == 0 ) break;
                u.uc = *scanptr++;
                if( (CharSet[u.c] & C_WS) == 0 ) break;
                u.uc = *scanptr++;
                if( (CharSet[u.c] & C_WS) == 0 ) break;
            }
            ScanCharPtr = scanptr;
            if( (CharSet[u.c] & C_EX) == 0 ) break;
            u.c = GetCharCheck( u.c );
            if( (CharSet[u.c] & C_WS) == 0 ) break;
        }
        CurrChar = u.c;
    }
    return( T_WHITE_SPACE );
}

static void SkipWhiteSpace( int c )
{
    if( !CompFlags.cpp_output ) {
        ScanWhiteSpace();
    } else {
        for(;;) {
            if( (CharSet[c] & C_WS) == 0 ) break;
            if( c != '\r' ) {
                if( !CompFlags.pre_processing )  PrtChar( c );
            }
            c = NextChar();
        }
    }
}


void SkipAhead()
{
    for(;;) {
        for(;;) {
            if( CharSet[CurrChar] & C_WS ) {
                SkipWhiteSpace( CurrChar );
            }
            if( CurrChar != '\n' ) break;
            if( CompFlags.cpp_output ) {
                if( !CompFlags.pre_processing )  PrtChar( '\n' );
            }
            NextChar();
        }
        if( CurrChar != '/' )  break;
        NextChar();
        if( CurrChar == '*' ) {
            ScanComment();
        } else {
            UnGetChar( CurrChar );
            CurrChar = '/';
            break;
        }
    }
}

int ScanNewline()
{
    if( CompFlags.pre_processing ) return( T_NULL );
    return( ChkControl() );
}

int ScanCarriageReturn()
{
    int         c;

    c = NextChar();
    if( c == '\n' ) {
        if( CompFlags.pre_processing ) return( T_NULL );
        return( ChkControl() );
    }
    return( ScanWhiteSpace() );
}

#if defined(__DOS__) || defined(__OS2__) || defined(__NT__) || defined(__OSI__)
    #define     SYS_EOF_CHAR 0x1A
#elif defined(__QNX__) || defined(__LINUX__)
    #undef      SYS_EOF_CHAR
#else
    #error System end of file character not configured.
#endif

int ScanInvalid()
{
    Buffer[0] = CurrChar;
    Buffer[1] = '\0';
#ifdef SYS_EOF_CHAR
    if( Buffer[0] == SYS_EOF_CHAR ) {
        CloseSrcFile( SrcFile );                /* 13-sep-94 */
        return( T_WHITE_SPACE );
    }
#endif
    NextChar();
    return( T_BAD_CHAR );
}

int ScanMacroToken()
{
    GetMacroToken();
    if( CurToken == T_NULL ) {
        if( CompFlags.cpp_output ) {
            PrtChar( ' ' );
        }
        CurrChar = SavedCurrChar;
        CurToken = ScanToken();
    }
    return( CurToken );
}

int ScanEof()
{
    return( T_EOF );
}

int (*ScanFunc[])() = {
    ScanName,
    ScanWide,
    ScanNum,
    ScanQuestionMark,
    ScanSlash,
    ScanMinus,
    ScanEqual,
    ScanColon,
    ScanStar,
    ScanDelim1,
    ScanDelim2,
    ScanDot,
    ScanString,
    ScanCharConst,
    ScanCarriageReturn,
    ScanNewline,
    ScanWhiteSpace,
    ScanInvalid,
    ScanMacroToken,
    ScanEof
};

int ScanToken()
{
    TokenLine = SrcFileLineNum;         /* remember line token starts on */
//    TokenLen = 1;
//    Buffer[0] = CurrChar;
    return( (*ScanFunc[ClassTable[CurrChar]])() );
}

int NextToken()
{
    do {
        CurToken = T_NULL;
        if( MacroPtr != NULL ) {
            GetMacroToken();
        }
        if( CurToken == T_NULL ) {
//          CurToken = ScanToken();
            TokenLine = SrcFileLineNum;
//          TokenLen = 1;
//          Buffer[0] = CurrChar;
            CurToken = (*ScanFunc[ClassTable[CurrChar]])();
        }
    } while( CurToken == T_WHITE_SPACE );
    #ifdef FDEBUG
        DumpToken();
    #endif
    return( CurToken );
}

int PPNextToken()                       // called from macro pre-processor
{
    do {
        if( MacroPtr != NULL ) {
            GetMacroToken();
            if( CurToken == T_NULL ) {
                if( CompFlags.cpp_output ) {
                    PrtChar( ' ' );
                }
                CurToken = ScanToken();
            }
        } else {
            CurToken = ScanToken();
        }
    } while( CurToken == T_WHITE_SPACE );
    return( CurToken );
}

int ReScanToken()
{
    int         saved_currchar;
    char        *saved_ScanCharPtr;
    int         (*saved_nextchar)();

    saved_currchar = CurrChar;
    saved_nextchar = NextChar;
    saved_ScanCharPtr = ScanCharPtr;
    ScanCharPtr = ReScanPtr;
    CompFlags.rescan_buffer_done = 0;
    NextChar = ReScanBuffer;
    CurrChar = ReScanBuffer();
    CompFlags.doing_macro_expansion = 1;        // return macros as ID's
    CurToken = ScanToken();
    CompFlags.doing_macro_expansion = 0;
    if( CurToken == T_STRING  &&  CompFlags.wide_char_string ) {
        CurToken = T_LSTRING;                   /* 12-nov-92 */
    }
    --ScanCharPtr;
    ReScanPtr = ScanCharPtr;
    ScanCharPtr = saved_ScanCharPtr;
    CurrChar = saved_currchar;
    NextChar = saved_nextchar;
    if( CompFlags.rescan_buffer_done == 0 ) {
        return( 1 );
    }
    return( 0 );
}

static void UnGetChar( int c )
{
    if( NextChar == ReScanBuffer ) {            /* 29-feb-92 */
        --ScanCharPtr;
        CompFlags.rescan_buffer_done = 0;
    } else {
        GetNextCharUndo( c );
    }
}

void ScanInit()
{
    int         i;
    int         c;

    memset( &ClassTable[0],   SCAN_INVALID, 256 );
    memset( &ClassTable['A'], SCAN_NAME,    26 );
    memset( &ClassTable['a'], SCAN_NAME,    26 );
    memset( &ClassTable['0'], SCAN_NUM,     10 );
    ClassTable[ EOF_CHAR ] = SCAN_EOF;
    ClassTable[ MACRO_CHAR ] = SCAN_MACRO;
    for( i = 0; ; i += 2 ) {
        c = InitClassTable[i];
        if( c == '\0' ) break;
        ClassTable[c] =  InitClassTable[i+1];
    }
    CurrChar = '\n';
    CompFlags.pre_processing = 0;
    CompFlags.scanning_comment = 0;
    SizeOfCount = 0;
    NextChar = GetNextChar;
}

// called by CollectParms() to gather tokens for macro parms
// and CDefine() to gather tokens for macro definition
// example usage:
//      int ppscan_mode;
//      ppscan_mode = InitPPScan();
//      CollectParms();
//      FiniPPScan( ppscan_mode );
int InitPPScan()
{
    if( ScanFunc[ SCAN_NUM ] == ScanNum ) {
        ScanFunc[ SCAN_NUM ] = ScanPPDigit;
        ScanFunc[ SCAN_DOT ] = ScanPPDot;
        return( 1 );            // indicate changed to PP mode
    }
    return( 0 );                // indicate already in PP mode
}

// called when CollectParms() and CDefine() are finished gathering tokens
void FiniPPScan( int ppscan_mode )
{
    if( ppscan_mode == 1 ) {    // if InitPPScan() changed into PP mode
        ScanFunc[ SCAN_NUM ] = ScanNum; // reset back to normal mode
        ScanFunc[ SCAN_DOT ] = ScanDot;
    }
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -