[cfe-commits] r99968 - in /cfe/trunk: lib/CodeGen/CGRTTI.cpp test/CodeGenCXX/rtti-linkage.cpp

Douglas Gregor dgregor at apple.com
Tue Mar 30 17:15:35 PDT 2010


Author: dgregor
Date: Tue Mar 30 19:15:35 2010
New Revision: 99968

URL: http://llvm.org/viewvc/llvm-project?rev=99968&view=rev
Log:
Drastically simplify the computation of linkage for typeinfo by using
the existing (and already well-tested) linkage computation for types,
with minor tweaks for dynamic classes and (pointers to) incomplete
types. Fixes PR6597.

Modified:
    cfe/trunk/lib/CodeGen/CGRTTI.cpp
    cfe/trunk/test/CodeGenCXX/rtti-linkage.cpp

Modified: cfe/trunk/lib/CodeGen/CGRTTI.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGRTTI.cpp?rev=99968&r1=99967&r2=99968&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CGRTTI.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGRTTI.cpp Tue Mar 30 19:15:35 2010
@@ -327,83 +327,20 @@
   if (ContainsIncompleteClassType(Ty))
     return llvm::GlobalValue::InternalLinkage;
   
-  switch (Ty->getTypeClass()) {
-  default:   
-    // FIXME: We need to add code to handle all types.
-    assert(false && "Unhandled type!");
-    break;
-
-  case Type::Pointer: {
-    const PointerType *PointerTy = cast<PointerType>(Ty);
- 
-    // If the pointee type has internal linkage, then the pointer type needs to
-    // have it as well.
-    if (getTypeInfoLinkage(PointerTy->getPointeeType()) == 
-        llvm::GlobalVariable::InternalLinkage)
-      return llvm::GlobalVariable::InternalLinkage;
-    
-    return llvm::GlobalVariable::WeakODRLinkage;
-  }
-
-  case Type::Enum: {
-    const EnumType *EnumTy = cast<EnumType>(Ty);
-    const EnumDecl *ED = EnumTy->getDecl();
-    
-    // If we're in an anonymous namespace, then we always want internal linkage.
-    if (ED->isInAnonymousNamespace() || !ED->hasLinkage())
-      return llvm::GlobalVariable::InternalLinkage;
-    
-    return llvm::GlobalValue::WeakODRLinkage;
-  }
-
-  case Type::Record: {
-    const RecordType *RecordTy = cast<RecordType>(Ty);
-    const CXXRecordDecl *RD = cast<CXXRecordDecl>(RecordTy->getDecl());
-
-    // If we're in an anonymous namespace, then we always want internal linkage.
-    if (RD->isInAnonymousNamespace() || !RD->hasLinkage())
-      return llvm::GlobalVariable::InternalLinkage;
-
-    // If this class does not have a vtable, we want weak linkage.
-    if (!RD->isDynamicClass())
-      return llvm::GlobalValue::WeakODRLinkage;
-    
-    return CodeGenModule::getVtableLinkage(RD);
-  }
-
-  case Type::Vector:
-  case Type::ExtVector:
-  case Type::Builtin:
-    return llvm::GlobalValue::WeakODRLinkage;
-
-  case Type::FunctionProto: {
-    const FunctionProtoType *FPT = cast<FunctionProtoType>(Ty);
+  switch (Ty->getLinkage()) {
+  case NoLinkage:
+  case InternalLinkage:
+  case UniqueExternalLinkage:
+    return llvm::GlobalValue::InternalLinkage;
 
-    // Check the return type.
-    if (getTypeInfoLinkage(FPT->getResultType()) == 
-        llvm::GlobalValue::InternalLinkage)
-      return llvm::GlobalValue::InternalLinkage;
-    
-    // Check the parameter types.
-    for (unsigned i = 0; i != FPT->getNumArgs(); ++i) {
-      if (getTypeInfoLinkage(FPT->getArgType(i)) == 
-          llvm::GlobalValue::InternalLinkage)
-        return llvm::GlobalValue::InternalLinkage;
+  case ExternalLinkage:
+    if (const RecordType *Record = dyn_cast<RecordType>(Ty)) {
+      const CXXRecordDecl *RD = cast<CXXRecordDecl>(Record->getDecl());
+      if (RD->isDynamicClass())
+        return CodeGenModule::getVtableLinkage(RD);
     }
-    
-    return llvm::GlobalValue::WeakODRLinkage;
-  }
-  
-  case Type::ConstantArray: 
-  case Type::IncompleteArray: {
-    const ArrayType *AT = cast<ArrayType>(Ty);
-
-    // Check the element type.
-    if (getTypeInfoLinkage(AT->getElementType()) ==
-        llvm::GlobalValue::InternalLinkage)
-      return llvm::GlobalValue::InternalLinkage;
-  }
 
+    return llvm::GlobalValue::WeakODRLinkage;
   }
 
   return llvm::GlobalValue::WeakODRLinkage;
@@ -444,8 +381,8 @@
   switch (Ty->getTypeClass()) {
   default: assert(0 && "Unhandled type!");
 
-  // GCC treats vector types as fundamental types.
   case Type::Builtin:
+  // GCC treats vector types as fundamental types.
   case Type::Vector:
   case Type::ExtVector:
     // abi::__fundamental_type_info.

Modified: cfe/trunk/test/CodeGenCXX/rtti-linkage.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenCXX/rtti-linkage.cpp?rev=99968&r1=99967&r2=99968&view=diff
==============================================================================
--- cfe/trunk/test/CodeGenCXX/rtti-linkage.cpp (original)
+++ cfe/trunk/test/CodeGenCXX/rtti-linkage.cpp Tue Mar 30 19:15:35 2010
@@ -92,6 +92,7 @@
   (void)typeid(D *);
   (void)typeid(D (*)());
   (void)typeid(void (*)(D));
+  (void)typeid(void (*)(D&));
   // The exception specification is not part of the RTTI descriptor, so it should not have
   // internal linkage.
   (void)typeid(void (*)() throw (D));





More information about the cfe-commits mailing list