From 035c7fabc3b82cbc9a346c11abe2e9462b4c0379 Mon Sep 17 00:00:00 2001 From: Anas Nashif Date: Tue, 30 Oct 2012 15:39:57 -0700 Subject: Imported Upstream version 2.8.9 --- Source/cmOutputRequiredFilesCommand.cxx | 240 ++++++++++++++++++++++++++++++++ 1 file changed, 240 insertions(+) create mode 100644 Source/cmOutputRequiredFilesCommand.cxx (limited to 'Source/cmOutputRequiredFilesCommand.cxx') diff --git a/Source/cmOutputRequiredFilesCommand.cxx b/Source/cmOutputRequiredFilesCommand.cxx new file mode 100644 index 000000000..be079c096 --- /dev/null +++ b/Source/cmOutputRequiredFilesCommand.cxx @@ -0,0 +1,240 @@ +/*============================================================================ + CMake - Cross Platform Makefile Generator + Copyright 2000-2009 Kitware, Inc., Insight Software Consortium + + Distributed under the OSI-approved BSD License (the "License"); + see accompanying file Copyright.txt for details. + + This software is distributed WITHOUT ANY WARRANTY; without even the + implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + See the License for more information. +============================================================================*/ +#include "cmOutputRequiredFilesCommand.h" +#include "cmMakeDepend.h" + +class cmLBDepend : public cmMakeDepend +{ + /** + * Compute the depend information for this class. + */ + virtual void DependWalk(cmDependInformation* info); +}; + +void cmLBDepend::DependWalk(cmDependInformation* info) +{ + std::ifstream fin(info->FullPath.c_str()); + if(!fin) + { + cmSystemTools::Error("error can not open ", info->FullPath.c_str()); + return; + } + + std::string line; + while(cmSystemTools::GetLineFromStream(fin, line)) + { + if(!strncmp(line.c_str(), "#include", 8)) + { + // if it is an include line then create a string class + std::string currentline = line; + size_t qstart = currentline.find('\"', 8); + size_t qend; + // if a quote is not found look for a < + if(qstart == std::string::npos) + { + qstart = currentline.find('<', 8); + // if a < is not found then move on + if(qstart == std::string::npos) + { + cmSystemTools::Error("unknown include directive ", + currentline.c_str() ); + continue; + } + else + { + qend = currentline.find('>', qstart+1); + } + } + else + { + qend = currentline.find('\"', qstart+1); + } + // extract the file being included + std::string includeFile = currentline.substr(qstart+1, qend - qstart-1); + // see if the include matches the regular expression + if(!this->IncludeFileRegularExpression.find(includeFile)) + { + if(this->Verbose) + { + std::string message = "Skipping "; + message += includeFile; + message += " for file "; + message += info->FullPath.c_str(); + cmSystemTools::Error(message.c_str(), 0); + } + continue; + } + + // Add this file and all its dependencies. + this->AddDependency(info, includeFile.c_str()); + /// add the cxx file if it exists + std::string cxxFile = includeFile; + std::string::size_type pos = cxxFile.rfind('.'); + if(pos != std::string::npos) + { + std::string root = cxxFile.substr(0, pos); + cxxFile = root + ".cxx"; + bool found = false; + // try jumping to .cxx .cpp and .c in order + if(cmSystemTools::FileExists(cxxFile.c_str())) + { + found = true; + } + for(std::vector::iterator i = + this->IncludeDirectories.begin(); + i != this->IncludeDirectories.end(); ++i) + { + std::string path = *i; + path = path + "/"; + path = path + cxxFile; + if(cmSystemTools::FileExists(path.c_str())) + { + found = true; + } + } + if (!found) + { + cxxFile = root + ".cpp"; + if(cmSystemTools::FileExists(cxxFile.c_str())) + { + found = true; + } + for(std::vector::iterator i = + this->IncludeDirectories.begin(); + i != this->IncludeDirectories.end(); ++i) + { + std::string path = *i; + path = path + "/"; + path = path + cxxFile; + if(cmSystemTools::FileExists(path.c_str())) + { + found = true; + } + } + } + if (!found) + { + cxxFile = root + ".c"; + if(cmSystemTools::FileExists(cxxFile.c_str())) + { + found = true; + } + for(std::vector::iterator i = + this->IncludeDirectories.begin(); + i != this->IncludeDirectories.end(); ++i) + { + std::string path = *i; + path = path + "/"; + path = path + cxxFile; + if(cmSystemTools::FileExists(path.c_str())) + { + found = true; + } + } + } + if (!found) + { + cxxFile = root + ".txx"; + if(cmSystemTools::FileExists(cxxFile.c_str())) + { + found = true; + } + for(std::vector::iterator i = + this->IncludeDirectories.begin(); + i != this->IncludeDirectories.end(); ++i) + { + std::string path = *i; + path = path + "/"; + path = path + cxxFile; + if(cmSystemTools::FileExists(path.c_str())) + { + found = true; + } + } + } + if (found) + { + this->AddDependency(info, cxxFile.c_str()); + } + } + } + } +} + +// cmOutputRequiredFilesCommand +bool cmOutputRequiredFilesCommand +::InitialPass(std::vector const& args, cmExecutionStatus &) +{ + if(args.size() != 2 ) + { + this->SetError("called with incorrect number of arguments"); + return false; + } + + // store the arg for final pass + this->File = args[0]; + this->OutputFile = args[1]; + + // compute the list of files + cmLBDepend md; + md.SetMakefile(this->Makefile); + md.AddSearchPath(this->Makefile->GetStartDirectory()); + // find the depends for a file + const cmDependInformation *info = md.FindDependencies(this->File.c_str()); + if (info) + { + // write them out + FILE *fout = fopen(this->OutputFile.c_str(),"w"); + if(!fout) + { + std::string err = "Can not open output file: "; + err += this->OutputFile; + this->SetError(err.c_str()); + return false; + } + std::set visited; + this->ListDependencies(info,fout, &visited); + fclose(fout); + } + + return true; +} + +void cmOutputRequiredFilesCommand:: +ListDependencies(cmDependInformation const *info, + FILE *fout, + std::set *visited) +{ + // add info to the visited set + visited->insert(info); + // now recurse with info's dependencies + for(cmDependInformation::DependencySetType::const_iterator d = + info->DependencySet.begin(); + d != info->DependencySet.end(); ++d) + { + if (visited->find(*d) == visited->end()) + { + if(info->FullPath != "") + { + std::string tmp = (*d)->FullPath; + std::string::size_type pos = tmp.rfind('.'); + if(pos != std::string::npos && (tmp.substr(pos) != ".h")) + { + tmp = tmp.substr(0, pos); + fprintf(fout,"%s\n",(*d)->FullPath.c_str()); + } + } + this->ListDependencies(*d,fout,visited); + } + } +} + -- cgit v1.2.3