From: Mike Stump Date: Fri, 27 Feb 2009 22:42:30 +0000 (+0000) Subject: Fix PR3612. We ensure that we add builtins to the GlobalDeclMap and X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=c136e6cf237711f9f1324637a0b2cdf6ae8e79e4;p=clang Fix PR3612. We ensure that we add builtins to the GlobalDeclMap and we ensure that things added to the module can be found even when they are not in GlobalDeclMap. The later is for increased flexibility, should someone want to do something tricky like extern "Ada" in the same module. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@65657 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/CodeGen/CodeGenModule.cpp b/lib/CodeGen/CodeGenModule.cpp index 6ebe12706b..a812ba9352 100644 --- a/lib/CodeGen/CodeGenModule.cpp +++ b/lib/CodeGen/CodeGenModule.cpp @@ -793,6 +793,8 @@ llvm::Constant *CodeGenModule::GetAddrOfFunction(const FunctionDecl *D) { // Lookup the entry, lazily creating it if necessary. llvm::GlobalValue *&Entry = GlobalDeclMap[getMangledName(D)]; + if (!Entry) + Entry = getModule().getFunction(getMangledName(D)); if (!Entry) Entry = EmitForwardFunctionDefinition(D, 0); @@ -872,14 +874,14 @@ void CodeGenModule::UpdateCompletedType(const TagDecl *TD) { /// getBuiltinLibFunction -llvm::Function *CodeGenModule::getBuiltinLibFunction(unsigned BuiltinID) { +llvm::Value *CodeGenModule::getBuiltinLibFunction(unsigned BuiltinID) { if (BuiltinID > BuiltinFunctions.size()) BuiltinFunctions.resize(BuiltinID); // Cache looked up functions. Since builtin id #0 is invalid we don't reserve // a slot for it. assert(BuiltinID && "Invalid Builtin ID"); - llvm::Function *&FunctionSlot = BuiltinFunctions[BuiltinID-1]; + llvm::Value *&FunctionSlot = BuiltinFunctions[BuiltinID-1]; if (FunctionSlot) return FunctionSlot; @@ -913,8 +915,15 @@ llvm::Function *CodeGenModule::getBuiltinLibFunction(unsigned BuiltinID) { assert(Existing == 0 && "FIXME: Name collision"); } + llvm::GlobalValue *&ExitingFn = GlobalDeclMap[getContext().Idents.get(Name).getName()]; + if (ExitingFn) { + llvm::Function *Fn = dyn_cast(ExitingFn); + assert(Fn && "builting mixing with non-function"); + return FunctionSlot = llvm::ConstantExpr::getBitCast(Fn, Ty); + } + // FIXME: param attributes for sext/zext etc. - return FunctionSlot = + return FunctionSlot = ExitingFn = llvm::Function::Create(Ty, llvm::Function::ExternalLinkage, Name, &getModule()); } diff --git a/lib/CodeGen/CodeGenModule.h b/lib/CodeGen/CodeGenModule.h index 3a98bb7d43..093a9b12f7 100644 --- a/lib/CodeGen/CodeGenModule.h +++ b/lib/CodeGen/CodeGenModule.h @@ -154,7 +154,7 @@ class CodeGenModule { int GlobalUniqueCount; } Block; - std::vector BuiltinFunctions; + std::vector BuiltinFunctions; public: CodeGenModule(ASTContext &C, const LangOptions &Features, llvm::Module &M, const llvm::TargetData &TD, Diagnostic &Diags, @@ -243,7 +243,7 @@ public: /// getBuiltinLibFunction - Given a builtin id for a function like /// "__builtin_fabsf", return a Function* for "fabsf". - llvm::Function *getBuiltinLibFunction(unsigned BuiltinID); + llvm::Value *getBuiltinLibFunction(unsigned BuiltinID); llvm::Function *getMemCpyFn(); llvm::Function *getMemMoveFn();