[PATCH] D20858: [clang-format] make header guard identification stricter in header insertion.
Eric Liu via cfe-commits
cfe-commits at lists.llvm.org
Wed Jun 1 05:32:25 PDT 2016
ioeric updated this revision to Diff 59206.
ioeric added a comment.
- Use iterator looping to simplify code.
http://reviews.llvm.org/D20858
Files:
lib/Format/Format.cpp
unittests/Format/CleanupTest.cpp
Index: unittests/Format/CleanupTest.cpp
===================================================================
--- unittests/Format/CleanupTest.cpp
+++ unittests/Format/CleanupTest.cpp
@@ -537,6 +537,34 @@
EXPECT_EQ(Expected, formatAndApply(Code, Replaces));
}
+TEST_F(CleanUpReplacementsTest, DontJustInsertAfterRandomDefine) {
+ std::string Code = "#define X 1";
+ std::string Expected = "#include <vector>\n"
+ "#define X 1";
+ tooling::Replacements Replaces = {createInsertion("#include <vector>")};
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertAfterHeaderGuard) {
+ std::string Code = "#ifndef X_H\n"
+ "#define X_H\n";
+ std::string Expected = "#ifndef X_H\n"
+ "#define X_H\n"
+ "#include <vector>\n";
+ tooling::Replacements Replaces = {createInsertion("#include <vector>")};
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, DontInsertAfterNonMatchedHeaderGuard) {
+ std::string Code = "#ifndef X_H\n"
+ "#define Y_H";
+ std::string Expected = "#include <vector>\n"
+ "#ifndef X_H\n"
+ "#define Y_H";
+ tooling::Replacements Replaces = {createInsertion("#include <vector>")};
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
} // end namespace
} // end namespace format
} // end namespace clang
Index: lib/Format/Format.cpp
===================================================================
--- lib/Format/Format.cpp
+++ lib/Format/Format.cpp
@@ -1469,7 +1469,8 @@
std::inserter(Result, Result.begin()));
llvm::Regex IncludeRegex(IncludeRegexPattern);
- llvm::Regex DefineRegex(R"(^[\t\ ]*#[\t\ ]*define[\t\ ]*[^\\]*$)");
+ llvm::Regex IfNDefRegex(R"(^[\t\ ]*#[\t\ ]*ifndef[\t\ ]*([^\\]*)$)");
+ llvm::Regex DefineRegex(R"(^[\t\ ]*#[\t\ ]*define[\t\ ]*([^\\]*)$)");
SmallVector<StringRef, 4> Matches;
StringRef FileName = Replaces.begin()->getFilePath();
@@ -1487,7 +1488,9 @@
int AfterHeaderGuard = 0;
SmallVector<StringRef, 32> Lines;
Code.split(Lines, '\n');
- for (auto Line : Lines) {
+ for (auto I = Lines.begin(), B = Lines.begin(), E = Lines.end(); I != E;
+ ++I) {
+ StringRef Line = *I;
if (IncludeRegex.match(Line, &Matches)) {
StringRef IncludeName = Matches[2];
int Category = Categories.getIncludePriority(
@@ -1497,9 +1500,13 @@
FirstIncludeOffset = Offset;
}
Offset += Line.size() + 1;
- // FIXME: make header guard matching stricter, e.g. consider #ifndef.
- if (AfterHeaderGuard == 0 && DefineRegex.match(Line))
- AfterHeaderGuard = Offset;
+ if (FirstIncludeOffset < 0 && AfterHeaderGuard == 0 && I != B &&
+ DefineRegex.match(Line, &Matches)) {
+ StringRef DefineName = Matches[1];
+ if (IfNDefRegex.match(*std::prev(I), &Matches) &&
+ DefineName == Matches[1])
+ AfterHeaderGuard = Offset;
+ }
}
// Populate CategoryEndOfssets:
-------------- next part --------------
A non-text attachment was scrubbed...
Name: D20858.59206.patch
Type: text/x-patch
Size: 3073 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/cfe-commits/attachments/20160601/8fb6f228/attachment.bin>
More information about the cfe-commits
mailing list