implement .include in the lexer/parser instead of passing it into the streamer.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@75896 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/tools/llvm-mc/AsmLexer.cpp b/tools/llvm-mc/AsmLexer.cpp
index 7b744fb..6ee9145 100644
--- a/tools/llvm-mc/AsmLexer.cpp
+++ b/tools/llvm-mc/AsmLexer.cpp
@@ -54,6 +54,21 @@
return asmtok::Error;
}
+/// EnterIncludeFile - Enter the specified file. This prints an error and
+/// returns true on failure.
+bool AsmLexer::EnterIncludeFile(const std::string &Filename) {
+ int NewBuf = SrcMgr.AddIncludeFile(Filename, SMLoc::getFromPointer(CurPtr));
+ if (NewBuf == -1)
+ return true;
+
+ // Save the line number and lex buffer of the includer.
+ CurBuffer = NewBuf;
+ CurBuf = SrcMgr.getMemoryBuffer(CurBuffer);
+ CurPtr = CurBuf->getBufferStart();
+ return false;
+}
+
+
int AsmLexer::getNextChar() {
char CurChar = *CurPtr++;
switch (CurChar) {
@@ -72,6 +87,10 @@
CurBuffer = SrcMgr.FindBufferContainingLoc(ParentIncludeLoc);
CurBuf = SrcMgr.getMemoryBuffer(CurBuffer);
CurPtr = ParentIncludeLoc.getPointer();
+
+ // Reset the token start pointer to the start of the new file.
+ TokStart = CurPtr;
+
return getNextChar();
}
diff --git a/tools/llvm-mc/AsmLexer.h b/tools/llvm-mc/AsmLexer.h
index 6360b12..5d59d0a 100644
--- a/tools/llvm-mc/AsmLexer.h
+++ b/tools/llvm-mc/AsmLexer.h
@@ -97,6 +97,9 @@
SMLoc getLoc() const;
+ /// EnterIncludeFile - Enter the specified file. This returns true on failure.
+ bool EnterIncludeFile(const std::string &Filename);
+
void PrintMessage(SMLoc Loc, const std::string &Msg, const char *Type) const;
private:
diff --git a/tools/llvm-mc/AsmParser.cpp b/tools/llvm-mc/AsmParser.cpp
index cb21a93..68eb9d5 100644
--- a/tools/llvm-mc/AsmParser.cpp
+++ b/tools/llvm-mc/AsmParser.cpp
@@ -1168,21 +1168,27 @@
/// ParseDirectiveInclude
/// ::= .include "filename"
bool AsmParser::ParseDirectiveInclude() {
- const char *Str;
-
if (Lexer.isNot(asmtok::String))
return TokError("expected string in '.include' directive");
- Str = Lexer.getCurStrVal();
-
+ std::string Filename = Lexer.getCurStrVal();
+ SMLoc IncludeLoc = Lexer.getLoc();
Lexer.Lex();
if (Lexer.isNot(asmtok::EndOfStatement))
return TokError("unexpected token in '.include' directive");
- Lexer.Lex();
-
- Out.SwitchInputAssemblyFile(Str);
+ // Strip the quotes.
+ Filename = Filename.substr(1, Filename.size()-2);
+
+ // Attempt to switch the lexer to the included file before consuming the end
+ // of statement to avoid losing it when we switch.
+ if (Lexer.EnterIncludeFile(Filename)) {
+ Lexer.PrintMessage(IncludeLoc,
+ "Could not find include file '" + Filename + "'",
+ "error");
+ return true;
+ }
return false;
}