]> granicus.if.org Git - clang/commitdiff
Experimental TBAA support for enum types.
authorDan Gohman <gohman@apple.com>
Fri, 15 Oct 2010 20:23:12 +0000 (20:23 +0000)
committerDan Gohman <gohman@apple.com>
Fri, 15 Oct 2010 20:23:12 +0000 (20:23 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@116613 91177308-0d34-0410-b5e6-96231b3b80d8

lib/CodeGen/CodeGenModule.cpp
lib/CodeGen/CodeGenTBAA.cpp
lib/CodeGen/CodeGenTBAA.h

index d71c74b8e3e6e51531919a90db6fdbf7b498eb3c..175c27b4c602fad9d2a6860d099e34f0ff240795 100644 (file)
@@ -83,7 +83,8 @@ CodeGenModule::CodeGenModule(ASTContext &C, const CodeGenOptions &CGO,
 
   // Enable TBAA unless it's suppressed.
   if (!CodeGenOpts.RelaxedAliasing && CodeGenOpts.OptimizationLevel > 0)
-    TBAA = new CodeGenTBAA(Context, VMContext, getLangOptions());
+    TBAA = new CodeGenTBAA(Context, VMContext, getLangOptions(),
+                           ABI.getMangleContext());
 
   // If debug info generation is enabled, create the CGDebugInfo object.
   DebugInfo = CodeGenOpts.DebugInfo ? new CGDebugInfo(*this) : 0;
index f9082fc9170fb034f49e6fc24d6214595eef522b..99a58a74575bc2a9a5732e6e3b1e86f97ef79971 100644 (file)
@@ -12,6 +12,7 @@
 //===----------------------------------------------------------------------===//
 
 #include "CodeGenTBAA.h"
+#include "Mangle.h"
 #include "clang/AST/ASTContext.h"
 #include "llvm/LLVMContext.h"
 #include "llvm/Metadata.h"
@@ -19,14 +20,15 @@ using namespace clang;
 using namespace CodeGen;
 
 CodeGenTBAA::CodeGenTBAA(ASTContext &Ctx, llvm::LLVMContext& VMContext,
-                         const LangOptions &Features)
-  : Context(Ctx), VMContext(VMContext), Features(Features), Root(0), Char(0) {
+                         const LangOptions &Features, MangleContext &MContext)
+  : Context(Ctx), VMContext(VMContext), Features(Features), MContext(MContext),
+    Root(0), Char(0) {
 }
 
 CodeGenTBAA::~CodeGenTBAA() {
 }
 
-llvm::MDNode *CodeGenTBAA::getTBAAInfoForNamedType(const char *NameStr,
+llvm::MDNode *CodeGenTBAA::getTBAAInfoForNamedType(llvm::StringRef NameStr,
                                                    llvm::MDNode *Parent) {
   llvm::Value *Ops[] = {
     llvm::MDString::get(VMContext, NameStr),
@@ -85,6 +87,32 @@ CodeGenTBAA::getTBAAInfo(QualType QTy) {
   if (Ty->isPointerType())
     return MetadataCache[Ty] = getTBAAInfoForNamedType("TBAA.pointer", Char);
 
+  // Enum types are distinct types. In C++ they have "underlying types",
+  // however they aren't related for TBAA.
+  if (const EnumType *ETy = dyn_cast<EnumType>(Ty)) {
+    // In C mode, two anonymous enums are compatible iff their members
+    // are the same -- see C99 6.2.7p1. For now, be conservative. We could
+    // theoretically implement this by combining information about all the
+    // members into a single identifying MDNode.
+    if (!Features.CPlusPlus &&
+        ETy->getDecl()->getTypedefForAnonDecl())
+      return MetadataCache[Ty] = Char;
+
+    // In C++ mode, types have linkage, so we can rely on the ODR and
+    // on their mangled names, if they're external.
+    // TODO: Is there a way to get a program-wide unique name for a
+    // decl with local linkage or no linkage?
+    if (Features.CPlusPlus &&
+        ETy->getDecl()->getLinkage() != ExternalLinkage)
+      return MetadataCache[Ty] = Char;
+
+    // TODO: This is using the RTTI name. Is there a better way to get
+    // a unique string for a type?
+    llvm::SmallString<256> OutName;
+    MContext.mangleCXXRTTIName(QualType(ETy, 0), OutName);
+    return MetadataCache[Ty] = getTBAAInfoForNamedType(OutName, Char);
+  }
+
   // For now, handle any other kind of type conservatively.
   return MetadataCache[Ty] = Char;
 }
index 8cfad3b6175affc99ab927143fe7cb7215d279e5..cdb910be155c8271a7225e5af548829785d89840 100644 (file)
@@ -29,7 +29,7 @@ namespace clang {
   class Type;
 
 namespace CodeGen {
-  class CGCXXABI;
+  class MangleContext;
   class CGRecordLayout;
 
 /// CodeGenTBAA - This class organizes the cross-module state that is used
@@ -38,6 +38,7 @@ class CodeGenTBAA {
   ASTContext &Context;
   llvm::LLVMContext& VMContext;
   const LangOptions &Features;
+  MangleContext &MContext;
 
   /// MetadataCache - This maps clang::Types to llvm::MDNodes describing them.
   llvm::DenseMap<const Type *, llvm::MDNode *> MetadataCache;
@@ -50,12 +51,13 @@ class CodeGenTBAA {
   /// considered to be equivalent to it.
   llvm::MDNode *Char;
 
-  llvm::MDNode *getTBAAInfoForNamedType(const char *NameStr,
+  llvm::MDNode *getTBAAInfoForNamedType(llvm::StringRef NameStr,
                                         llvm::MDNode *Parent);
 
 public:
   CodeGenTBAA(ASTContext &Ctx, llvm::LLVMContext &VMContext,
-              const LangOptions &Features);
+              const LangOptions &Features,
+              MangleContext &MContext);
   ~CodeGenTBAA();
 
   llvm::MDNode *getTBAAInfo(QualType QTy);