Emit stub debug info for generated functions to work around LLVM bug 2172.

This commit is contained in:
Christian Kamm 2008-10-12 14:38:55 +02:00
parent c2f17bda87
commit b413b9aa54
3 changed files with 103 additions and 2 deletions

View file

@ -149,6 +149,28 @@ static LLGlobalVariable* dwarfCompileUnit(Module* m)
//////////////////////////////////////////////////////////////////////////////////////////////////
static LLGlobalVariable* dwarfSubProgram(llvm::GlobalVariable* emitUnit, llvm::GlobalVariable* defineUnit, const char* prettyname, const char* mangledname, uint linenum, bool isprivate)
{
std::vector<LLConstant*> vals(11);
vals[0] = DBG_TAG(DW_TAG_subprogram);
vals[1] = DBG_CAST(getDwarfAnchor(DW_TAG_subprogram));
vals[2] = DBG_CAST(emitUnit);
vals[3] = DtoConstStringPtr(prettyname, "llvm.metadata");
vals[4] = vals[3];
vals[5] = DtoConstStringPtr(mangledname, "llvm.metadata");
vals[6] = DBG_CAST(defineUnit);
vals[7] = DtoConstUint(linenum);
vals[8] = DBG_NULL;
vals[9] = DtoConstBool(isprivate);
vals[10] = DtoConstBool(emitUnit == defineUnit);
Logger::println("emitting subprogram global");
return emitDwarfGlobal(getDwarfSubProgramType(), vals, "llvm.dbg.subprogram");
}
/*
static LLGlobalVariable* dwarfSubProgram(FuncDeclaration* fd, llvm::GlobalVariable* compileUnit)
{
std::vector<LLConstant*> vals(11);
@ -168,7 +190,7 @@ static LLGlobalVariable* dwarfSubProgram(FuncDeclaration* fd, llvm::GlobalVariab
Logger::println("emitting subprogram global");
return emitDwarfGlobal(getDwarfSubProgramType(), vals, "llvm.dbg.subprogram");
}
}*/
//////////////////////////////////////////////////////////////////////////////////////////////////
@ -648,7 +670,28 @@ LLGlobalVariable* DtoDwarfSubProgram(FuncDeclaration* fd)
LOG_SCOPE;
// FIXME: duplicates ?
return dwarfSubProgram(fd, DtoDwarfCompileUnit(gIR->dmodule));
return dwarfSubProgram(
DtoDwarfCompileUnit(gIR->dmodule),
DtoDwarfCompileUnit(fd->getModule()),
fd->toPrettyChars(), fd->mangle(),
fd->loc.linnum,
fd->protection == PROTprivate);
}
//////////////////////////////////////////////////////////////////////////////////////////////////
LLGlobalVariable* DtoDwarfSubProgramInternal(const char* prettyname, const char* mangledname)
{
Logger::println("D to dwarf subprogram");
LOG_SCOPE;
// FIXME: duplicates ?
return dwarfSubProgram(
DtoDwarfCompileUnit(gIR->dmodule),
DtoDwarfCompileUnit(gIR->dmodule),
prettyname, mangledname,
0,
true);
}
//////////////////////////////////////////////////////////////////////////////////////////////////

View file

@ -17,6 +17,14 @@ llvm::GlobalVariable* DtoDwarfCompileUnit(Module* m);
*/
llvm::GlobalVariable* DtoDwarfSubProgram(FuncDeclaration* fd);
/**
* Emit the Dwarf subprogram global for a internal function.
* This is used for generated functions like moduleinfoctors,
* module ctors/dtors and unittests.
* @return the Dwarf subprogram global.
*/
llvm::GlobalVariable* DtoDwarfSubProgramInternal(const char* prettyname, const char* mangledname);
void DtoDwarfFuncStart(FuncDeclaration* fd);
void DtoDwarfFuncEnd(FuncDeclaration* fd);

View file

@ -449,6 +449,12 @@ void assemble(const llvm::sys::Path& asmpath, const llvm::sys::Path& objpath, ch
/* ================================================================== */
// the following code generates functions and needs to output
// debug info. these macros are useful for that
#define DBG_TYPE ( getPtrToType(llvm::StructType::get(NULL,NULL)) )
#define DBG_CAST(X) ( llvm::ConstantExpr::getBitCast(X, DBG_TYPE) )
// build module ctor
llvm::Function* build_module_ctor()
@ -473,12 +479,23 @@ llvm::Function* build_module_ctor()
llvm::BasicBlock* bb = llvm::BasicBlock::Create("entry", fn);
IRBuilder<> builder(bb);
// debug info
LLGlobalVariable* subprog;
if(global.params.symdebug) {
subprog = DtoDwarfSubProgramInternal(name.c_str(), name.c_str());
builder.CreateCall(gIR->module->getFunction("llvm.dbg.func.start"), DBG_CAST(subprog));
}
for (size_t i=0; i<n; i++) {
llvm::Function* f = gIR->ctors[i]->ir.irFunc->func;
llvm::CallInst* call = builder.CreateCall(f,"");
call->setCallingConv(llvm::CallingConv::Fast);
}
// debug info end
if(global.params.symdebug)
builder.CreateCall(gIR->module->getFunction("llvm.dbg.region.end"), DBG_CAST(subprog));
builder.CreateRetVoid();
return fn;
}
@ -507,12 +524,23 @@ static llvm::Function* build_module_dtor()
llvm::BasicBlock* bb = llvm::BasicBlock::Create("entry", fn);
IRBuilder<> builder(bb);
// debug info
LLGlobalVariable* subprog;
if(global.params.symdebug) {
subprog = DtoDwarfSubProgramInternal(name.c_str(), name.c_str());
builder.CreateCall(gIR->module->getFunction("llvm.dbg.func.start"), DBG_CAST(subprog));
}
for (size_t i=0; i<n; i++) {
llvm::Function* f = gIR->dtors[i]->ir.irFunc->func;
llvm::CallInst* call = builder.CreateCall(f,"");
call->setCallingConv(llvm::CallingConv::Fast);
}
// debug info end
if(global.params.symdebug)
builder.CreateCall(gIR->module->getFunction("llvm.dbg.region.end"), DBG_CAST(subprog));
builder.CreateRetVoid();
return fn;
}
@ -541,12 +569,23 @@ static llvm::Function* build_module_unittest()
llvm::BasicBlock* bb = llvm::BasicBlock::Create("entry", fn);
IRBuilder<> builder(bb);
// debug info
LLGlobalVariable* subprog;
if(global.params.symdebug) {
subprog = DtoDwarfSubProgramInternal(name.c_str(), name.c_str());
builder.CreateCall(gIR->module->getFunction("llvm.dbg.func.start"), DBG_CAST(subprog));
}
for (size_t i=0; i<n; i++) {
llvm::Function* f = gIR->unitTests[i]->ir.irFunc->func;
llvm::CallInst* call = builder.CreateCall(f,"");
call->setCallingConv(llvm::CallingConv::Fast);
}
// debug info end
if(global.params.symdebug)
builder.CreateCall(gIR->module->getFunction("llvm.dbg.region.end"), DBG_CAST(subprog));
builder.CreateRetVoid();
return fn;
}
@ -587,6 +626,13 @@ static LLFunction* build_module_reference_and_ctor(LLConstant* moduleinfo)
llvm::BasicBlock* bb = llvm::BasicBlock::Create("moduleinfoCtorEntry", ctor);
IRBuilder<> builder(bb);
// debug info
LLGlobalVariable* subprog;
if(global.params.symdebug) {
subprog = DtoDwarfSubProgramInternal(fname.c_str(), fname.c_str());
builder.CreateCall(gIR->module->getFunction("llvm.dbg.func.start"), DBG_CAST(subprog));
}
// get current beginning
LLValue* curbeg = builder.CreateLoad(mref, "current");
@ -597,6 +643,10 @@ static LLFunction* build_module_reference_and_ctor(LLConstant* moduleinfo)
// replace beginning
builder.CreateStore(thismref, mref);
// debug info end
if(global.params.symdebug)
builder.CreateCall(gIR->module->getFunction("llvm.dbg.region.end"), DBG_CAST(subprog));
// return
builder.CreateRetVoid();