aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/clang/AST/Mangle.h6
-rw-r--r--lib/AST/ItaniumMangle.cpp5
-rw-r--r--lib/AST/MicrosoftMangle.cpp9
-rw-r--r--lib/CodeGen/CodeGenTBAA.cpp10
-rw-r--r--test/CodeGen/tbaa-ms-abi.cpp22
5 files changed, 45 insertions, 7 deletions
diff --git a/include/clang/AST/Mangle.h b/include/clang/AST/Mangle.h
index e875c31fc0..4df2955aec 100644
--- a/include/clang/AST/Mangle.h
+++ b/include/clang/AST/Mangle.h
@@ -148,6 +148,12 @@ public:
virtual void mangleDynamicAtExitDestructor(const VarDecl *D,
raw_ostream &) = 0;
+ /// Generates a unique string for an externally visible type for use with TBAA
+ /// or type uniquing.
+ /// TODO: Extend this to internal types by generating names that are unique
+ /// across translation units so it can be used with LTO.
+ virtual void mangleTypeName(QualType T, raw_ostream &) = 0;
+
/// @}
};
diff --git a/lib/AST/ItaniumMangle.cpp b/lib/AST/ItaniumMangle.cpp
index e94b4cf907..0621d7b1ad 100644
--- a/lib/AST/ItaniumMangle.cpp
+++ b/lib/AST/ItaniumMangle.cpp
@@ -144,6 +144,7 @@ public:
raw_ostream &);
void mangleCXXRTTI(QualType T, raw_ostream &);
void mangleCXXRTTIName(QualType T, raw_ostream &);
+ void mangleTypeName(QualType T, raw_ostream &);
void mangleCXXCtor(const CXXConstructorDecl *D, CXXCtorType Type,
raw_ostream &);
void mangleCXXDtor(const CXXDestructorDecl *D, CXXDtorType Type,
@@ -3784,6 +3785,10 @@ void ItaniumMangleContextImpl::mangleCXXRTTIName(QualType Ty,
Mangler.mangleType(Ty);
}
+void ItaniumMangleContextImpl::mangleTypeName(QualType Ty, raw_ostream &Out) {
+ mangleCXXRTTIName(Ty, Out);
+}
+
ItaniumMangleContext *
ItaniumMangleContext::create(ASTContext &Context, DiagnosticsEngine &Diags) {
return new ItaniumMangleContextImpl(Context, Diags);
diff --git a/lib/AST/MicrosoftMangle.cpp b/lib/AST/MicrosoftMangle.cpp
index ff1b0158c5..ed7168e3eb 100644
--- a/lib/AST/MicrosoftMangle.cpp
+++ b/lib/AST/MicrosoftMangle.cpp
@@ -197,6 +197,7 @@ public:
raw_ostream &Out);
virtual void mangleCXXRTTI(QualType T, raw_ostream &);
virtual void mangleCXXRTTIName(QualType T, raw_ostream &);
+ virtual void mangleTypeName(QualType T, raw_ostream &);
virtual void mangleCXXCtor(const CXXConstructorDecl *D, CXXCtorType Type,
raw_ostream &);
virtual void mangleCXXDtor(const CXXDestructorDecl *D, CXXDtorType Type,
@@ -2019,6 +2020,14 @@ void MicrosoftMangleContextImpl::mangleCXXRTTIName(QualType T, raw_ostream &) {
<< T.getBaseTypeIdentifier();
}
+void MicrosoftMangleContextImpl::mangleTypeName(QualType T, raw_ostream &Out) {
+ // This is just a made up unique string for the purposes of tbaa. undname
+ // does *not* know how to demangle it.
+ MicrosoftCXXNameMangler Mangler(*this, Out);
+ Mangler.getStream() << '?';
+ Mangler.mangleType(T, SourceRange());
+}
+
void MicrosoftMangleContextImpl::mangleCXXCtor(const CXXConstructorDecl *D,
CXXCtorType Type,
raw_ostream &Out) {
diff --git a/lib/CodeGen/CodeGenTBAA.cpp b/lib/CodeGen/CodeGenTBAA.cpp
index 11e376ff40..699cc2eabe 100644
--- a/lib/CodeGen/CodeGenTBAA.cpp
+++ b/lib/CodeGen/CodeGenTBAA.cpp
@@ -152,11 +152,9 @@ CodeGenTBAA::getTBAAInfo(QualType QTy) {
if (!Features.CPlusPlus || !ETy->getDecl()->isExternallyVisible())
return MetadataCache[Ty] = getChar();
- // TODO: This is using the RTTI name. Is there a better way to get
- // a unique string for a type?
SmallString<256> OutName;
llvm::raw_svector_ostream Out(OutName);
- MContext.mangleCXXRTTIName(QualType(ETy, 0), Out);
+ MContext.mangleTypeName(QualType(ETy, 0), Out);
Out.flush();
return MetadataCache[Ty] = createTBAAScalarType(OutName, getChar());
}
@@ -268,13 +266,11 @@ CodeGenTBAA::getTBAAStructTypeInfo(QualType QTy) {
FieldNode, Layout.getFieldOffset(idx) / Context.getCharWidth()));
}
- // TODO: This is using the RTTI name. Is there a better way to get
- // a unique string for a type?
SmallString<256> OutName;
if (Features.CPlusPlus) {
- // Don't use mangleCXXRTTIName for C code.
+ // Don't use the mangler for C code.
llvm::raw_svector_ostream Out(OutName);
- MContext.mangleCXXRTTIName(QualType(Ty, 0), Out);
+ MContext.mangleTypeName(QualType(Ty, 0), Out);
Out.flush();
} else {
OutName = RD->getName();
diff --git a/test/CodeGen/tbaa-ms-abi.cpp b/test/CodeGen/tbaa-ms-abi.cpp
new file mode 100644
index 0000000000..67390b1a8a
--- /dev/null
+++ b/test/CodeGen/tbaa-ms-abi.cpp
@@ -0,0 +1,22 @@
+// RUN: %clang_cc1 -cxx-abi microsoft -triple i686-pc-win32 -disable-llvm-optzns -emit-llvm -o - -O1 %s | FileCheck %s
+//
+// Test that TBAA works in the Microsoft C++ ABI. We used to error out while
+// attempting to mangle RTTI.
+
+struct StructA {
+ int a;
+};
+
+struct StructB : virtual StructA {
+ StructB();
+};
+
+StructB::StructB() {
+ a = 42;
+// CHECK: store i32 42, i32* {{.*}}, !tbaa [[TAG_A_i32:!.*]]
+}
+
+// CHECK: [[TYPE_CHAR:!.*]] = metadata !{metadata !"omnipotent char", metadata
+// CHECK: [[TYPE_INT:!.*]] = metadata !{metadata !"int", metadata [[TYPE_CHAR]], i64 0}
+// CHECK: [[TAG_A_i32]] = metadata !{metadata [[TYPE_A:!.*]], metadata [[TYPE_INT]], i64 0}
+// CHECK: [[TYPE_A]] = metadata !{metadata !"?AUStructA@@", metadata [[TYPE_INT]], i64 0}