diff --git a/utils/TableGen/ClangDiagnosticsEmitter.cpp b/utils/TableGen/ClangDiagnosticsEmitter.cpp index fa139e7729e..f9501fb494d 100644 --- a/utils/TableGen/ClangDiagnosticsEmitter.cpp +++ b/utils/TableGen/ClangDiagnosticsEmitter.cpp @@ -22,8 +22,8 @@ typedef std::vector RecordVector; typedef std::vector SuperClassVector; typedef std::vector RecordValVector; -static const RecordVal* findRecordVal(const RecordValVector& Vals, - const std::string &key) { +static const RecordVal* findRecordVal(const Record& R, const std::string &key) { + const RecordValVector &Vals = R.getValues(); for (RecordValVector::const_iterator I=Vals.begin(), E=Vals.end(); I!=E; ++I) if ((*I).getName() == key) return &*I; @@ -49,6 +49,11 @@ static void EmitEscaped(std::ostream& OS, const std::string &s) { } } +static void EmitAllCaps(std::ostream& OS, const std::string &s) { + for (std::string::const_iterator I=s.begin(), E=s.end(); I!=E; ++I) + OS << char(toupper(*I)); +} + static void ProcessDiag(std::ostream& OS, const Record* DiagClass, const Record& R) { @@ -57,12 +62,9 @@ static void ProcessDiag(std::ostream& OS, const Record* DiagClass, return; OS << "DIAG(" << R.getName() << ", "; + EmitAllCaps(OS, DiagKind->getName()); - const std::string &s = DiagKind->getName(); - for (std::string::const_iterator I=s.begin(), E=s.end(); I!=E; ++I) - OS << char(toupper(*I)); - - const RecordVal* Text = findRecordVal(R.getValues(), "Text"); + const RecordVal* Text = findRecordVal(R, "Text"); assert(Text && "No 'Text' entry in Diagnostic."); const StringInit* TextVal = dynamic_cast(Text->getValue()); assert(TextVal && "Value 'Text' must be a string."); @@ -77,8 +79,30 @@ void ClangDiagsDefsEmitter::run(std::ostream &OS) { const Record* DiagClass = Records.getClass("Diagnostic"); assert(DiagClass && "No Diagnostic class defined."); + // Write the #if guard + if (!Component.empty()) { + OS << "#ifdef "; + EmitAllCaps(OS, Component); + OS << "START\n__"; + EmitAllCaps(OS, Component); + OS << "START = DIAG_START_"; + EmitAllCaps(OS, Component); + OS << ",\n#undef "; + EmitAllCaps(OS, Component); + OS << "START\n#endif\n"; + } + for (RecordVector::const_iterator I=Diags.begin(), E=Diags.end(); I!=E; ++I) { - // FIXME: Compare the component. + if (!Component.empty()) { + const RecordVal* V = findRecordVal(**I, "Component"); + if (!V) + continue; + + const StringInit* SV = dynamic_cast(V->getValue()); + if (SV->getValue() != Component) + continue; + } + ProcessDiag(OS, DiagClass, **I); } -} \ No newline at end of file +} diff --git a/utils/TableGen/ClangDiagnosticsEmitter.h b/utils/TableGen/ClangDiagnosticsEmitter.h index 93979708b07..bedfe5af8f8 100644 --- a/utils/TableGen/ClangDiagnosticsEmitter.h +++ b/utils/TableGen/ClangDiagnosticsEmitter.h @@ -23,8 +23,10 @@ namespace llvm { /// class ClangDiagsDefsEmitter : public TableGenBackend { RecordKeeper &Records; + const std::string& Component; public: - explicit ClangDiagsDefsEmitter(RecordKeeper &R) : Records(R) {} + explicit ClangDiagsDefsEmitter(RecordKeeper &R, const std::string& component) + : Records(R), Component(component) {} // run - Output the .def file contents void run(std::ostream &OS); diff --git a/utils/TableGen/TableGen.cpp b/utils/TableGen/TableGen.cpp index e6ed092b62f..22c5d504155 100644 --- a/utils/TableGen/TableGen.cpp +++ b/utils/TableGen/TableGen.cpp @@ -110,6 +110,11 @@ namespace { cl::list IncludeDirs("I", cl::desc("Directory of include files"), cl::value_desc("directory"), cl::Prefix); + + cl::opt + ClangComponent("clang-component", + cl::desc("Only use warnings from specified component"), + cl::value_desc("component"), cl::Hidden); } @@ -202,7 +207,7 @@ int main(int argc, char **argv) { AsmWriterEmitter(Records).run(*Out); break; case GenClangDiagsDefs: - ClangDiagsDefsEmitter(Records).run(*Out); + ClangDiagsDefsEmitter(Records, ClangComponent).run(*Out); break; case GenDAGISel: DAGISelEmitter(Records).run(*Out);