[clang-tools-extra] r187481 - Fixed path differences when using include/exclude headers

Ariel J. Bernal ariel.j.bernal at intel.com
Tue Jul 30 21:00:28 PDT 2013


Author: ajbernal
Date: Tue Jul 30 23:00:28 2013
New Revision: 187481

URL: http://llvm.org/viewvc/llvm-project?rev=187481&view=rev
Log:
Fixed path differences when using include/exclude headers

Added function for removing relative operators from input paths.

Modified:
    clang-tools-extra/trunk/cpp11-migrate/Core/IncludeExcludeInfo.cpp
    clang-tools-extra/trunk/unittests/cpp11-migrate/IncludeExcludeTest.cpp

Modified: clang-tools-extra/trunk/cpp11-migrate/Core/IncludeExcludeInfo.cpp
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/Core/IncludeExcludeInfo.cpp?rev=187481&r1=187480&r2=187481&view=diff
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/Core/IncludeExcludeInfo.cpp (original)
+++ clang-tools-extra/trunk/cpp11-migrate/Core/IncludeExcludeInfo.cpp Tue Jul 30 23:00:28 2013
@@ -26,6 +26,9 @@ namespace {
 /// \brief Helper function to determine whether a file has the same path
 /// prefix as \a Path.
 ///
+/// \a File shouldn't contain relative operators i.e. ".." or "." since Path
+/// comes from the include/exclude list of paths in which relative operators
+/// were removed.
 /// \a Path must be an absolute path.
 bool fileHasPathPrefix(StringRef File, StringRef Path) {
   // Converts File to its absolute path.
@@ -48,6 +51,31 @@ bool fileHasPathPrefix(StringRef File, S
   return true;
 }
 
+/// \brief Helper function for removing relative operators from a given
+/// path i.e. "..", ".".
+std::string removeRelativeOperators(StringRef Path) {
+  sys::path::const_iterator PathI = sys::path::begin(Path);
+  sys::path::const_iterator PathE = sys::path::end(Path);
+  SmallVector<StringRef, 16> PathT;
+  while (PathI != PathE) {
+    if (PathI->equals("..")) {
+      // Test if we have reached the root then Path is invalid.
+      if (PathT.empty())
+        return "";
+      PathT.pop_back();
+    } else if (!PathI->equals("."))
+      PathT.push_back(*PathI);
+    ++PathI;
+  }
+  // Rebuild the new path.
+  SmallString<64> NewPath;
+  for (SmallVectorImpl<StringRef>::iterator I = PathT.begin(), E = PathT.end();
+       I != E; ++I) {
+    llvm::sys::path::append(NewPath, *I);
+  }
+  return NewPath.str();
+}
+
 /// \brief Helper function to tokenize a string of paths and populate
 /// the vector.
 error_code parseCLInput(StringRef Line, std::vector<std::string> &List,
@@ -61,13 +89,13 @@ error_code parseCLInput(StringRef Line,
     SmallString<64> Path = I->rtrim();
     if (error_code Err = sys::fs::make_absolute(Path))
       return Err;
-
-    // sys::fs::make_absolute will turn "." into "<pwd>/.". Need to strip "/."
-    // off or it interferes with prefix checking.
-    if (Path.endswith("/."))
-      List.push_back(Path.slice(0, Path.size() - 2).str());
+    // Remove relative operators from the path.
+    std::string AbsPath = removeRelativeOperators(Path);
+    // Add only non-empty paths to the list.
+    if (!AbsPath.empty())
+      List.push_back(AbsPath);
     else
-      List.push_back(Path.str());
+      llvm::errs() << "Unable to parse input path: " << *I << "\n";
 
     llvm::errs() << "Parse: " <<List.back() << "\n";
   }

Modified: clang-tools-extra/trunk/unittests/cpp11-migrate/IncludeExcludeTest.cpp
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/unittests/cpp11-migrate/IncludeExcludeTest.cpp?rev=187481&r1=187480&r2=187481&view=diff
==============================================================================
--- clang-tools-extra/trunk/unittests/cpp11-migrate/IncludeExcludeTest.cpp (original)
+++ clang-tools-extra/trunk/unittests/cpp11-migrate/IncludeExcludeTest.cpp Tue Jul 30 23:00:28 2013
@@ -52,6 +52,23 @@ TEST(IncludeExcludeTest, ParseString) {
   EXPECT_FALSE(IEManager.isFileIncluded("c/c2/c3/f.cpp"));
 }
 
+TEST(IncludeExcludeTest, ParseStringCases) {
+  IncludeExcludeInfo IEManager;
+  llvm::error_code Err = IEManager.readListFromString(
+      /*include=*/  "a/.,b/b2/,c/c2/c3/../../c4/,d/d2/./d3/,/e/e2/.",
+      /*exclude=*/ "");
+
+  ASSERT_EQ(Err, llvm::error_code::success());
+
+  EXPECT_TRUE(IEManager.isFileIncluded("a/f.cpp"));
+  EXPECT_TRUE(IEManager.isFileIncluded("b/b2/f.cpp"));
+  EXPECT_TRUE(IEManager.isFileIncluded("c/c4/f.cpp"));
+  EXPECT_TRUE(IEManager.isFileIncluded("d/d2/d3/f.cpp"));
+  EXPECT_TRUE(IEManager.isFileIncluded("/e/e2/f.cpp"));
+
+  EXPECT_FALSE(IEManager.isFileIncluded("c/c2/c3/f.cpp"));
+}
+
 // Utility for creating and filling files with data for IncludeExcludeFileTest
 // tests.
 struct InputFiles {





More information about the cfe-commits mailing list