Refactor fetching file/line info from DWARFContext to simplify the

code and allow better code reuse. Make the code a bit more conforming
to LLVM code style.
No functionality change.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@162895 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Alexey Samsonov
2012-08-30 07:49:50 +00:00
parent 6b1e1d8b3d
commit 38a6381c0a
4 changed files with 127 additions and 63 deletions

View File

@ -145,75 +145,93 @@ namespace {
};
}
DWARFCompileUnit *DWARFContext::getCompileUnitForOffset(uint32_t offset) {
DWARFCompileUnit *DWARFContext::getCompileUnitForOffset(uint32_t Offset) {
if (CUs.empty())
parseCompileUnits();
DWARFCompileUnit *i = std::lower_bound(CUs.begin(), CUs.end(), offset,
OffsetComparator());
if (i != CUs.end())
return &*i;
DWARFCompileUnit *CU = std::lower_bound(CUs.begin(), CUs.end(), Offset,
OffsetComparator());
if (CU != CUs.end())
return &*CU;
return 0;
}
DILineInfo DWARFContext::getLineInfoForAddress(uint64_t address,
DILineInfoSpecifier specifier) {
DWARFCompileUnit *DWARFContext::getCompileUnitForAddress(uint64_t Address) {
// First, get the offset of the compile unit.
uint32_t cuOffset = getDebugAranges()->findAddress(address);
uint32_t CUOffset = getDebugAranges()->findAddress(Address);
// Retrieve the compile unit.
DWARFCompileUnit *cu = getCompileUnitForOffset(cuOffset);
if (!cu)
return getCompileUnitForOffset(CUOffset);
}
static bool getFileNameForCompileUnit(
DWARFCompileUnit *CU, const DWARFDebugLine::LineTable *LineTable,
uint64_t FileIndex, bool NeedsAbsoluteFilePath, std::string &FileName) {
if (CU == 0 ||
LineTable == 0 ||
!LineTable->getFileNameByIndex(FileIndex, NeedsAbsoluteFilePath,
FileName))
return false;
if (NeedsAbsoluteFilePath && sys::path::is_relative(FileName)) {
// We may still need to append compilation directory of compile unit.
SmallString<16> AbsolutePath;
if (const char *CompilationDir = CU->getCompilationDir()) {
sys::path::append(AbsolutePath, CompilationDir);
}
sys::path::append(AbsolutePath, FileName);
FileName = AbsolutePath.str();
}
return true;
}
bool
DWARFContext::getFileLineInfoForCompileUnit(DWARFCompileUnit *CU,
uint64_t Address,
bool NeedsAbsoluteFilePath,
std::string &FileName,
uint32_t &Line, uint32_t &Column) {
// Get the line table for this compile unit.
const DWARFDebugLine::LineTable *LineTable = getLineTableForCompileUnit(CU);
if (!LineTable)
return false;
// Get the index of row we're looking for in the line table.
uint32_t RowIndex = LineTable->lookupAddress(Address);
if (RowIndex == -1U)
return false;
// Take file number and line/column from the row.
const DWARFDebugLine::Row &Row = LineTable->Rows[RowIndex];
if (!getFileNameForCompileUnit(CU, LineTable, Row.File,
NeedsAbsoluteFilePath, FileName))
return false;
Line = Row.Line;
Column = Row.Column;
return true;
}
DILineInfo DWARFContext::getLineInfoForAddress(uint64_t Address,
DILineInfoSpecifier Specifier) {
DWARFCompileUnit *CU = getCompileUnitForAddress(Address);
if (!CU)
return DILineInfo();
SmallString<16> fileName("<invalid>");
SmallString<16> functionName("<invalid>");
uint32_t line = 0;
uint32_t column = 0;
if (specifier.needs(DILineInfoSpecifier::FunctionName)) {
const DWARFDebugInfoEntryMinimal *function_die =
cu->getFunctionDIEForAddress(address);
if (function_die) {
if (const char *name = function_die->getSubprogramName(cu))
functionName = name;
std::string FileName = "<invalid>";
std::string FunctionName = "<invalid>";
uint32_t Line = 0;
uint32_t Column = 0;
if (Specifier.needs(DILineInfoSpecifier::FunctionName)) {
const DWARFDebugInfoEntryMinimal *FunctionDIE =
CU->getFunctionDIEForAddress(Address);
if (FunctionDIE) {
if (const char *Name = FunctionDIE->getSubprogramName(CU))
FunctionName = Name;
}
}
if (specifier.needs(DILineInfoSpecifier::FileLineInfo)) {
// Get the line table for this compile unit.
const DWARFDebugLine::LineTable *lineTable = getLineTableForCompileUnit(cu);
if (lineTable) {
// Get the index of the row we're looking for in the line table.
uint32_t rowIndex = lineTable->lookupAddress(address);
if (rowIndex != -1U) {
const DWARFDebugLine::Row &row = lineTable->Rows[rowIndex];
// Take file/line info from the line table.
const DWARFDebugLine::FileNameEntry &fileNameEntry =
lineTable->Prologue.FileNames[row.File - 1];
fileName = fileNameEntry.Name;
if (specifier.needs(DILineInfoSpecifier::AbsoluteFilePath) &&
sys::path::is_relative(fileName.str())) {
// Append include directory of file (if it is present in line table)
// and compilation directory of compile unit to make path absolute.
const char *includeDir = 0;
if (uint64_t includeDirIndex = fileNameEntry.DirIdx) {
includeDir = lineTable->Prologue
.IncludeDirectories[includeDirIndex - 1];
}
SmallString<16> absFileName;
if (includeDir == 0 || sys::path::is_relative(includeDir)) {
if (const char *compilationDir = cu->getCompilationDir())
sys::path::append(absFileName, compilationDir);
}
if (includeDir) {
sys::path::append(absFileName, includeDir);
}
sys::path::append(absFileName, fileName.str());
fileName = absFileName;
}
line = row.Line;
column = row.Column;
}
}
if (Specifier.needs(DILineInfoSpecifier::FileLineInfo)) {
const bool NeedsAbsoluteFilePath =
Specifier.needs(DILineInfoSpecifier::AbsoluteFilePath);
getFileLineInfoForCompileUnit(CU, Address, NeedsAbsoluteFilePath,
FileName, Line, Column);
}
return DILineInfo(fileName, functionName, line, column);
return DILineInfo(StringRef(FileName), StringRef(FunctionName),
Line, Column);
}
void DWARFContextInMemory::anchor() { }