Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Make llvm-symbolizer work on Windows.
Differential Revision: http://reviews.llvm.org/D9234 Reviewed By: Alexey Samsonov llvm-svn: 235900
- Loading branch information
Zachary Turner
committed
Apr 27, 2015
1 parent
4cb2dbd
commit 20dbd0d
Showing
12 changed files
with
202 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,58 @@ | ||
//===-- PDBContext.h --------------------------------------------*- C++ -*-===// | ||
// | ||
// The LLVM Compiler Infrastructure | ||
// | ||
// This file is distributed under the University of Illinois Open Source | ||
// License. See LICENSE.TXT for details. | ||
// | ||
//===----------------------------------------------------------------------===/ | ||
|
||
#ifndef LLVM_DEBUGINFO_PDB_PDBCONTEXT_H | ||
#define LLVM_DEBUGINFO_PDB_PDBCONTEXT_H | ||
|
||
#include "llvm/DebugInfo/DIContext.h" | ||
#include "llvm/DebugInfo/PDB/IPDBSession.h" | ||
|
||
namespace llvm { | ||
|
||
namespace object { | ||
class COFFObjectFile; | ||
} | ||
|
||
/// PDBContext | ||
/// This data structure is the top level entity that deals with PDB debug | ||
/// information parsing. This data structure exists only when there is a | ||
/// need for a transparent interface to different debug information formats | ||
/// (e.g. PDB and DWARF). More control and power over the debug information | ||
/// access can be had by using the PDB interfaces directly. | ||
class PDBContext : public DIContext { | ||
|
||
PDBContext(PDBContext &) = delete; | ||
PDBContext &operator=(PDBContext &) = delete; | ||
|
||
public: | ||
PDBContext(const object::COFFObjectFile &Object, | ||
std::unique_ptr<IPDBSession> PDBSession); | ||
|
||
static bool classof(const DIContext *DICtx) { | ||
return DICtx->getKind() == CK_PDB; | ||
} | ||
|
||
void dump(raw_ostream &OS, DIDumpType DumpType = DIDT_All) override; | ||
|
||
DILineInfo getLineInfoForAddress( | ||
uint64_t Address, | ||
DILineInfoSpecifier Specifier = DILineInfoSpecifier()) override; | ||
DILineInfoTable getLineInfoForAddressRange( | ||
uint64_t Address, uint64_t Size, | ||
DILineInfoSpecifier Specifier = DILineInfoSpecifier()) override; | ||
DIInliningInfo getInliningInfoForAddress( | ||
uint64_t Address, | ||
DILineInfoSpecifier Specifier = DILineInfoSpecifier()) override; | ||
|
||
private: | ||
std::unique_ptr<IPDBSession> Session; | ||
}; | ||
} | ||
|
||
#endif |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,103 @@ | ||
//===-- PDBContext.cpp ------------------------------------------*- C++ -*-===// | ||
// | ||
// The LLVM Compiler Infrastructure | ||
// | ||
// This file is distributed under the University of Illinois Open Source | ||
// License. See LICENSE.TXT for details. | ||
// | ||
//===----------------------------------------------------------------------===/ | ||
|
||
#include "llvm/DebugInfo/PDB/PDBContext.h" | ||
#include "llvm/DebugInfo/PDB/IPDBEnumChildren.h" | ||
#include "llvm/DebugInfo/PDB/IPDBLineNumber.h" | ||
#include "llvm/DebugInfo/PDB/IPDBSourceFile.h" | ||
#include "llvm/DebugInfo/PDB/PDBSymbol.h" | ||
#include "llvm/DebugInfo/PDB/PDBSymbolFunc.h" | ||
#include "llvm/DebugInfo/PDB/PDBSymbolData.h" | ||
#include "llvm/Object/COFF.h" | ||
|
||
using namespace llvm; | ||
using namespace llvm::object; | ||
|
||
PDBContext::PDBContext(const COFFObjectFile &Object, | ||
std::unique_ptr<IPDBSession> PDBSession) | ||
: DIContext(CK_PDB), Session(std::move(PDBSession)) { | ||
uint64_t ImageBase = 0; | ||
if (Object.is64()) { | ||
const pe32plus_header *Header = nullptr; | ||
Object.getPE32PlusHeader(Header); | ||
if (Header) | ||
ImageBase = Header->ImageBase; | ||
} else { | ||
const pe32_header *Header = nullptr; | ||
Object.getPE32Header(Header); | ||
if (Header) | ||
ImageBase = static_cast<uint64_t>(Header->ImageBase); | ||
} | ||
Session->setLoadAddress(ImageBase); | ||
} | ||
|
||
void PDBContext::dump(raw_ostream &OS, DIDumpType DumpType) {} | ||
|
||
DILineInfo PDBContext::getLineInfoForAddress(uint64_t Address, | ||
DILineInfoSpecifier Specifier) { | ||
auto Symbol = Session->findSymbolByAddress(Address); | ||
|
||
uint32_t Length = 1; | ||
DILineInfo Result; | ||
if (auto Func = dyn_cast_or_null<PDBSymbolFunc>(Symbol.get())) { | ||
if (Specifier.FNKind == DINameKind::LinkageName) | ||
Result.FunctionName = Func->getUndecoratedName(); | ||
else if (Specifier.FNKind == DINameKind::ShortName) | ||
Result.FunctionName = Func->getName(); | ||
|
||
Length = Func->getLength(); | ||
} else if (auto Data = dyn_cast_or_null<PDBSymbolData>(Symbol.get())) { | ||
Length = Data->getLength(); | ||
} | ||
|
||
// If we couldn't find a symbol, then just assume 1 byte, so that we get | ||
// only the line number of the first instruction. | ||
auto LineNumbers = Session->findLineNumbersByAddress(Address, Length); | ||
if (!LineNumbers || LineNumbers->getChildCount() == 0) | ||
return Result; | ||
|
||
auto LineInfo = LineNumbers->getNext(); | ||
assert(LineInfo); | ||
auto SourceFile = Session->getSourceFileById(LineInfo->getSourceFileId()); | ||
|
||
if (SourceFile && | ||
Specifier.FLIKind != DILineInfoSpecifier::FileLineInfoKind::None) | ||
Result.FileName = SourceFile->getFileName(); | ||
Result.Column = LineInfo->getColumnNumber(); | ||
Result.Line = LineInfo->getLineNumber(); | ||
return Result; | ||
} | ||
|
||
DILineInfoTable | ||
PDBContext::getLineInfoForAddressRange(uint64_t Address, uint64_t Size, | ||
DILineInfoSpecifier Specifier) { | ||
if (Size == 0) | ||
return DILineInfoTable(); | ||
|
||
DILineInfoTable Table; | ||
auto LineNumbers = Session->findLineNumbersByAddress(Address, Size); | ||
if (!LineNumbers || LineNumbers->getChildCount() == 0) | ||
return Table; | ||
|
||
while (auto LineInfo = LineNumbers->getNext()) { | ||
DILineInfo LineEntry = | ||
getLineInfoForAddress(LineInfo->getVirtualAddress(), Specifier); | ||
Table.push_back(std::make_pair(LineInfo->getVirtualAddress(), LineEntry)); | ||
} | ||
return Table; | ||
} | ||
|
||
DIInliningInfo | ||
PDBContext::getInliningInfoForAddress(uint64_t Address, | ||
DILineInfoSpecifier Specifier) { | ||
DIInliningInfo InlineInfo; | ||
DILineInfo Frame = getLineInfoForAddress(Address, Specifier); | ||
InlineInfo.addFrame(Frame); | ||
return InlineInfo; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
// To generate the corresponding EXE/PDB, run: | ||
// cl /Zi test.c | ||
void foo() { | ||
} | ||
|
||
int main() { | ||
foo(); | ||
} |
Binary file not shown.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
0x401020 | ||
0x401030 | ||
0x500000 |
Binary file not shown.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
config.unsupported = not config.have_dia_sdk |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
RUN: llvm-symbolizer -obj="%p/Inputs/test.exe" < "%p/Inputs/test.exe.input" | FileCheck %s --check-prefix=CHECK | ||
|
||
CHECK: _foo | ||
CHECK-NEXT: test.c:3:0 | ||
CHECK: _main | ||
CHECK-NEXT: test.c:6:0 | ||
CHECK: ?? | ||
CHECK-NEXT: ??:0:0 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -5,6 +5,7 @@ | |
|
||
set(LLVM_LINK_COMPONENTS | ||
DebugInfoDWARF | ||
DebugInfoPDB | ||
Object | ||
Support | ||
) | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters