blob: 4e975d9f4865a5917ffcb837dabd6077ef1c6069 [file] [log] [blame]
Ted Kremenek274b2082008-11-12 21:37:15 +00001//===--- PTHLexer.cpp - Lex from a token stream ---------------------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// This file implements the PTHLexer interface.
11//
12//===----------------------------------------------------------------------===//
13
14#include "clang/Lex/PTHLexer.h"
15#include "clang/Lex/Preprocessor.h"
Ted Kremenek274b2082008-11-12 21:37:15 +000016#include "clang/Basic/TokenKinds.h"
Ted Kremenek274b2082008-11-12 21:37:15 +000017using namespace clang;
18
19PTHLexer::PTHLexer(Preprocessor& pp, SourceLocation fileloc,
Ted Kremenek452e3782008-11-20 01:29:45 +000020 const Token *TokArray, unsigned NumTokens)
21 : PreprocessorLexer(&pp, fileloc),
22 Tokens(TokArray),
23 LastToken(NumTokens - 1),
24 CurToken(0) {
Ted Kremenek274b2082008-11-12 21:37:15 +000025
Ted Kremenekd6f53dc2008-11-20 07:58:05 +000026 assert(NumTokens >= 1);
27 assert(Tokens[LastToken].is(tok::eof));
Ted Kremenek274b2082008-11-12 21:37:15 +000028}
29
30void PTHLexer::Lex(Token& Tok) {
Ted Kremenekd6f53dc2008-11-20 07:58:05 +000031LexNextToken:
32 if (CurToken == LastToken) {
33 if (ParsingPreprocessorDirective) {
Ted Kremenek274b2082008-11-12 21:37:15 +000034 ParsingPreprocessorDirective = false;
Ted Kremenekd6f53dc2008-11-20 07:58:05 +000035 Tok = Tokens[LastToken];
36 Tok.setKind(tok::eom);
37 MIOpt.ReadToken();
38 return;
Ted Kremenek274b2082008-11-12 21:37:15 +000039 }
Ted Kremenek274b2082008-11-12 21:37:15 +000040
Ted Kremenekd6f53dc2008-11-20 07:58:05 +000041 assert(!LexingRawMode && "PTHLexer cannot lex in raw mode.");
42
43 // FIXME: Issue diagnostics similar to Lexer.
44 PP->HandleEndOfFile(Tok, false);
Ted Kremenek274b2082008-11-12 21:37:15 +000045 return;
46 }
47
48 Tok = Tokens[CurToken];
49
Ted Kremenekd6f53dc2008-11-20 07:58:05 +000050 // Don't advance to the next token yet. Check if we are at the
51 // start of a new line and we're processing a directive. If so, we
52 // consume this token twice, once as an tok::eom.
53 if (Tok.isAtStartOfLine() && ParsingPreprocessorDirective) {
54 ParsingPreprocessorDirective = false;
55 Tok.setKind(tok::eom);
Ted Kremenek274b2082008-11-12 21:37:15 +000056 MIOpt.ReadToken();
Ted Kremenek274b2082008-11-12 21:37:15 +000057 return;
58 }
Ted Kremenekd6f53dc2008-11-20 07:58:05 +000059
60 // Advance to the next token.
61 ++CurToken;
Ted Kremenek274b2082008-11-12 21:37:15 +000062
Ted Kremenekd6f53dc2008-11-20 07:58:05 +000063 if (Tok.is(tok::hash)) {
64 if (Tok.isAtStartOfLine() && !LexingRawMode) {
65 PP->HandleDirective(Tok);
66
67 if (PP->isCurrentLexer(this))
68 goto LexNextToken;
69
70 return PP->Lex(Tok);
71 }
72 }
73
Ted Kremenek274b2082008-11-12 21:37:15 +000074 MIOpt.ReadToken();
Ted Kremenekd6f53dc2008-11-20 07:58:05 +000075
76 if (Tok.is(tok::identifier)) {
77 if (LexingRawMode) return;
78 return PP->HandleIdentifier(Tok);
79 }
Ted Kremenek274b2082008-11-12 21:37:15 +000080}
81
82void PTHLexer::setEOF(Token& Tok) {
Ted Kremenek452e3782008-11-20 01:29:45 +000083 Tok = Tokens[LastToken];
Ted Kremenek274b2082008-11-12 21:37:15 +000084}
Ted Kremenek17ff58a2008-11-19 22:21:33 +000085
86void PTHLexer::DiscardToEndOfLine() {
87 assert(ParsingPreprocessorDirective && ParsingFilename == false &&
88 "Must be in a preprocessing directive!");
Ted Kremenek4d35da22008-11-20 01:16:50 +000089
90 // Already at end-of-file?
Ted Kremenek452e3782008-11-20 01:29:45 +000091 if (CurToken == LastToken)
Ted Kremenek4d35da22008-11-20 01:16:50 +000092 return;
93
94 // Find the first token that is not the start of the *current* line.
Ted Kremenek452e3782008-11-20 01:29:45 +000095 for ( ++CurToken; CurToken != LastToken ; ++CurToken )
Ted Kremenek4d35da22008-11-20 01:16:50 +000096 if (Tokens[CurToken].isAtStartOfLine())
97 return;
Ted Kremenek17ff58a2008-11-19 22:21:33 +000098}
Ted Kremenek2f1c0242008-11-19 22:42:26 +000099
Ted Kremenek4d35da22008-11-20 01:16:50 +0000100unsigned PTHLexer::isNextPPTokenLParen() {
Ted Kremenek452e3782008-11-20 01:29:45 +0000101 if (CurToken == LastToken)
Ted Kremenek4d35da22008-11-20 01:16:50 +0000102 return 2;
103
104 return Tokens[CurToken].is(tok::l_paren);
Ted Kremenek2f1c0242008-11-19 22:42:26 +0000105}
106