summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--clang/include/clang/CrossTU/CrossTranslationUnit.h3
-rw-r--r--clang/lib/CrossTU/CrossTranslationUnit.cpp20
-rw-r--r--clang/test/Analysis/Inputs/ctu-other.cpp14
-rw-r--r--clang/test/Analysis/Inputs/ctu-other.cpp.externalDefMap.txt1
-rw-r--r--clang/test/Analysis/ctu-main.cpp14
-rw-r--r--clang/test/Analysis/func-mapping-test.cpp7
-rw-r--r--clang/tools/clang-extdef-mapping/ClangExtDefMapGen.cpp9
7 files changed, 56 insertions, 12 deletions
diff --git a/clang/include/clang/CrossTU/CrossTranslationUnit.h b/clang/include/clang/CrossTU/CrossTranslationUnit.h
index a712560790f..bf9ee8d1a02 100644
--- a/clang/include/clang/CrossTU/CrossTranslationUnit.h
+++ b/clang/include/clang/CrossTU/CrossTranslationUnit.h
@@ -17,6 +17,7 @@
#include "clang/AST/ASTImporterSharedState.h"
#include "clang/Basic/LLVM.h"
#include "llvm/ADT/DenseMap.h"
+#include "llvm/ADT/Optional.h"
#include "llvm/ADT/SmallPtrSet.h"
#include "llvm/ADT/StringMap.h"
#include "llvm/Support/Error.h"
@@ -159,7 +160,7 @@ public:
ASTUnit *Unit);
/// Get a name to identify a named decl.
- static std::string getLookupName(const NamedDecl *ND);
+ static llvm::Optional<std::string> getLookupName(const NamedDecl *ND);
/// Emit diagnostics for the user for potential configuration errors.
void emitCrossTUDiagnostics(const IndexError &IE);
diff --git a/clang/lib/CrossTU/CrossTranslationUnit.cpp b/clang/lib/CrossTU/CrossTranslationUnit.cpp
index f43180a2a27..bd8a022eb4d 100644
--- a/clang/lib/CrossTU/CrossTranslationUnit.cpp
+++ b/clang/lib/CrossTU/CrossTranslationUnit.cpp
@@ -193,12 +193,13 @@ CrossTranslationUnitContext::CrossTranslationUnitContext(CompilerInstance &CI)
CrossTranslationUnitContext::~CrossTranslationUnitContext() {}
-std::string CrossTranslationUnitContext::getLookupName(const NamedDecl *ND) {
+llvm::Optional<std::string>
+CrossTranslationUnitContext::getLookupName(const NamedDecl *ND) {
SmallString<128> DeclUSR;
bool Ret = index::generateUSRForDecl(ND, DeclUSR);
- (void)Ret;
- assert(!Ret && "Unable to generate USR");
- return DeclUSR.str();
+ if (Ret)
+ return {};
+ return std::string(DeclUSR.str());
}
/// Recursively visits the decls of a DeclContext, and returns one with the
@@ -218,7 +219,8 @@ CrossTranslationUnitContext::findDefInDeclContext(const DeclContext *DC,
const T *ResultDecl;
if (!ND || !hasBodyOrInit(ND, ResultDecl))
continue;
- if (getLookupName(ResultDecl) != LookupName)
+ llvm::Optional<std::string> ResultLookupName = getLookupName(ResultDecl);
+ if (!ResultLookupName || *ResultLookupName != LookupName)
continue;
return ResultDecl;
}
@@ -233,12 +235,12 @@ llvm::Expected<const T *> CrossTranslationUnitContext::getCrossTUDefinitionImpl(
assert(!hasBodyOrInit(D) &&
"D has a body or init in current translation unit!");
++NumGetCTUCalled;
- const std::string LookupName = getLookupName(D);
- if (LookupName.empty())
+ const llvm::Optional<std::string> LookupName = getLookupName(D);
+ if (!LookupName)
return llvm::make_error<IndexError>(
index_error_code::failed_to_generate_usr);
llvm::Expected<ASTUnit *> ASTUnitOrError =
- loadExternalAST(LookupName, CrossTUDir, IndexName, DisplayCTUProgress);
+ loadExternalAST(*LookupName, CrossTUDir, IndexName, DisplayCTUProgress);
if (!ASTUnitOrError)
return ASTUnitOrError.takeError();
ASTUnit *Unit = *ASTUnitOrError;
@@ -294,7 +296,7 @@ llvm::Expected<const T *> CrossTranslationUnitContext::getCrossTUDefinitionImpl(
}
TranslationUnitDecl *TU = Unit->getASTContext().getTranslationUnitDecl();
- if (const T *ResultDecl = findDefInDeclContext<T>(TU, LookupName))
+ if (const T *ResultDecl = findDefInDeclContext<T>(TU, *LookupName))
return importDefinition(ResultDecl, Unit);
return llvm::make_error<IndexError>(index_error_code::failed_import);
}
diff --git a/clang/test/Analysis/Inputs/ctu-other.cpp b/clang/test/Analysis/Inputs/ctu-other.cpp
index a9ff6b5a93a..c2410ced35d 100644
--- a/clang/test/Analysis/Inputs/ctu-other.cpp
+++ b/clang/test/Analysis/Inputs/ctu-other.cpp
@@ -131,3 +131,17 @@ union U {
const unsigned int b;
};
U extU = {.a = 4};
+
+class TestAnonUnionUSR {
+public:
+ inline float f(int value) {
+ union {
+ float f;
+ int i;
+ };
+ i = value;
+ return f;
+ }
+ static const int Test;
+};
+const int TestAnonUnionUSR::Test = 5;
diff --git a/clang/test/Analysis/Inputs/ctu-other.cpp.externalDefMap.txt b/clang/test/Analysis/Inputs/ctu-other.cpp.externalDefMap.txt
index 3df181b29d5..da95098f4c8 100644
--- a/clang/test/Analysis/Inputs/ctu-other.cpp.externalDefMap.txt
+++ b/clang/test/Analysis/Inputs/ctu-other.cpp.externalDefMap.txt
@@ -25,3 +25,4 @@ c:@extSCN ctu-other.cpp.ast
c:@extSubSCN ctu-other.cpp.ast
c:@extSCC ctu-other.cpp.ast
c:@extU ctu-other.cpp.ast
+c:@S@TestAnonUnionUSR@Test ctu-other.cpp.ast
diff --git a/clang/test/Analysis/ctu-main.cpp b/clang/test/Analysis/ctu-main.cpp
index 1cb0d4a9d77..aae4808e90f 100644
--- a/clang/test/Analysis/ctu-main.cpp
+++ b/clang/test/Analysis/ctu-main.cpp
@@ -112,6 +112,19 @@ void test_virtual_functions(mycls* obj) {
clang_analyzer_eval(obj->fvcl(1) == 8); // expected-warning{{FALSE}} expected-warning{{TRUE}}
}
+class TestAnonUnionUSR {
+public:
+ inline float f(int value) {
+ union {
+ float f;
+ int i;
+ };
+ i = value;
+ return f;
+ }
+ static const int Test;
+};
+
int main() {
clang_analyzer_eval(f(3) == 2); // expected-warning{{TRUE}}
clang_analyzer_eval(f(4) == 3); // expected-warning{{TRUE}}
@@ -144,4 +157,5 @@ int main() {
clang_analyzer_eval(extSubSCN.a == 1); // expected-warning{{TRUE}}
// clang_analyzer_eval(extSCC.a == 7); // TODO
clang_analyzer_eval(extU.a == 4); // expected-warning{{TRUE}}
+ clang_analyzer_eval(TestAnonUnionUSR::Test == 5); // expected-warning{{TRUE}}
}
diff --git a/clang/test/Analysis/func-mapping-test.cpp b/clang/test/Analysis/func-mapping-test.cpp
index f6eeb261da5..5c04d9411fe 100644
--- a/clang/test/Analysis/func-mapping-test.cpp
+++ b/clang/test/Analysis/func-mapping-test.cpp
@@ -41,3 +41,10 @@ union U {
};
U u = {.a = 6};
// CHECK-DAG: c:@u
+
+// No USR can be generated for this.
+// Check for no crash in this case.
+static union {
+ float uf;
+ const int ui;
+};
diff --git a/clang/tools/clang-extdef-mapping/ClangExtDefMapGen.cpp b/clang/tools/clang-extdef-mapping/ClangExtDefMapGen.cpp
index 7a374698f7b..3c015fef93c 100644
--- a/clang/tools/clang-extdef-mapping/ClangExtDefMapGen.cpp
+++ b/clang/tools/clang-extdef-mapping/ClangExtDefMapGen.cpp
@@ -76,7 +76,12 @@ void MapExtDefNamesConsumer::handleDecl(const Decl *D) {
void MapExtDefNamesConsumer::addIfInMain(const DeclaratorDecl *DD,
SourceLocation defStart) {
- std::string LookupName = CrossTranslationUnitContext::getLookupName(DD);
+ llvm::Optional<std::string> LookupName =
+ CrossTranslationUnitContext::getLookupName(DD);
+ if (!LookupName)
+ return;
+ assert(!LookupName->empty() && "Lookup name should be non-empty.");
+
if (CurrentFileName.empty()) {
CurrentFileName =
SM.getFileEntryForID(SM.getMainFileID())->tryGetRealPathName();
@@ -89,7 +94,7 @@ void MapExtDefNamesConsumer::addIfInMain(const DeclaratorDecl *DD,
case VisibleNoLinkage:
case UniqueExternalLinkage:
if (SM.isInMainFile(defStart))
- Index[LookupName] = CurrentFileName;
+ Index[*LookupName] = CurrentFileName;
break;
default:
break;
OpenPOWER on IntegriCloud