martong updated this revision to Diff 176172. martong added a comment. - Add lit tests
Repository: rC Clang CHANGES SINCE LAST ACTION https://reviews.llvm.org/D55134/new/ https://reviews.llvm.org/D55134 Files: include/clang/Basic/DiagnosticCrossTUKinds.td include/clang/CrossTU/CrossTranslationUnit.h lib/CrossTU/CrossTranslationUnit.cpp test/Analysis/ctu-different-triples.cpp test/Analysis/ctu-unknown-parts-in-triples.cpp
Index: test/Analysis/ctu-unknown-parts-in-triples.cpp =================================================================== --- /dev/null +++ test/Analysis/ctu-unknown-parts-in-triples.cpp @@ -0,0 +1,16 @@ +// We do not expect any error when one part of the triple is unknown, but other +// known parts are equal. + +// RUN: rm -rf %t && mkdir %t +// RUN: mkdir -p %t/ctudir +// RUN: %clang_cc1 -triple x86_64-pc-linux-gnu -emit-pch -o %t/ctudir/ctu-other.cpp.ast %S/Inputs/ctu-other.cpp +// RUN: cp %S/Inputs/externalFnMap.txt %t/ctudir/externalFnMap.txt +// RUN: %clang_cc1 -triple x86_64-unknown-linux-gnu -fsyntax-only -analyze -analyzer-checker=core,debug.ExprInspection -analyzer-config experimental-enable-naive-ctu-analysis=true -analyzer-config ctu-dir=%t/ctudir -verify %s + +// expected-no-diagnostics + +int f(int); + +int main() { + return f(5); +} Index: test/Analysis/ctu-different-triples.cpp =================================================================== --- /dev/null +++ test/Analysis/ctu-different-triples.cpp @@ -0,0 +1,14 @@ +// RUN: rm -rf %t && mkdir %t +// RUN: mkdir -p %t/ctudir +// RUN: %clang_cc1 -triple x86_64-pc-linux-gnu -emit-pch -o %t/ctudir/ctu-other.cpp.ast %S/Inputs/ctu-other.cpp +// RUN: cp %S/Inputs/externalFnMap.txt %t/ctudir/externalFnMap.txt +// RUN: %clang_cc1 -triple powerpc64-montavista-linux-gnu -fsyntax-only -analyze -analyzer-checker=core,debug.ExprInspection -analyzer-config experimental-enable-naive-ctu-analysis=true -analyzer-config ctu-dir=%t/ctudir -verify %s + +// We expect an error in this file, but without a location. +// expected-error-re@./ctu-different-triples.cpp:*{{imported AST from {{.*}} had been generated for a different target, current: powerpc64-montavista-linux-gnu, imported: x86_64-pc-linux-gnu}} + +int f(int); + +int main() { + return f(5); +} Index: lib/CrossTU/CrossTranslationUnit.cpp =================================================================== --- lib/CrossTU/CrossTranslationUnit.cpp +++ lib/CrossTU/CrossTranslationUnit.cpp @@ -28,6 +28,36 @@ #include <fstream> #include <sstream> +namespace llvm { +// Same as Triple's equality operator, but we check a field only if that is +// known in both instances. +bool hasEqualKnownFields(const Triple &Lhs, const Triple &Rhs) { + return ((Lhs.getArch() != Triple::UnknownArch && + Rhs.getArch() != Triple::UnknownArch) + ? Lhs.getArch() == Rhs.getArch() + : true) && + ((Lhs.getSubArch() != Triple::NoSubArch && + Rhs.getSubArch() != Triple::NoSubArch) + ? Lhs.getSubArch() == Rhs.getSubArch() + : true) && + ((Lhs.getVendor() != Triple::UnknownVendor && + Rhs.getVendor() != Triple::UnknownVendor) + ? Lhs.getVendor() == Rhs.getVendor() + : true) && + ((Lhs.getOS() != Triple::UnknownOS && Rhs.getOS() != Triple::UnknownOS) + ? Lhs.getOS() == Rhs.getOS() + : true) && + ((Lhs.getEnvironment() != Triple::UnknownEnvironment && + Rhs.getEnvironment() != Triple::UnknownEnvironment) + ? Lhs.getEnvironment() == Rhs.getEnvironment() + : true) && + ((Lhs.getObjectFormat() != Triple::UnknownObjectFormat && + Rhs.getObjectFormat() != Triple::UnknownObjectFormat) + ? Lhs.getObjectFormat() == Rhs.getObjectFormat() + : true); +} +} + namespace clang { namespace cross_tu { @@ -55,6 +85,10 @@ return "Failed to load external AST source."; case index_error_code::failed_to_generate_usr: return "Failed to generate USR."; + case index_error_code::triple_mismatch: + return "Triple mismatch"; + case index_error_code::lang_mismatch: + return "Language mismatch"; } llvm_unreachable("Unrecognized index_error_code."); } @@ -166,6 +200,30 @@ assert(&Unit->getFileManager() == &Unit->getASTContext().getSourceManager().getFileManager()); + const auto& TripleTo = Context.getTargetInfo().getTriple(); + const auto& TripleFrom = Unit->getASTContext().getTargetInfo().getTriple(); + // The imported AST had been generated for a different target. + // Some parts of the triple in the loaded ASTContext can be unknown while the + // very same parts in the target ASTContext are known. Thus we check for the + // known parts only. + if (!hasEqualKnownFields(TripleTo, TripleFrom)) { + // TODO pass the SourceLocation of the CallExpression for more precise + // diagnostics + Context.getDiagnostics().Report(diag::err_ctu_incompat_triple) + << Unit->getMainFileName() << TripleTo.str() << TripleFrom.str(); + // TODO Add statistics here + return llvm::make_error<IndexError>(index_error_code::triple_mismatch); + } + + const auto& LangTo = Context.getLangOpts(); + const auto& LangFrom = Unit->getASTContext().getLangOpts(); + // FIXME: Currenty we do not support CTU across C++ and C and across + // different dialects of C++. + if (LangTo.CPlusPlus != LangFrom.CPlusPlus) { + // TODO Add statistics here. + return llvm::make_error<IndexError>(index_error_code::lang_mismatch); + } + TranslationUnitDecl *TU = Unit->getASTContext().getTranslationUnitDecl(); if (const FunctionDecl *ResultDecl = findFunctionInDeclContext(TU, LookupFnName)) Index: include/clang/CrossTU/CrossTranslationUnit.h =================================================================== --- include/clang/CrossTU/CrossTranslationUnit.h +++ include/clang/CrossTU/CrossTranslationUnit.h @@ -41,7 +41,9 @@ missing_definition, failed_import, failed_to_get_external_ast, - failed_to_generate_usr + failed_to_generate_usr, + triple_mismatch, + lang_mismatch }; class IndexError : public llvm::ErrorInfo<IndexError> { Index: include/clang/Basic/DiagnosticCrossTUKinds.td =================================================================== --- include/clang/Basic/DiagnosticCrossTUKinds.td +++ include/clang/Basic/DiagnosticCrossTUKinds.td @@ -15,4 +15,7 @@ def err_multiple_def_index : Error< "multiple definitions are found for the same key in index ">; + +def err_ctu_incompat_triple : Error< + "imported AST from '%0' had been generated for a different target, current: %1, imported: %2">; }
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits