void ParseSymbols() { StartToken(); switch (Previous()) { case '/': if (Current() == '/') { ParseLineComment(); break; } else if (Current() == '*') { ParseBlockComment(); break; } // Yes. No break. This is deliberate. default: { String4 tinySource = {}; tinySource.Append(Previous()); lastSourceToken.tokenType = TokenType::Reserved; lastSourceToken.tokenIndex = FindOperator(tinySource); for (int i = index; i < length && IsSymbol(source[i]); ++i) { tinySource.Append(source[i]); auto tokenIndex = FindOperator(tinySource); if (tokenIndex != -1) { lastSourceToken.tokenIndex = tokenIndex; lastSourceToken.length = i - index + 2; } } int offset = lastSourceToken.length - 1; index += offset; position.column += offset; break; } } }
char* Preprocessor::ParseLexem( char* start, char* end, Lexem& out ) { if( start == end ) return start; char current_char = *start; if( IsTrivial( current_char ) ) { out.Value += current_char; out.Type = TrivialTypes[Trivials.find_first_of( current_char )]; return ++start; } if( IsIdentifierStart( current_char ) ) return ParseIdentifier( start, end, out ); if( current_char == '#' ) { out.Value = "#"; ++start; if( *start == '#' ) { out.Value = "##"; out.Type = Lexem::IGNORE; return ( ++start ); } while( start != end && ( *start == ' ' || *start == '\t' ) ) ++start; if( start != end && IsIdentifierStart( *start ) ) start = ParseIdentifier( start, end, out ); out.Type = Lexem::PREPROCESSOR; return start; } if( IsNumber( current_char ) ) return ParseNumber( start, end, out ); if( current_char == '\"' ) return ParseStringLiteral( start, end, '\"', out ); if( current_char == '\'' ) return ParseStringLiteral( start, end, '\'', out ); // Todo: set optional ParseCharacterLiteral? if( current_char == '/' ) { // Need to see if it's a comment. ++start; if( start == end ) return start; if( *start == '*' ) return ParseBlockComment( start, end, out ); if( *start == '/' ) return ParseLineComment( start, end, out ); // Not a comment - let default code catch it as MISC --start; } if( current_char == '\\' ) { out.Type = Lexem::BACKSLASH; return ++start; } out.Value = std::string( 1, current_char ); out.Type = Lexem::IGNORE; return ++start; }