Author: dergachev Date: Fri Apr 5 14:48:52 2019 New Revision: 357823 URL: http://llvm.org/viewvc/llvm-project?rev=357823&view=rev Log: [Lexer] NFC: Fix an off-by-one bug in getAsCharRange().
As the unit test demonstrates, subtracting 1 from the offset was unnecessary. The only user of this function was the plist file emitter (in Static Analyzer and ARCMigrator). It means that a lot of Static Analyzer's plist arrows are in fact off by one character. The patch carefully preserves this completely incorrect behavior and causes no functional change, i.e. no plist format breakage. Differential Revision: https://reviews.llvm.org/D59977 Modified: cfe/trunk/include/clang/Basic/PlistSupport.h cfe/trunk/include/clang/Lex/Lexer.h cfe/trunk/unittests/Lex/LexerTest.cpp Modified: cfe/trunk/include/clang/Basic/PlistSupport.h URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/PlistSupport.h?rev=357823&r1=357822&r2=357823&view=diff ============================================================================== --- cfe/trunk/include/clang/Basic/PlistSupport.h (original) +++ cfe/trunk/include/clang/Basic/PlistSupport.h Fri Apr 5 14:48:52 2019 @@ -127,7 +127,11 @@ inline void EmitRange(raw_ostream &o, co assert(R.isCharRange() && "cannot handle a token range"); Indent(o, indent) << "<array>\n"; EmitLocation(o, SM, R.getBegin(), FM, indent + 1); - EmitLocation(o, SM, R.getEnd(), FM, indent + 1); + + // The ".getLocWithOffset(-1)" emulates the behavior of an off-by-one bug + // in Lexer that is already fixed. It is here for backwards compatibility + // even though it is incorrect. + EmitLocation(o, SM, R.getEnd().getLocWithOffset(-1), FM, indent + 1); Indent(o, indent) << "</array>\n"; } Modified: cfe/trunk/include/clang/Lex/Lexer.h URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Lex/Lexer.h?rev=357823&r1=357822&r2=357823&view=diff ============================================================================== --- cfe/trunk/include/clang/Lex/Lexer.h (original) +++ cfe/trunk/include/clang/Lex/Lexer.h Fri Apr 5 14:48:52 2019 @@ -382,7 +382,7 @@ public: SourceLocation End = getLocForEndOfToken(Range.getEnd(), 0, SM, LangOpts); return End.isInvalid() ? CharSourceRange() : CharSourceRange::getCharRange( - Range.getBegin(), End.getLocWithOffset(-1)); + Range.getBegin(), End); } static CharSourceRange getAsCharRange(CharSourceRange Range, const SourceManager &SM, Modified: cfe/trunk/unittests/Lex/LexerTest.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/unittests/Lex/LexerTest.cpp?rev=357823&r1=357822&r2=357823&view=diff ============================================================================== --- cfe/trunk/unittests/Lex/LexerTest.cpp (original) +++ cfe/trunk/unittests/Lex/LexerTest.cpp Fri Apr 5 14:48:52 2019 @@ -513,4 +513,23 @@ TEST_F(LexerTest, StringizingRasString) EXPECT_EQ(String6, R"(a\\\n\n\n \\\\b)"); } +TEST_F(LexerTest, CharRangeOffByOne) { + std::vector<Token> toks = Lex(R"(#define MOO 1 + void foo() { MOO; })"); + const Token &moo = toks[5]; + + EXPECT_EQ(getSourceText(moo, moo), "MOO"); + + SourceRange R{moo.getLocation(), moo.getLocation()}; + + EXPECT_TRUE( + Lexer::isAtStartOfMacroExpansion(R.getBegin(), SourceMgr, LangOpts)); + EXPECT_TRUE( + Lexer::isAtEndOfMacroExpansion(R.getEnd(), SourceMgr, LangOpts)); + + CharSourceRange CR = Lexer::getAsCharRange(R, SourceMgr, LangOpts); + + EXPECT_EQ(Lexer::getSourceText(CR, SourceMgr, LangOpts), "MOO"); // Was "MO". +} + } // anonymous namespace _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits