[cfe-commits] r102473 - in /cfe/trunk: lib/CodeGen/CodeGenModule.cpp test/CodeGen/functions.c

John McCall rjmccall at apple.com
Tue Apr 27 17:00:30 PDT 2010


Author: rjmccall
Date: Tue Apr 27 19:00:30 2010
New Revision: 102473

URL: http://llvm.org/viewvc/llvm-project?rev=102473&view=rev
Log:
Properly pass the address of a lazily-generated function declaration with
incomplete type.  Fixes PR6911.


Modified:
    cfe/trunk/lib/CodeGen/CodeGenModule.cpp
    cfe/trunk/test/CodeGen/functions.c

Modified: cfe/trunk/lib/CodeGen/CodeGenModule.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CodeGenModule.cpp?rev=102473&r1=102472&r2=102473&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CodeGenModule.cpp (original)
+++ cfe/trunk/lib/CodeGen/CodeGenModule.cpp Tue Apr 27 19:00:30 2010
@@ -779,12 +779,16 @@
   // type is an incomplete struct). Use a fake type instead, and make
   // sure not to try to set attributes.
   bool IsIncompleteFunction = false;
-  if (!isa<llvm::FunctionType>(Ty)) {
-    Ty = llvm::FunctionType::get(llvm::Type::getVoidTy(VMContext),
-                                 std::vector<const llvm::Type*>(), false);
+
+  const llvm::FunctionType *FTy;
+  if (isa<llvm::FunctionType>(Ty)) {
+    FTy = cast<llvm::FunctionType>(Ty);
+  } else {
+    FTy = llvm::FunctionType::get(llvm::Type::getVoidTy(VMContext),
+                                  std::vector<const llvm::Type*>(), false);
     IsIncompleteFunction = true;
   }
-  llvm::Function *F = llvm::Function::Create(cast<llvm::FunctionType>(Ty),
+  llvm::Function *F = llvm::Function::Create(FTy,
                                              llvm::Function::ExternalLinkage,
                                              MangledName, &getModule());
   assert(F->getName() == MangledName && "name was uniqued!");
@@ -826,7 +830,14 @@
     }
   }
 
-  return F;
+  // Make sure the result is of the requested type.
+  if (!IsIncompleteFunction) {
+    assert(F->getType()->getElementType() == Ty);
+    return F;
+  }
+
+  const llvm::Type *PTy = llvm::PointerType::getUnqual(Ty);
+  return llvm::ConstantExpr::getBitCast(F, PTy);
 }
 
 /// GetAddrOfFunction - Return the address of the given function.  If Ty is

Modified: cfe/trunk/test/CodeGen/functions.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGen/functions.c?rev=102473&r1=102472&r2=102473&view=diff
==============================================================================
--- cfe/trunk/test/CodeGen/functions.c (original)
+++ cfe/trunk/test/CodeGen/functions.c Tue Apr 27 19:00:30 2010
@@ -47,3 +47,15 @@
 // CHECK: define void @f7(float{{.*}}, float{{.*}})
 // CHECK: call void @f6(float{{.*}}, float{{.*}})
 }
+
+// PR6911 - incomplete function types
+struct Incomplete;
+void f8_callback(struct Incomplete);
+void f8_user(void (*callback)(struct Incomplete));
+void f8_test() {
+  f8_user(&f8_callback);
+// CHECK: define void @f8_test()
+// CHECK: call void @f8_user({{.*}}* bitcast (void ()* @f8_callback to {{.*}}*))
+// CHECK: declare void @f8_user({{.*}}*)
+// CHECK: declare void @f8_callback()
+}





More information about the cfe-commits mailing list