Changes in directory llvm/lib/CodeGen:
DwarfWriter.cpp updated: 1.53 -> 1.54 MachineDebugInfo.cpp updated: 1.36 -> 1.37 PrologEpilogInserter.cpp updated: 1.52 -> 1.53 --- Log message: Foundation for call frame information. --- Diffs of the changes: (+153 -43) DwarfWriter.cpp | 153 +++++++++++++++++++++++++++++++++++++---------- MachineDebugInfo.cpp | 37 +++++++---- PrologEpilogInserter.cpp | 6 + 3 files changed, 153 insertions(+), 43 deletions(-) Index: llvm/lib/CodeGen/DwarfWriter.cpp diff -u llvm/lib/CodeGen/DwarfWriter.cpp:1.53 llvm/lib/CodeGen/DwarfWriter.cpp:1.54 --- llvm/lib/CodeGen/DwarfWriter.cpp:1.53 Tue Mar 28 08:58:32 2006 +++ llvm/lib/CodeGen/DwarfWriter.cpp Fri Apr 7 11:34:45 2006 @@ -18,6 +18,7 @@ #include "llvm/Type.h" #include "llvm/CodeGen/AsmPrinter.h" #include "llvm/CodeGen/MachineDebugInfo.h" +#include "llvm/CodeGen/MachineFrameInfo.h" #include "llvm/CodeGen/MachineLocation.h" #include "llvm/Support/Dwarf.h" #include "llvm/Support/CommandLine.h" @@ -1073,8 +1074,6 @@ if (Asm->Data64bitsDirective) { O << Asm->Data64bitsDirective << "0x" << std::hex << Value << std::dec; } else { - const TargetData &TD = Asm->TM.getTargetData(); - if (TD.isBigEndian()) { EmitInt32(unsigned(Value >> 32)); O << "\n"; EmitInt32(unsigned(Value)); @@ -1216,12 +1215,14 @@ /// AddAddress - Add an address attribute to a die based on the location /// provided. void DwarfWriter::AddAddress(DIE *Die, unsigned Attribute, - MachineLocation &Location) { + const MachineLocation &Location) { DIEBlock *Block = new DIEBlock(); if (Location.isRegister()) { - Block->AddUInt(DW_FORM_data1, DW_OP_reg0 + Location.getRegister()); + Block->AddUInt(DW_FORM_data1, + DW_OP_reg0 + RI->getDwarfRegNum(Location.getRegister())); } else { - Block->AddUInt(DW_FORM_data1, DW_OP_breg0 + Location.getRegister()); + Block->AddUInt(DW_FORM_data1, + DW_OP_breg0 + RI->getDwarfRegNum(Location.getRegister())); Block->AddUInt(DW_FORM_sdata, Location.getOffset()); } Block->ComputeSize(*this); @@ -1358,8 +1359,7 @@ // Now normalize offset to the field. Offset -= FieldOffset; - // Maybe we need to work from the other. - const TargetData &TD = Asm->TM.getTargetData(); + // Maybe we need to work from the other end. if (TD.isLittleEndian()) Offset = FieldSize - (Offset + Size); Member->AddUInt(DW_AT_byte_size, 0, FieldSize >> 3); @@ -1515,8 +1515,11 @@ DIE *SubprogramDie = new DIE(DW_TAG_subprogram); SubprogramDie->AddString (DW_AT_name, DW_FORM_string, Name); - SubprogramDie->AddDIEntry (DW_AT_type, DW_FORM_ref4, Type); - SubprogramDie->AddUInt (DW_AT_external, DW_FORM_flag, IsExternal); + if (Type) { + SubprogramDie->AddDIEntry (DW_AT_type, DW_FORM_ref4, Type); + } + SubprogramDie->AddUInt (DW_AT_external, DW_FORM_flag, IsExternal); + SubprogramDie->AddUInt (DW_AT_prototyped, DW_FORM_flag, 1); // Add source line info if available. AddSourceLine(SubprogramDie, UnitDesc, SPD->getLine()); @@ -1561,7 +1564,7 @@ // Add variable address. MachineLocation Location; - Asm->TM.getRegisterInfo()->getLocation(*MF, DV->getFrameIndex(), Location); + RI->getLocation(*MF, DV->getFrameIndex(), Location); AddAddress(VariableDie, DW_AT_location, Location); return VariableDie; @@ -1621,18 +1624,20 @@ // Get the compile unit context. CompileUnitDesc *UnitDesc = static_cast<CompileUnitDesc *>(SPD->getContext()); - CompileUnit *Unit = FindCompileUnit(UnitDesc); + CompileUnit *Unit = FindCompileUnit(UnitDesc); + + // Generate the mangled name. + std::string MangledName = Asm->Mang->getValueName(MF->getFunction()); // Get the subprogram die. DIE *SPDie = Unit->getDieMapSlotFor(SPD); assert(SPDie && "Missing subprogram descriptor"); // Add the function bounds. - SPDie->AddLabel(DW_AT_low_pc, DW_FORM_addr, - DWLabel("func_begin", SubprogramCount)); + SPDie->AddObjectLabel(DW_AT_low_pc, DW_FORM_addr, MangledName); SPDie->AddLabel(DW_AT_high_pc, DW_FORM_addr, DWLabel("func_end", SubprogramCount)); - MachineLocation Location(Asm->TM.getRegisterInfo()->getFrameRegister(*MF)); + MachineLocation Location(RI->getFrameRegister(*MF)); AddAddress(SPDie, DW_AT_frame_base, Location); ConstructScope(RootScope, SPDie, Unit); @@ -1792,6 +1797,50 @@ } } +/// EmitFrameMoves - Emit frame instructions to describe the layout of the +/// frame. +void DwarfWriter::EmitFrameMoves(const char *BaseLabel, unsigned BaseLabelID, + std::vector<MachineMove *> &Moves) { + for (unsigned i = 0, N = Moves.size(); i < N; ++i) { + MachineMove *Move = Moves[i]; + unsigned LabelID = Move->getLabelID(); + const MachineLocation &Dst = Move->getDestination(); + const MachineLocation &Src = Move->getSource(); + + // Advance row if new location. + if (BaseLabel && LabelID && BaseLabelID != LabelID) { + EmitULEB128Bytes(DW_CFA_advance_loc4); + EOL("DW_CFA_advance_loc4"); + EmitDifference("loc", LabelID, BaseLabel, BaseLabelID); + EOL(""); + + BaseLabelID = LabelID; + BaseLabel = "loc"; + } + + // If advancing cfa. + if (Dst.isRegister() && Dst.getRegister() == MachineLocation::VirtualFP) { + if (!Src.isRegister()) { + if (Src.getRegister() == MachineLocation::VirtualFP) { + EmitULEB128Bytes(DW_CFA_def_cfa_offset); + EOL("DW_CFA_def_cfa_offset"); + } else { + EmitULEB128Bytes(DW_CFA_def_cfa); + EOL("DW_CFA_def_cfa"); + + EmitULEB128Bytes(RI->getDwarfRegNum(Src.getRegister())); + EOL("Register"); + } + + EmitULEB128Bytes(Src.getOffset() / RI->getStackDirection()); + EOL("Offset"); + } else { + } + } else { + } + } +} + /// EmitDebugInfo - Emit the debug info section. /// void DwarfWriter::EmitDebugInfo() const { @@ -1999,10 +2048,10 @@ O << "\n"; } -/// EmitDebugFrame - Emit visible names into a debug frame section. +/// EmitInitialDebugFrame - Emit common frame info into a debug frame section. /// -void DwarfWriter::EmitDebugFrame() { - // Start the dwarf pubnames section. +void DwarfWriter::EmitInitialDebugFrame() { + // Start the dwarf frame section. Asm->SwitchSection(DwarfFrameSection, 0); EmitDifference("frame_common_end", 0, @@ -2014,20 +2063,49 @@ EmitInt8(DW_CIE_VERSION); EOL("CIE Version"); EmitString(""); EOL("CIE Augmentation"); EmitULEB128Bytes(1); EOL("CIE Code Alignment Factor"); - // FIXME - needs to change based on stack direction. - EmitSLEB128Bytes(-sizeof(int32_t)); EOL("CIE Data Alignment Factor"); - // FIXME - hard coded for PPC (LR). - EmitInt8(0x41); EOL("CIE RA Column Hardcoded (PPC LR)"); - // FIXME - hard coded for PPC 0(SP). - EmitULEB128Bytes(DW_CFA_def_cfa); EOL("DW_CFA_def_cfa"); - EmitULEB128Bytes(1); EOL("PPC Register SP"); - EmitULEB128Bytes(0); EOL("PPC offset 0 as in 0(SP)"); + EmitSLEB128Bytes(RI->getStackDirection()); EOL("CIE Data Alignment Factor"); + EmitInt8(RI->getDwarfRegNum(RI->getRARegister())); EOL("CIE RA Column"); + + std::vector<MachineMove *> Moves; + RI->getInitialFrameState(Moves); + EmitFrameMoves(NULL, 0, Moves); + for (unsigned i = 0, N = Moves.size(); i < N; ++i) delete Moves[i]; + EmitAlign(2); EmitLabel("frame_common_end", 0); O << "\n"; } +/// EmitFunctionDebugFrame - Emit per function frame info into a debug frame +/// section. +void DwarfWriter::EmitFunctionDebugFrame() { + // Start the dwarf frame section. + Asm->SwitchSection(DwarfFrameSection, 0); + + EmitDifference("frame_end", SubprogramCount, + "frame_begin", SubprogramCount); + EOL("Length of Frame Information Entry"); + + EmitLabel("frame_begin", SubprogramCount); + + EmitReference("section_frame", 0); EOL("FDE CIE offset"); + + EmitReference("func_begin", SubprogramCount); EOL("FDE initial location"); + EmitDifference("func_end", SubprogramCount, + "func_begin", SubprogramCount); + EOL("FDE address range"); + + std::vector<MachineMove *> &Moves = DebugInfo->getFrameMoves(); + + EmitFrameMoves("func_begin", SubprogramCount, Moves); + + EmitAlign(2); + EmitLabel("frame_end", SubprogramCount); + + O << "\n"; +} + /// EmitDebugPubNames - Emit visible names into a debug pubnames section. /// void DwarfWriter::EmitDebugPubNames() { @@ -2208,6 +2286,9 @@ if (!didInitial) { EmitInitial(); + // Emit common frame information. + EmitInitialDebugFrame(); + // Create all the compile unit DIEs. ConstructCompileUnitDIEs(); @@ -2231,6 +2312,8 @@ DwarfWriter::DwarfWriter(std::ostream &OS, AsmPrinter *A) : O(OS) , Asm(A) +, TD(Asm->TM.getTargetData()) +, RI(Asm->TM.getRegisterInfo()) , M(NULL) , MF(NULL) , DebugInfo(NULL) @@ -2267,6 +2350,12 @@ } } +/// SetDebugInfo - Set DebugInfo when it's known that pass manager has +/// created it. Set by the target AsmPrinter. +void DwarfWriter::SetDebugInfo(MachineDebugInfo *DI) { + DebugInfo = DI; +} + /// BeginModule - Emit all Dwarf sections that should come prior to the content. /// void DwarfWriter::BeginModule(Module *M) { @@ -2300,9 +2389,6 @@ // Emit source line correspondence into a debug line section. EmitDebugLines(); - // Emit info into a debug frame section. - EmitDebugFrame(); - // Emit info into a debug pubnames section. EmitDebugPubNames(); @@ -2327,6 +2413,9 @@ void DwarfWriter::BeginFunction(MachineFunction *MF) { this->MF = MF; + // Begin accumulating function debug information. + DebugInfo->BeginFunction(MF); + if (!ShouldEmitDwarf()) return; EOL("Dwarf Begin Function"); @@ -2335,7 +2424,6 @@ EmitLabel("func_begin", ++SubprogramCount); } - /// EndFunction - Gather and emit post-function debug information. /// void DwarfWriter::EndFunction() { @@ -2348,5 +2436,10 @@ // Construct scopes for subprogram. ConstructRootScope(DebugInfo->getRootScope()); - DebugInfo->ClearScopes(); + + // Emit function frame information. + EmitFunctionDebugFrame(); + + // Clear function debug information. + DebugInfo->EndFunction(); } Index: llvm/lib/CodeGen/MachineDebugInfo.cpp diff -u llvm/lib/CodeGen/MachineDebugInfo.cpp:1.36 llvm/lib/CodeGen/MachineDebugInfo.cpp:1.37 --- llvm/lib/CodeGen/MachineDebugInfo.cpp:1.36 Mon Mar 27 19:30:18 2006 +++ llvm/lib/CodeGen/MachineDebugInfo.cpp Fri Apr 7 11:34:45 2006 @@ -10,6 +10,7 @@ #include "llvm/CodeGen/MachineDebugInfo.h" #include "llvm/Constants.h" +#include "llvm/CodeGen/MachineLocation.h" #include "llvm/DerivedTypes.h" #include "llvm/GlobalVariable.h" #include "llvm/Intrinsics.h" @@ -1424,9 +1425,8 @@ , LabelID(0) , ScopeMap() , RootScope(NULL) -{ - -} +, FrameMoves() +{} MachineDebugInfo::~MachineDebugInfo() { } @@ -1443,6 +1443,27 @@ return false; } +/// BeginFunction - Begin gathering function debug information. +/// +void MachineDebugInfo::BeginFunction(MachineFunction *MF) { + // Coming soon. +} + +/// MachineDebugInfo::EndFunction - Discard function debug information. +/// +void MachineDebugInfo::EndFunction() { + // Clean up scope information. + if (RootScope) { + delete RootScope; + ScopeMap.clear(); + RootScope = NULL; + } + + // Clean up frame info. + for (unsigned i = 0, N = FrameMoves.size(); i < N; ++i) delete FrameMoves[i]; + FrameMoves.clear(); +} + /// getDescFor - Convert a Value to a debug information descriptor. /// // FIXME - use new Value type when available. @@ -1565,14 +1586,4 @@ return Slot; } -/// ClearScopes - Delete the scope and variable info after a function is -/// completed. -void MachineDebugInfo::ClearScopes() { - if (RootScope) { - delete RootScope; - ScopeMap.clear(); - RootScope = NULL; - } -} - Index: llvm/lib/CodeGen/PrologEpilogInserter.cpp diff -u llvm/lib/CodeGen/PrologEpilogInserter.cpp:1.52 llvm/lib/CodeGen/PrologEpilogInserter.cpp:1.53 --- llvm/lib/CodeGen/PrologEpilogInserter.cpp:1.52 Mon Apr 3 16:39:57 2006 +++ llvm/lib/CodeGen/PrologEpilogInserter.cpp Fri Apr 7 11:34:45 2006 @@ -36,6 +36,12 @@ /// frame indexes with appropriate references. /// bool runOnMachineFunction(MachineFunction &Fn) { + // Get MachineDebugInfo so that we can track the construction of the + // frame. + if (MachineDebugInfo *DI = getAnalysisToUpdate<MachineDebugInfo>()) { + Fn.getFrameInfo()->setMachineDebugInfo(DI); + } + // Scan the function for modified caller saved registers and insert spill // code for any caller saved registers that are modified. Also calculate // the MaxCallFrameSize and HasCalls variables for the function's frame _______________________________________________ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits