summaryrefslogtreecommitdiffstats
path: root/clang-tools-extra/modularize/ModularizeUtilities.cpp
diff options
context:
space:
mode:
authorJohn Thompson <John.Thompson.JTSoftware@gmail.com>2015-07-10 00:37:25 +0000
committerJohn Thompson <John.Thompson.JTSoftware@gmail.com>2015-07-10 00:37:25 +0000
commit4018c62428f125ababbd2bec0d0cb7529472f37c (patch)
tree74f4381c7e9ab8765e74e83a4cb688380c4d2232 /clang-tools-extra/modularize/ModularizeUtilities.cpp
parentfdbff2afed6e7f39183de1f6118de71e36874ae8 (diff)
Added mechanism to modularize for doing a compilation precheck
to determine files that have comnpilation or dependency problems. A new -display-file-lists option use this to display lists of good files (no compile errors), problem files, and a combined list with problem files preceded by a '#'. The problem files list can be used in the module map generation assistant mode to exclude problem files. The combined files list can be used during module map development. See added docs. llvm-svn: 241880
Diffstat (limited to 'clang-tools-extra/modularize/ModularizeUtilities.cpp')
-rw-r--r--clang-tools-extra/modularize/ModularizeUtilities.cpp163
1 files changed, 143 insertions, 20 deletions
diff --git a/clang-tools-extra/modularize/ModularizeUtilities.cpp b/clang-tools-extra/modularize/ModularizeUtilities.cpp
index 7594b6725cc4..08c92fc90c0d 100644
--- a/clang-tools-extra/modularize/ModularizeUtilities.cpp
+++ b/clang-tools-extra/modularize/ModularizeUtilities.cpp
@@ -42,9 +42,11 @@ public:
// Constructor.
ModularizeUtilities::ModularizeUtilities(std::vector<std::string> &InputPaths,
- llvm::StringRef Prefix)
+ llvm::StringRef Prefix,
+ llvm::StringRef ProblemFilesListPath)
: InputFilePaths(InputPaths),
HeaderPrefix(Prefix),
+ ProblemFilesPath(ProblemFilesListPath),
HasModuleMap(false),
MissingHeaderCount(0),
// Init clang stuff needed for loading the module map and preprocessing.
@@ -65,9 +67,10 @@ ModularizeUtilities::ModularizeUtilities(std::vector<std::string> &InputPaths,
// Create instance of ModularizeUtilities, to simplify setting up
// subordinate objects.
ModularizeUtilities *ModularizeUtilities::createModularizeUtilities(
- std::vector<std::string> &InputPaths, llvm::StringRef Prefix) {
+ std::vector<std::string> &InputPaths, llvm::StringRef Prefix,
+ llvm::StringRef ProblemFilesListPath) {
- return new ModularizeUtilities(InputPaths, Prefix);
+ return new ModularizeUtilities(InputPaths, Prefix, ProblemFilesListPath);
}
// Load all header lists and dependencies.
@@ -91,6 +94,15 @@ std::error_code ModularizeUtilities::loadAllHeaderListsAndDependencies() {
}
}
}
+ // If we have a problem files list.
+ if (ProblemFilesPath.size() != 0) {
+ // Load problem files list.
+ if (std::error_code EC = loadProblemHeaderList(ProblemFilesPath)) {
+ errs() << "modularize: error: Unable to get problem header list '" << ProblemFilesPath
+ << "': " << EC.message() << '\n';
+ return EC;
+ }
+ }
return std::error_code();
}
@@ -194,6 +206,58 @@ std::error_code ModularizeUtilities::loadSingleHeaderListsAndDependencies(
return std::error_code();
}
+// Load problem header list.
+std::error_code ModularizeUtilities::loadProblemHeaderList(
+ llvm::StringRef InputPath) {
+
+ // By default, use the path component of the list file name.
+ SmallString<256> HeaderDirectory(InputPath);
+ llvm::sys::path::remove_filename(HeaderDirectory);
+ SmallString<256> CurrentDirectory;
+ llvm::sys::fs::current_path(CurrentDirectory);
+
+ // Get the prefix if we have one.
+ if (HeaderPrefix.size() != 0)
+ HeaderDirectory = HeaderPrefix;
+
+ // Read the header list file into a buffer.
+ ErrorOr<std::unique_ptr<MemoryBuffer>> listBuffer =
+ MemoryBuffer::getFile(InputPath);
+ if (std::error_code EC = listBuffer.getError())
+ return EC;
+
+ // Parse the header list into strings.
+ SmallVector<StringRef, 32> Strings;
+ listBuffer.get()->getBuffer().split(Strings, "\n", -1, false);
+
+ // Collect the header file names from the string list.
+ for (SmallVectorImpl<StringRef>::iterator I = Strings.begin(),
+ E = Strings.end();
+ I != E; ++I) {
+ StringRef Line = I->trim();
+ // Ignore comments and empty lines.
+ if (Line.empty() || (Line[0] == '#'))
+ continue;
+ SmallString<256> HeaderFileName;
+ // Prepend header file name prefix if it's not absolute.
+ if (llvm::sys::path::is_absolute(Line))
+ llvm::sys::path::native(Line, HeaderFileName);
+ else {
+ if (HeaderDirectory.size() != 0)
+ HeaderFileName = HeaderDirectory;
+ else
+ HeaderFileName = CurrentDirectory;
+ llvm::sys::path::append(HeaderFileName, Line);
+ llvm::sys::path::native(HeaderFileName);
+ }
+ // Get canonical form.
+ HeaderFileName = getCanonicalPath(HeaderFileName);
+ // Save the resulting header file path.
+ ProblemFileNames.push_back(HeaderFileName.str());
+ }
+ return std::error_code();
+}
+
// Load single module map and extract header file list.
std::error_code ModularizeUtilities::loadModuleMap(
llvm::StringRef InputPath) {
@@ -364,24 +428,24 @@ bool ModularizeUtilities::collectUmbrellaHeaders(StringRef UmbrellaDirName,
}
// Replace .. embedded in path for purposes of having
-// a canonical path.
+// a canonical path.
static std::string replaceDotDot(StringRef Path) {
- SmallString<128> Buffer;
- llvm::sys::path::const_iterator B = llvm::sys::path::begin(Path),
- E = llvm::sys::path::end(Path);
- while (B != E) {
- if (B->compare(".") == 0) {
- }
- else if (B->compare("..") == 0)
- llvm::sys::path::remove_filename(Buffer);
- else
- llvm::sys::path::append(Buffer, *B);
- ++B;
- }
- if (Path.endswith("/") || Path.endswith("\\"))
- Buffer.append(1, Path.back());
- return Buffer.c_str();
-}
+ SmallString<128> Buffer;
+ llvm::sys::path::const_iterator B = llvm::sys::path::begin(Path),
+ E = llvm::sys::path::end(Path);
+ while (B != E) {
+ if (B->compare(".") == 0) {
+ }
+ else if (B->compare("..") == 0)
+ llvm::sys::path::remove_filename(Buffer);
+ else
+ llvm::sys::path::append(Buffer, *B);
+ ++B;
+ }
+ if (Path.endswith("/") || Path.endswith("\\"))
+ Buffer.append(1, Path.back());
+ return Buffer.c_str();
+}
// Convert header path to canonical form.
// The canonical form is basically just use forward slashes, and remove "./".
@@ -424,3 +488,62 @@ std::string ModularizeUtilities::getDirectoryFromPath(StringRef Path) {
return ".";
return Directory.str();
}
+
+// Add unique problem file.
+// Also standardizes the path.
+void ModularizeUtilities::addUniqueProblemFile(std::string FilePath) {
+ FilePath = getCanonicalPath(FilePath);
+ // Don't add if already present.
+ for(auto &TestFilePath : ProblemFileNames) {
+ if (TestFilePath == FilePath)
+ return;
+ }
+ ProblemFileNames.push_back(FilePath);
+}
+
+// Add file with no compile errors.
+// Also standardizes the path.
+void ModularizeUtilities::addNoCompileErrorsFile(std::string FilePath) {
+ FilePath = getCanonicalPath(FilePath);
+ GoodFileNames.push_back(FilePath);
+}
+
+// List problem files.
+void ModularizeUtilities::displayProblemFiles() {
+ errs() << "\nThese are the files with possible errors:\n\n";
+ for (auto &ProblemFile : ProblemFileNames) {
+ errs() << ProblemFile << "\n";
+ }
+}
+
+// List files with no problems.
+void ModularizeUtilities::displayGoodFiles() {
+ errs() << "\nThese are the files with no detected errors:\n\n";
+ for (auto &GoodFile : HeaderFileNames) {
+ bool Good = true;
+ for (auto &ProblemFile : ProblemFileNames) {
+ if (ProblemFile == GoodFile) {
+ Good = false;
+ break;
+ }
+ }
+ if (Good)
+ errs() << GoodFile << "\n";
+ }
+}
+
+// List files with problem files commented out.
+void ModularizeUtilities::displayCombinedFiles() {
+ errs() <<
+ "\nThese are the combined files, with problem files preceded by #:\n\n";
+ for (auto &File : HeaderFileNames) {
+ bool Good = true;
+ for (auto &ProblemFile : ProblemFileNames) {
+ if (ProblemFile == File) {
+ Good = false;
+ break;
+ }
+ }
+ errs() << (Good ? "" : "#") << File << "\n";
+ }
+}