Simplify debug info intrisinc lowering.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@74733 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Devang Patel 2009-07-02 22:43:26 +00:00
parent 2f510aed9c
commit 7e1e31f467
5 changed files with 120 additions and 172 deletions

View File

@ -581,13 +581,11 @@ namespace llvm {
/// ExtractDebugLocation - Extract debug location information
/// from llvm.dbg.stoppoint intrinsic.
DebugLoc ExtractDebugLocation(DbgStopPointInst &SPI,
CodeGenOpt::Level OptLev,
DebugLocTracker &DebugLocInfo);
/// ExtractDebugLocation - Extract debug location information
/// from llvm.dbg.func_start intrinsic.
DebugLoc ExtractDebugLocation(DbgFuncStartInst &FSI,
CodeGenOpt::Level OptLev,
DebugLocTracker &DebugLocInfo);
/// isInlinedFnStart - Return true if FSI is starting an inlined function.

View File

@ -356,6 +356,9 @@ public:
/// setDefaultDebugLoc - Get the default debug location for the machine
/// function.
void setDefaultDebugLoc(DebugLoc DL) { DefaultDebugLoc = DL; }
/// getDebugLocInfo - Get the debug info location tracker.
DebugLocTracker &getDebugLocInfo() { return DebugLocInfo; }
};
//===--------------------------------------------------------------------===//

View File

@ -1091,12 +1091,9 @@ namespace llvm {
/// ExtractDebugLocation - Extract debug location information
/// from llvm.dbg.stoppoint intrinsic.
DebugLoc ExtractDebugLocation(DbgStopPointInst &SPI,
CodeGenOpt::Level OptLev,
DebugLocTracker &DebugLocInfo) {
DebugLoc DL;
Value *Context = SPI.getContext();
if (DIDescriptor::ValidDebugInfo(Context, OptLev) == false)
return DL;
// If this location is already tracked then use it.
DebugLocTuple Tuple(cast<GlobalVariable>(Context), SPI.getLine(),
@ -1117,12 +1114,9 @@ namespace llvm {
/// ExtractDebugLocation - Extract debug location information
/// from llvm.dbg.func_start intrinsic.
DebugLoc ExtractDebugLocation(DbgFuncStartInst &FSI,
CodeGenOpt::Level OptLev,
DebugLocTracker &DebugLocInfo) {
DebugLoc DL;
Value *SP = FSI.getSubprogram();
if (DIDescriptor::ValidDebugInfo(SP, OptLev) == false)
return DL;
DISubprogram Subprogram(cast<GlobalVariable>(SP));
unsigned Line = Subprogram.getLineNumber();

View File

@ -326,19 +326,14 @@ bool FastISel::SelectCall(User *I) {
default: break;
case Intrinsic::dbg_stoppoint: {
DbgStopPointInst *SPI = cast<DbgStopPointInst>(I);
if (DIDescriptor::ValidDebugInfo(SPI->getContext(), CodeGenOpt::None)) {
DICompileUnit CU(cast<GlobalVariable>(SPI->getContext()));
unsigned Line = SPI->getLine();
unsigned Col = SPI->getColumn();
unsigned Idx = MF.getOrCreateDebugLocID(CU.getGV(), Line, Col);
setCurDebugLoc(DebugLoc::get(Idx));
}
if (isValidDebugInfoIntrinsic(*SPI, CodeGenOpt::None))
setCurDebugLoc(ExtractDebugLocation(*SPI, MF.getDebugLocInfo()));
return true;
}
case Intrinsic::dbg_region_start: {
DbgRegionStartInst *RSI = cast<DbgRegionStartInst>(I);
if (DIDescriptor::ValidDebugInfo(RSI->getContext(), CodeGenOpt::None) &&
DW && DW->ShouldEmitDwarfDebug()) {
if (isValidDebugInfoIntrinsic(*RSI, CodeGenOpt::None) && DW
&& DW->ShouldEmitDwarfDebug()) {
unsigned ID =
DW->RecordRegionStart(cast<GlobalVariable>(RSI->getContext()));
const TargetInstrDesc &II = TII.get(TargetInstrInfo::DBG_LABEL);
@ -348,11 +343,11 @@ bool FastISel::SelectCall(User *I) {
}
case Intrinsic::dbg_region_end: {
DbgRegionEndInst *REI = cast<DbgRegionEndInst>(I);
if (DIDescriptor::ValidDebugInfo(REI->getContext(), CodeGenOpt::None) &&
DW && DW->ShouldEmitDwarfDebug()) {
if (isValidDebugInfoIntrinsic(*REI, CodeGenOpt::None) && DW
&& DW->ShouldEmitDwarfDebug()) {
unsigned ID = 0;
DISubprogram Subprogram(cast<GlobalVariable>(REI->getContext()));
if (!Subprogram.isNull() && !Subprogram.describes(MF.getFunction())) {
if (isInlinedFnEnd(*REI, MF.getFunction())) {
// This is end of an inlined function.
const TargetInstrDesc &II = TII.get(TargetInstrInfo::DBG_LABEL);
ID = DW->RecordInlinedFnEnd(Subprogram);
@ -372,19 +367,13 @@ bool FastISel::SelectCall(User *I) {
}
case Intrinsic::dbg_func_start: {
DbgFuncStartInst *FSI = cast<DbgFuncStartInst>(I);
Value *SP = FSI->getSubprogram();
if (!DIDescriptor::ValidDebugInfo(SP, CodeGenOpt::None))
if (!isValidDebugInfoIntrinsic(*FSI, CodeGenOpt::None) || !DW
|| !DW->ShouldEmitDwarfDebug())
return true;
DISubprogram Subprogram(cast<GlobalVariable>(SP));
DICompileUnit CompileUnit = Subprogram.getCompileUnit();
unsigned Line = Subprogram.getLineNumber();
// If this subprogram does not describe current function then this is
// beginning of a inlined function.
if (!Subprogram.describes(MF.getFunction())) {
if (isInlinedFnStart(*FSI, MF.getFunction())) {
// This is a beginning of an inlined function.
// If llvm.dbg.func.start is seen in a new block before any
// llvm.dbg.stoppoint intrinsic then the location info is unknown.
// FIXME : Why DebugLoc is reset at the beginning of each block ?
@ -392,59 +381,53 @@ bool FastISel::SelectCall(User *I) {
if (PrevLoc.isUnknown())
return true;
// Record the source line.
unsigned LocID = MF.getOrCreateDebugLocID(CompileUnit.getGV(), Line, 0);
setCurDebugLoc(DebugLoc::get(LocID));
if (DW && DW->ShouldEmitDwarfDebug()) {
DebugLocTuple PrevLocTpl = MF.getDebugLocTuple(PrevLoc);
unsigned LabelID = DW->RecordInlinedFnStart(Subprogram,
DICompileUnit(PrevLocTpl.CompileUnit),
PrevLocTpl.Line,
PrevLocTpl.Col);
const TargetInstrDesc &II = TII.get(TargetInstrInfo::DBG_LABEL);
BuildMI(MBB, DL, II).addImm(LabelID);
}
setCurDebugLoc(ExtractDebugLocation(*FSI, MF.getDebugLocInfo()));
DebugLocTuple PrevLocTpl = MF.getDebugLocTuple(PrevLoc);
DISubprogram SP(cast<GlobalVariable>(FSI->getSubprogram()));
unsigned LabelID = DW->RecordInlinedFnStart(SP,
DICompileUnit(PrevLocTpl.CompileUnit),
PrevLocTpl.Line,
PrevLocTpl.Col);
const TargetInstrDesc &II = TII.get(TargetInstrInfo::DBG_LABEL);
BuildMI(MBB, DL, II).addImm(LabelID);
return true;
}
// This is a beginning of a new function.
// Record the source line.
unsigned LocID = MF.getOrCreateDebugLocID(CompileUnit.getGV(), Line, 0);
MF.setDefaultDebugLoc(DebugLoc::get(LocID));
if (DW && DW->ShouldEmitDwarfDebug())
// llvm.dbg.func_start also defines beginning of function scope.
DW->RecordRegionStart(cast<GlobalVariable>(FSI->getSubprogram()));
// This is a beginning of a new function.
MF.setDefaultDebugLoc(ExtractDebugLocation(*FSI, MF.getDebugLocInfo()));
// llvm.dbg.func_start also defines beginning of function scope.
DW->RecordRegionStart(cast<GlobalVariable>(FSI->getSubprogram()));
return true;
}
case Intrinsic::dbg_declare: {
DbgDeclareInst *DI = cast<DbgDeclareInst>(I);
if (!isValidDebugInfoIntrinsic(*DI, CodeGenOpt::None) || !DW
|| !DW->ShouldEmitDwarfDebug())
return true;
Value *Variable = DI->getVariable();
if (DIDescriptor::ValidDebugInfo(Variable, CodeGenOpt::None) &&
DW && DW->ShouldEmitDwarfDebug()) {
// Determine the address of the declared object.
Value *Address = DI->getAddress();
if (BitCastInst *BCI = dyn_cast<BitCastInst>(Address))
Address = BCI->getOperand(0);
AllocaInst *AI = dyn_cast<AllocaInst>(Address);
// Don't handle byval struct arguments or VLAs, for example.
if (!AI) break;
DenseMap<const AllocaInst*, int>::iterator SI =
StaticAllocaMap.find(AI);
if (SI == StaticAllocaMap.end()) break; // VLAs.
int FI = SI->second;
// Determine the debug globalvariable.
GlobalValue *GV = cast<GlobalVariable>(Variable);
// Build the DECLARE instruction.
const TargetInstrDesc &II = TII.get(TargetInstrInfo::DECLARE);
MachineInstr *DeclareMI
= BuildMI(MBB, DL, II).addFrameIndex(FI).addGlobalAddress(GV);
DIVariable DV(cast<GlobalVariable>(GV));
DW->RecordVariableScope(DV, DeclareMI);
}
Value *Address = DI->getAddress();
if (BitCastInst *BCI = dyn_cast<BitCastInst>(Address))
Address = BCI->getOperand(0);
AllocaInst *AI = dyn_cast<AllocaInst>(Address);
// Don't handle byval struct arguments or VLAs, for example.
if (!AI) break;
DenseMap<const AllocaInst*, int>::iterator SI =
StaticAllocaMap.find(AI);
if (SI == StaticAllocaMap.end()) break; // VLAs.
int FI = SI->second;
// Determine the debug globalvariable.
GlobalValue *GV = cast<GlobalVariable>(Variable);
// Build the DECLARE instruction.
const TargetInstrDesc &II = TII.get(TargetInstrInfo::DECLARE);
MachineInstr *DeclareMI
= BuildMI(MBB, DL, II).addFrameIndex(FI).addGlobalAddress(GV);
DIVariable DV(cast<GlobalVariable>(GV));
DW->RecordVariableScope(DV, DeclareMI);
return true;
}
case Intrinsic::eh_exception: {

View File

@ -332,30 +332,14 @@ void FunctionLoweringInfo::set(Function &fn, MachineFunction &mf,
default: break;
case Intrinsic::dbg_stoppoint: {
DbgStopPointInst *SPI = cast<DbgStopPointInst>(I);
if (DIDescriptor::ValidDebugInfo(SPI->getContext(),
CodeGenOpt::Default)) {
DICompileUnit CU(cast<GlobalVariable>(SPI->getContext()));
unsigned idx = MF->getOrCreateDebugLocID(CU.getGV(),
SPI->getLine(),
SPI->getColumn());
DL = DebugLoc::get(idx);
}
if (isValidDebugInfoIntrinsic(*SPI, CodeGenOpt::Default))
DL = ExtractDebugLocation(*SPI, MF->getDebugLocInfo());
break;
}
case Intrinsic::dbg_func_start: {
DbgFuncStartInst *FSI = cast<DbgFuncStartInst>(I);
Value *SP = FSI->getSubprogram();
if (DIDescriptor::ValidDebugInfo(SP, CodeGenOpt::Default)) {
DISubprogram Subprogram(cast<GlobalVariable>(SP));
DICompileUnit CU(Subprogram.getCompileUnit());
unsigned Line = Subprogram.getLineNumber();
DL = DebugLoc::get(MF->getOrCreateDebugLocID(CU.getGV(),
Line, 0));
}
if (isValidDebugInfoIntrinsic(*FSI, CodeGenOpt::Default))
DL = ExtractDebugLocation(*FSI, MF->getDebugLocInfo());
break;
}
}
@ -3887,13 +3871,11 @@ SelectionDAGLowering::visitIntrinsicCall(CallInst &I, unsigned Intrinsic) {
}
case Intrinsic::dbg_stoppoint: {
DbgStopPointInst &SPI = cast<DbgStopPointInst>(I);
if (DIDescriptor::ValidDebugInfo(SPI.getContext(), OptLevel)) {
if (isValidDebugInfoIntrinsic(SPI, CodeGenOpt::Default)) {
MachineFunction &MF = DAG.getMachineFunction();
DICompileUnit CU(cast<GlobalVariable>(SPI.getContext()));
DebugLoc Loc = DebugLoc::get(MF.getOrCreateDebugLocID(CU.getGV(),
SPI.getLine(), SPI.getColumn()));
DebugLoc Loc = ExtractDebugLocation(SPI, MF.getDebugLocInfo());
setCurDebugLoc(Loc);
if (OptLevel == CodeGenOpt::None)
DAG.setRoot(DAG.getDbgStopPoint(Loc, getRoot(),
SPI.getLine(),
@ -3905,115 +3887,103 @@ SelectionDAGLowering::visitIntrinsicCall(CallInst &I, unsigned Intrinsic) {
case Intrinsic::dbg_region_start: {
DwarfWriter *DW = DAG.getDwarfWriter();
DbgRegionStartInst &RSI = cast<DbgRegionStartInst>(I);
if (DIDescriptor::ValidDebugInfo(RSI.getContext(), OptLevel) &&
DW && DW->ShouldEmitDwarfDebug()) {
if (isValidDebugInfoIntrinsic(RSI, OptLevel) && DW
&& DW->ShouldEmitDwarfDebug()) {
unsigned LabelID =
DW->RecordRegionStart(cast<GlobalVariable>(RSI.getContext()));
DAG.setRoot(DAG.getLabel(ISD::DBG_LABEL, getCurDebugLoc(),
getRoot(), LabelID));
}
return 0;
}
case Intrinsic::dbg_region_end: {
DwarfWriter *DW = DAG.getDwarfWriter();
DbgRegionEndInst &REI = cast<DbgRegionEndInst>(I);
if (DIDescriptor::ValidDebugInfo(REI.getContext(), OptLevel) &&
DW && DW->ShouldEmitDwarfDebug()) {
MachineFunction &MF = DAG.getMachineFunction();
DISubprogram Subprogram(cast<GlobalVariable>(REI.getContext()));
if (!isValidDebugInfoIntrinsic(REI, OptLevel) || !DW
|| !DW->ShouldEmitDwarfDebug())
return 0;
if (Subprogram.isNull() || Subprogram.describes(MF.getFunction())) {
unsigned LabelID =
DW->RecordRegionEnd(cast<GlobalVariable>(REI.getContext()));
DAG.setRoot(DAG.getLabel(ISD::DBG_LABEL, getCurDebugLoc(),
getRoot(), LabelID));
} else {
// This is end of inlined function. Debugging information for inlined
// function is not handled yet (only supported by FastISel).
if (OptLevel == CodeGenOpt::None) {
unsigned ID = DW->RecordInlinedFnEnd(Subprogram);
if (ID != 0)
// Returned ID is 0 if this is unbalanced "end of inlined
// scope". This could happen if optimizer eats dbg intrinsics or
// "beginning of inlined scope" is not recoginized due to missing
// location info. In such cases, do ignore this region.end.
DAG.setRoot(DAG.getLabel(ISD::DBG_LABEL, getCurDebugLoc(),
getRoot(), ID));
}
MachineFunction &MF = DAG.getMachineFunction();
DISubprogram Subprogram(cast<GlobalVariable>(REI.getContext()));
if (isInlinedFnEnd(REI, MF.getFunction())) {
// This is end of inlined function. Debugging information for inlined
// function is not handled yet (only supported by FastISel).
if (OptLevel == CodeGenOpt::None) {
unsigned ID = DW->RecordInlinedFnEnd(Subprogram);
if (ID != 0)
// Returned ID is 0 if this is unbalanced "end of inlined
// scope". This could happen if optimizer eats dbg intrinsics or
// "beginning of inlined scope" is not recoginized due to missing
// location info. In such cases, do ignore this region.end.
DAG.setRoot(DAG.getLabel(ISD::DBG_LABEL, getCurDebugLoc(),
getRoot(), ID));
}
}
return 0;
}
unsigned LabelID =
DW->RecordRegionEnd(cast<GlobalVariable>(REI.getContext()));
DAG.setRoot(DAG.getLabel(ISD::DBG_LABEL, getCurDebugLoc(),
getRoot(), LabelID));
return 0;
}
case Intrinsic::dbg_func_start: {
DwarfWriter *DW = DAG.getDwarfWriter();
DbgFuncStartInst &FSI = cast<DbgFuncStartInst>(I);
Value *SP = FSI.getSubprogram();
if (!DIDescriptor::ValidDebugInfo(SP, OptLevel))
if (!isValidDebugInfoIntrinsic(FSI, CodeGenOpt::None) || !DW
|| !DW->ShouldEmitDwarfDebug())
return 0;
DISubprogram Subprogram(cast<GlobalVariable>(SP));
DICompileUnit CompileUnit = Subprogram.getCompileUnit();
unsigned Line = Subprogram.getLineNumber();
MachineFunction &MF = DAG.getMachineFunction();
// If this subprogram does not describe current function then this is
// beginning of a inlined function.
bool isInlinedFnStart = !Subprogram.describes(MF.getFunction());
if (isInlinedFnStart && OptLevel != CodeGenOpt::None)
// FIXME: Debugging informaation for inlined function is only
// supported at CodeGenOpt::Node.
return 0;
if (isInlinedFnStart && OptLevel == CodeGenOpt::None) {
// This is a beginning of an inlined function.
// This is a beginning of an inlined function.
if (isInlinedFnStart(FSI, MF.getFunction())) {
if (OptLevel != CodeGenOpt::None)
// FIXME: Debugging informaation for inlined function is only
// supported at CodeGenOpt::Node.
return 0;
DebugLoc PrevLoc = CurDebugLoc;
// If llvm.dbg.func.start is seen in a new block before any
// llvm.dbg.stoppoint intrinsic then the location info is unknown.
// FIXME : Why DebugLoc is reset at the beginning of each block ?
if (PrevLoc.isUnknown())
return 0;
// Record the source line.
unsigned LocID = MF.getOrCreateDebugLocID(CompileUnit.getGV(), Line, 0);
setCurDebugLoc(DebugLoc::get(LocID));
if (DW && DW->ShouldEmitDwarfDebug()) {
DebugLocTuple PrevLocTpl = MF.getDebugLocTuple(PrevLoc);
unsigned LabelID = DW->RecordInlinedFnStart(Subprogram,
DICompileUnit(PrevLocTpl.CompileUnit),
PrevLocTpl.Line,
PrevLocTpl.Col);
DAG.setRoot(DAG.getLabel(ISD::DBG_LABEL, getCurDebugLoc(),
getRoot(), LabelID));
}
// Record the source line.
setCurDebugLoc(ExtractDebugLocation(FSI, MF.getDebugLocInfo()));
DebugLocTuple PrevLocTpl = MF.getDebugLocTuple(PrevLoc);
DISubprogram SP(cast<GlobalVariable>(FSI.getSubprogram()));
DICompileUnit CU(PrevLocTpl.CompileUnit);
unsigned LabelID = DW->RecordInlinedFnStart(SP, CU,
PrevLocTpl.Line,
PrevLocTpl.Col);
DAG.setRoot(DAG.getLabel(ISD::DBG_LABEL, getCurDebugLoc(),
getRoot(), LabelID));
return 0;
}
// This is a beginning of a new function.
// Record the source line.
unsigned LocID = MF.getOrCreateDebugLocID(CompileUnit.getGV(), Line, 0);
MF.setDefaultDebugLoc(DebugLoc::get(LocID));
MF.setDefaultDebugLoc(ExtractDebugLocation(FSI, MF.getDebugLocInfo()));
if (DW && DW->ShouldEmitDwarfDebug())
// llvm.dbg.func_start also defines beginning of function scope.
DW->RecordRegionStart(cast<GlobalVariable>(FSI.getSubprogram()));
// llvm.dbg.func_start also defines beginning of function scope.
DW->RecordRegionStart(cast<GlobalVariable>(FSI.getSubprogram()));
return 0;
}
case Intrinsic::dbg_declare: {
if (OptLevel == CodeGenOpt::None) {
DbgDeclareInst &DI = cast<DbgDeclareInst>(I);
Value *Variable = DI.getVariable();
if (DIDescriptor::ValidDebugInfo(Variable, OptLevel))
DAG.setRoot(DAG.getNode(ISD::DECLARE, dl, MVT::Other, getRoot(),
getValue(DI.getAddress()), getValue(Variable)));
} else {
// FIXME: Do something sensible here when we support debug declare.
}
if (OptLevel != CodeGenOpt::None)
// FIXME: Variable debug info is not supported here.
return 0;
DbgDeclareInst &DI = cast<DbgDeclareInst>(I);
if (!isValidDebugInfoIntrinsic(DI, CodeGenOpt::None))
return 0;
Value *Variable = DI.getVariable();
DAG.setRoot(DAG.getNode(ISD::DECLARE, dl, MVT::Other, getRoot(),
getValue(DI.getAddress()), getValue(Variable)));
return 0;
}
case Intrinsic::eh_exception: {