[cfe-commits] r38561 - in /cfe/cfe/trunk: Driver/clang.cpp Lex/Preprocessor.cpp include/clang/Lex/Preprocessor.h
sabre at cs.uiuc.edu
sabre at cs.uiuc.edu
Wed Jul 11 09:22:40 PDT 2007
Author: sabre
Date: Wed Jul 11 11:22:39 2007
New Revision: 38561
URL: http://llvm.org/viewvc/llvm-project?rev=38561&view=rev
Log:
Improve #line emission in -E mode to include file entry/exits. This is
still pretty hacky because it doesn't compute the 3/4 markers correctly.
Modified:
cfe/cfe/trunk/Driver/clang.cpp
cfe/cfe/trunk/Lex/Preprocessor.cpp
cfe/cfe/trunk/include/clang/Lex/Preprocessor.h
Modified: cfe/cfe/trunk/Driver/clang.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/Driver/clang.cpp?rev=38561&r1=38560&r2=38561&view=diff
==============================================================================
--- cfe/cfe/trunk/Driver/clang.cpp (original)
+++ cfe/cfe/trunk/Driver/clang.cpp Wed Jul 11 11:22:39 2007
@@ -588,24 +588,76 @@
// Preprocessed output mode.
//===----------------------------------------------------------------------===//
+static unsigned EModeCurLine;
+static std::string EModeCurFilename;
+static Preprocessor *EModePP;
+static bool EmodeEmittedTokensOnThisLine;
+
+static void MoveToLine(unsigned LineNo) {
+ // If this line is "close enough" to the original line, just print newlines,
+ // otherwise print a #line directive.
+ if (LineNo-EModeCurLine < 8) {
+ for (; EModeCurLine != LineNo; ++EModeCurLine)
+ std::cout << "\n";
+ } else {
+ if (EmodeEmittedTokensOnThisLine) {
+ std::cout << "\n";
+ EmodeEmittedTokensOnThisLine = false;
+ }
+
+ std::cout << "# " << LineNo << " " << EModeCurFilename;
+
+ // FIXME: calculate system file right.
+ std::cout << " 3";
+
+ std::cout << "\n";
+ EModeCurLine = LineNo;
+ }
+}
+
+/// HandleFileChange - Whenever the preprocessor enters or exits a #include file
+/// it invokes this handler. Update our conception of the current
+static void HandleFileChange(SourceLocation Loc, bool EnteringFile) {
+ SourceManager &SourceMgr = EModePP->getSourceManager();
+
+ // If we are entering a new #include, make sure to skip ahead to the line the
+ // #include directive was at.
+ if (EnteringFile) {
+ SourceLocation IncludeLoc = SourceMgr.getIncludeLoc(Loc.getFileID());
+ MoveToLine(SourceMgr.getLineNumber(IncludeLoc));
+ }
+
+ EModeCurLine = SourceMgr.getLineNumber(Loc);
+ // FIXME: escape filename right.
+ EModeCurFilename = '"' + SourceMgr.getSourceName(Loc) + '"';
+
+ if (EmodeEmittedTokensOnThisLine) {
+ std::cout << "\n";
+ EmodeEmittedTokensOnThisLine = false;
+ }
+ std::cout << "# " << EModeCurLine << " " << EModeCurFilename;
+ if (EnteringFile)
+ std::cout << " 1";
+ else
+ std::cout << " 2";
+
+ // FIXME: calculate system file right.
+ std::cout << " 3";
+
+ std::cout << "\n";
+}
+
+
/// HandleFirstTokOnLine - When emitting a preprocessed file in -E mode, this
/// is called for the first token on each new line.
-static void HandleFirstTokOnLine(LexerToken &Tok, Preprocessor &PP,
- unsigned &CurLine) {
+static void HandleFirstTokOnLine(LexerToken &Tok, Preprocessor &PP) {
// Figure out what line we went to and insert the appropriate number of
// newline characters.
unsigned LineNo = PP.getSourceManager().getLineNumber(Tok.getLocation());
- // If this line is "close enough" to the original line, just print newlines,
- // otherwise print a #line directive.
- if (LineNo-CurLine < 8) {
- for (; CurLine != LineNo; ++CurLine)
- std::cout << "\n";
- } else {
- // FIXME: filename too.
- std::cout << "\n# " << LineNo << "\n";
- CurLine = LineNo;
- }
+ // Move to the specified line.
+ MoveToLine(LineNo);
+
// Print out space characters so that the first token on a line is
// indented for easy reading.
@@ -630,7 +682,12 @@
void DoPrintPreprocessedInput(Preprocessor &PP) {
LexerToken Tok;
char Buffer[256];
- unsigned CurLine = 1;
+ EModeCurLine = 0;
+ EModeCurFilename = "\"<uninit>\"";
+ PP.setFileChangeHandler(HandleFileChange);
+ EModePP = &PP;
+ EmodeEmittedTokensOnThisLine = false;
+
do {
PP.Lex(Tok);
@@ -640,7 +697,7 @@
// FIXME: For some tests, this fails just because there is no col# info from
// macro expansions!
if (Tok.isAtStartOfLine()) {
- HandleFirstTokOnLine(Tok, PP, CurLine);
+ HandleFirstTokOnLine(Tok, PP);
} else if (Tok.hasLeadingSpace()) {
std::cout << ' ';
}
@@ -652,6 +709,7 @@
} else {
std::cout << PP.getSpelling(Tok);
}
+ EmodeEmittedTokensOnThisLine = true;
} while (Tok.getKind() != tok::eof);
std::cout << "\n";
}
Modified: cfe/cfe/trunk/Lex/Preprocessor.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/Lex/Preprocessor.cpp?rev=38561&r1=38560&r2=38561&view=diff
==============================================================================
--- cfe/cfe/trunk/Lex/Preprocessor.cpp (original)
+++ cfe/cfe/trunk/Lex/Preprocessor.cpp Wed Jul 11 11:22:39 2007
@@ -55,10 +55,13 @@
NumEnteredSourceFiles = NumMacroExpanded = NumFastMacroExpanded = 0;
MaxIncludeStackDepth = MaxMacroStackDepth = 0;
NumSkipped = 0;
-
+
// Macro expansion is enabled.
DisableMacroExpansion = false;
SkippingContents = false;
+
+ // There is no file-change handler yet.
+ FileChangeHandler = 0;
}
Preprocessor::~Preprocessor() {
@@ -342,6 +345,10 @@
CurLexer = new Lexer(Buffer, FileID, *this);
CurNextDirLookup = NextDir;
+
+ // Notify the client, if desired, that we are in a new source file.
+ if (FileChangeHandler)
+ FileChangeHandler(CurLexer->getSourceLocation(CurLexer->BufferStart), true);
}
/// EnterMacro - Add a Macro to the top of the include stack and start lexing
@@ -464,7 +471,7 @@
/// HandleEndOfFile - This callback is invoked when the lexer hits the end of
/// the current file. This either returns the EOF token or pops a level off
/// the include stack and keeps going.
-void Preprocessor::HandleEndOfFile(LexerToken &Result) {
+void Preprocessor::HandleEndOfFile(LexerToken &Result, bool isEndOfMacro) {
assert(!CurMacroExpander &&
"Ending a file when currently in a macro!");
@@ -488,6 +495,12 @@
CurLexer = IncludeStack.back().TheLexer;
CurNextDirLookup = IncludeStack.back().TheDirLookup;
IncludeStack.pop_back();
+
+ // Notify the client, if desired, that we are in a new source file.
+ if (FileChangeHandler && !isEndOfMacro)
+ FileChangeHandler(CurLexer->getSourceLocation(CurLexer->BufferPtr),
+ false);
+
return Lex(Result);
}
@@ -519,7 +532,7 @@
} else {
CurMacroExpander = 0;
// Handle this like a #include file being popped off the stack.
- return HandleEndOfFile(Result);
+ return HandleEndOfFile(Result, true);
}
}
Modified: cfe/cfe/trunk/include/clang/Lex/Preprocessor.h
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/include/clang/Lex/Preprocessor.h?rev=38561&r1=38560&r2=38561&view=diff
==============================================================================
--- cfe/cfe/trunk/include/clang/Lex/Preprocessor.h (original)
+++ cfe/cfe/trunk/include/clang/Lex/Preprocessor.h Wed Jul 11 11:22:39 2007
@@ -87,6 +87,13 @@
std::vector<DirectoryLookup> SearchDirs;
unsigned SystemDirIdx;
bool NoCurDirSearch;
+
+ /// FileChangeHandler - This callback is invoked whenever a source file is
+ /// entered or exited. The SourceLocation indicates the new location, and
+ /// EnteringFile indicates whether this is because we are entering a new
+ /// #include'd file (when true) or whether we're exiting one because we ran
+ /// off the end (when false).
+ void (*FileChangeHandler)(SourceLocation Loc, bool EnteringFile);
enum {
/// MaxIncludeStackDepth - Maximum depth of #includes.
@@ -103,7 +110,6 @@
/// CurLexer - This is the current top of the stack that we're lexing from if
/// not expanding a macro. One of CurLexer and CurMacroExpander must be null.
- ///
Lexer *CurLexer;
/// CurDirLookup - The next DirectoryLookup structure to search for a file if
@@ -185,6 +191,16 @@
NoCurDirSearch = noCurDirSearch;
}
+ /// setFileChangeHandler - Set the callback invoked whenever a source file is
+ /// entered or exited. The SourceLocation indicates the new location, and
+ /// EnteringFile indicates whether this is because we are entering a new
+ /// #include'd file (when true) or whether we're exiting one because we ran
+ /// off the end (when false).
+ void setFileChangeHandler(void (*Handler)(SourceLocation, bool)) {
+ FileChangeHandler = Handler;
+ }
+
+
/// getIdentifierInfo - Return information about the specified preprocessor
/// identifier token. The version of this method that takes two character
/// pointers is preferred unless the identifier is already available as a
@@ -302,7 +318,7 @@
/// HandleEndOfFile - This callback is invoked when the lexer hits the end of
/// the current file. This either returns the EOF token or pops a level off
/// the include stack and keeps going.
- void HandleEndOfFile(LexerToken &Result);
+ void HandleEndOfFile(LexerToken &Result, bool isEndOfMacro = false);
/// HandleEndOfMacro - This callback is invoked when the lexer hits the end of
/// the current macro line.
More information about the cfe-commits
mailing list