move to LLVM 3.9

This change removes support for earlier LLVM versions; making them
work as well is simply too tedious.

Change-Id: I372a151279ceb2bfd6de101c9e0c15f0a4b18c03
This commit is contained in:
Horst Schirmeier
2018-05-03 18:58:14 +02:00
parent baaa6c3ce8
commit ff3a5fb498
17 changed files with 175 additions and 131 deletions

View File

@ -1,4 +1,4 @@
find_program(LLVMCONFIG NAMES llvm-config-3.4 llvm-config-3.3 llvm-config-3.2 llvm-config-3.1 llvm-config)
find_program(LLVMCONFIG NAMES llvm-config-3.9 llvm-config)
if( NOT LLVMCONFIG )
message(FATAL_ERROR "llvm-config not found, try installing llvm-dev llvm")

View File

@ -24,9 +24,7 @@ Required for FAIL*:
"-D__NO_MATH_INLINES -D__STRICT_ANSI__" or "--c_compiler clang++" (the
latter requires the clang++ compiler).
- optional:
* LLVM 3.3 or 3.4 (needed for several importers in tools/import-trace)
(compiles/links with 3.1 or 3.2, but fails to properly import information
from ELF binaries not compiled with -ffunction-sections)
* LLVM 3.9 (needed for several importers in tools/import-trace)
- built with "make REQUIRES_RTTI=1" (the Debian/Ubuntu packages already
come built this way)
- details below
@ -289,12 +287,12 @@ Database backend setup: MySQL / MariaDB
=========================================================================================
Building LLVM from sources
=========================================================================================
If your Linux distribution does not provide a library package for LLVM 3.3 or
If your Linux distribution does not provide a library package for LLVM 3.9 or
newer, and you need LLVM support in FAIL*, you may need to build LLVM from the
sources and install it, e.g., locally in your home.
1. Download the source tarball of LLVM 3.4 from http://llvm.org (or use the git
repository http://llvm.org/git/llvm.git and checkout release_34)
1. Download the source tarball of LLVM 3.9 from http://llvm.org (or use the git
repository http://llvm.org/git/llvm.git and checkout release_39)
2. Configure as needed. On mixed 32/64-bit systems (userland/kernel),
prefixing with "linux32" may be necessary:
$ linux32 ./configure --prefix=$(echo ~/localroot/usr) --enable-optimized --disable-assertions --disable-werror

View File

@ -81,7 +81,7 @@ add_library(fail-util ${SRCS})
add_dependencies(fail-util fail-comm)
target_link_libraries(fail-util fail-comm ${ADDITIONAL_LIBS} ${PROTOBUF_LIBRARY} ${Boost_LIBRARIES} ${LibIberty_LIBRARIES} ${ZLIB_LIBRARIES} ${LIBDWARF_LIBRARIES} ${LIBELF_LIBRARIES})
option(BUILD_LLVM_DISASSEMBLER "Build the LLVM-based disassembler (LLVM 3.3 preferred, for 3.1 and 3.2 read doc/how-to-build.txt)" OFF)
option(BUILD_LLVM_DISASSEMBLER "Build the LLVM-based disassembler (LLVM 3.9 preferred, other versions may not work)" OFF)
if (BUILD_LLVM_DISASSEMBLER)
add_subdirectory(llvmdisassembler)
endif (BUILD_LLVM_DISASSEMBLER)

View File

@ -5,8 +5,8 @@ using namespace llvm;
using namespace llvm::object;
LLVMtoFailTranslator & LLVMDisassembler::getTranslator() {
if ( ltofail == 0 ) {
LLVMtoFailTranslator *LLVMDisassembler::getTranslator() {
if (ltofail == 0) {
std::cout << "ArchType: " << llvm::Triple::getArchTypeName( llvm::Triple::ArchType(object->getArch()) ) << std::endl;
switch ( llvm::Triple::ArchType(object->getArch()) ) {
@ -22,42 +22,44 @@ LLVMtoFailTranslator & LLVMDisassembler::getTranslator() {
exit(1);
}
}
return *ltofail;
return ltofail;
}
void LLVMDisassembler::disassemble()
{
llvm::error_code ec;
for (section_iterator i = object->begin_sections(),
e = object->end_sections();
i != e; i.increment(ec)) {
if (error(ec)) break;
bool text;
if (error(i->isText(text))) break;
std::error_code ec;
for (section_iterator i = object->section_begin(),
e = object->section_end(); i != e; ++i) {
bool text = i->isText();
if (!text) continue;
uint64_t SectionAddr;
if (error(i->getAddress(SectionAddr))) break;
uint64_t SectionLength;
if (error(i->getSize(SectionLength))) break;
uint64_t SectionAddr = i->getAddress();
// FIXME uint64_t SectionLength = i->getSize();
// Make a list of all the symbols in this section.
std::vector<std::pair<uint64_t, StringRef> > Symbols;
for (symbol_iterator si = object->begin_symbols(),
se = object->end_symbols();
si != se; si.increment(ec)) {
bool contains;
for (const SymbolRef &symbol : object->symbols()) {
StringRef Name;
if (!error(i->containsSymbol(*si, contains)) && contains) {
uint64_t Address;
if (error(si->getAddress(Address))) break;
Address -= SectionAddr;
if (error(si->getName(Name))) break;
Symbols.push_back(std::make_pair(Address, Name));
if (!i->containsSymbol(symbol)) {
continue;
}
uint64_t Address;
Expected<uint64_t> AddrOrErr = symbol.getAddress();
if (!AddrOrErr) {
// FIXME fail
continue;
}
Address = *AddrOrErr - SectionAddr;
Expected<StringRef> NameOrErr = symbol.getName();
if (!NameOrErr) {
// FIXME fail
continue;
}
Symbols.push_back(std::make_pair(Address, *NameOrErr));
}
// Sort the symbols by address, just in case they didn't come in that way.
@ -71,13 +73,14 @@ void LLVMDisassembler::disassemble()
if (Symbols.empty())
Symbols.push_back(std::make_pair(0, name));
StringRef Bytes;
if (error(i->getContents(Bytes))) break;
StringRefMemoryObject memoryObject(Bytes);
StringRef BytesStr;
if (error(i->getContents(BytesStr))) break;
ArrayRef<uint8_t> Bytes(reinterpret_cast<const uint8_t *>(BytesStr.data()),
BytesStr.size());
uint64_t Size;
uint64_t Index;
uint64_t SectSize;
if (error(i->getSize(SectSize))) break;
uint64_t SectSize = i->getSize();
// Disassemble symbol by symbol.
for (unsigned si = 0, se = Symbols.size(); si != se; ++si) {
@ -100,7 +103,7 @@ void LLVMDisassembler::disassemble()
for (Index = Start; Index < End; Index += Size) {
MCInst Inst;
if (disas->getInstruction(Inst, Size, memoryObject, Index,
if (disas->getInstruction(Inst, Size, Bytes.slice(Index), Index,
nulls(), nulls()) == MCDisassembler::Success) {
const MCInstrDesc &desc = this->instr_info->get(Inst.getOpcode());
// Inst.dump();
@ -148,7 +151,4 @@ void LLVMDisassembler::disassemble()
}
}
}
}
void LLVMDisassembler::StringRefMemoryObject::anchor() {}

View File

@ -5,13 +5,17 @@
#include <vector>
#include <map>
#include <limits.h>
#include <memory> // unique_ptr
#include "llvm/Object/ObjectFile.h"
#include "llvm/ADT/STLExtras.h"
#include "llvm/MC/MCDisassembler.h"
#include "llvm/MC/MCAsmInfo.h"
#include "llvm/MC/MCContext.h"
#include "llvm/MC/MCDisassembler/MCDisassembler.h"
#include "llvm/MC/MCInst.h"
#include "llvm/MC/MCInstrInfo.h"
#include "llvm/MC/MCObjectFileInfo.h"
#include "llvm/MC/MCRegisterInfo.h"
#include "llvm/MC/MCStreamer.h"
#include "llvm/MC/MCSubtargetInfo.h"
@ -25,8 +29,6 @@
#include "llvm/Support/Casting.h"
#include "llvm/ADT/OwningPtr.h"
#include "LLVMtoFailTranslator.hpp"
#include "LLVMtoFailBochs.hpp"
#include "LLVMtoFailGem5.hpp"
@ -55,13 +57,13 @@ private:
std::string triple;
std::string MCPU;
std::string FeaturesStr;
llvm::OwningPtr<llvm::MCSubtargetInfo> subtargetinfo;
llvm::OwningPtr<const llvm::MCDisassembler> disas;
llvm::OwningPtr<const llvm::MCInstrInfo> instr_info;
llvm::OwningPtr<const llvm::MCRegisterInfo> register_info;
llvm::OwningPtr<InstrMap> instrs;
std::unique_ptr<const llvm::MCSubtargetInfo> subtargetinfo;
std::unique_ptr<const llvm::MCDisassembler> disas;
std::unique_ptr<const llvm::MCInstrInfo> instr_info;
std::unique_ptr<const llvm::MCRegisterInfo> register_info;
std::unique_ptr<InstrMap> instrs;
fail::LLVMtoFailTranslator * ltofail;
fail::LLVMtoFailTranslator *ltofail;
static std::string GetTriple(const llvm::object::ObjectFile *Obj) {
@ -84,41 +86,56 @@ private:
return 0;
}
static bool error(llvm::error_code ec) {
static bool error(std::error_code ec) {
if (!ec) return false;
std::cerr << "DIS" << ": error reading file: " << ec.message() << ".\n";
std::cerr << "DIS error: " << ec.message() << ".\n";
return true;
}
class StringRefMemoryObject : public llvm::MemoryObject {
virtual void anchor();
llvm::StringRef Bytes;
public:
StringRefMemoryObject(llvm::StringRef bytes) : Bytes(bytes) {}
uint64_t getBase() const { return 0; }
uint64_t getExtent() const { return Bytes.size(); }
int readByte(uint64_t Addr, uint8_t *Byte) const {
if (Addr >= getExtent())
return -1;
*Byte = Bytes[Addr];
return 0;
}
};
public:
LLVMDisassembler(const llvm::object::ObjectFile *object) : ltofail(0) {
this->object = object;
this->triple = GetTriple(object);
this->target = GetTarget(triple);
this->subtargetinfo.reset(target->createMCSubtargetInfo(triple, MCPU, FeaturesStr));
this->disas.reset(target->createMCDisassembler(*subtargetinfo));
this->instr_info.reset(target->createMCInstrInfo());
this->register_info.reset(target->createMCRegInfo(triple));
std::unique_ptr<const llvm::MCRegisterInfo> MRI(target->createMCRegInfo(triple));
if (!MRI) {
std::cerr << "DIS error: no register info for target " << triple << "\n";
return;
}
std::unique_ptr<const llvm::MCAsmInfo> MAI(target->createMCAsmInfo(*MRI, triple));
if (!MAI) {
std::cerr << "DIS error: no assembly info for target " << triple << "\n";
return;
}
std::unique_ptr<const llvm::MCSubtargetInfo> STI(
target->createMCSubtargetInfo(triple, MCPU, FeaturesStr));
if (!STI) {
std::cerr << "DIS error: no subtarget info for target " << triple << "\n";
return;
}
std::unique_ptr<const llvm::MCInstrInfo> MII(target->createMCInstrInfo());
if (!MII) {
std::cerr << "DIS error: no instruction info for target " << triple << "\n";
return;
}
std::unique_ptr<const llvm::MCObjectFileInfo> MOFI(new llvm::MCObjectFileInfo);
// Set up the MCContext for creating symbols and MCExpr's.
llvm::MCContext Ctx(MAI.get(), MRI.get(), MOFI.get());
this->subtargetinfo = std::move(STI);
std::unique_ptr<llvm::MCDisassembler> DisAsm(
target->createMCDisassembler(*subtargetinfo, Ctx));
if (!DisAsm) {
std::cerr << "DIS error: no disassembler for target " << triple << "\n";
return;
}
this->disas = std::move(DisAsm);
this->instr_info = std::move(MII);
this->register_info = std::move(MRI);
this->instrs.reset(new InstrMap());
}
@ -126,14 +143,13 @@ public:
~LLVMDisassembler() { delete ltofail; };
InstrMap &getInstrMap() { return *instrs; };
const llvm::MCRegisterInfo &getRegisterInfo() { return *register_info;}
fail::LLVMtoFailTranslator & getTranslator() ;
const llvm::MCRegisterInfo& getRegisterInfo() { return *register_info; }
fail::LLVMtoFailTranslator *getTranslator() ;
const std::string & GetTriple() const { return triple; };
const std::string& GetTriple() const { return triple; };
void disassemble();
};
}
#endif // __LLVMDISASSEMBLER_HPP__

View File

@ -43,20 +43,18 @@ void LLVMtoFailTranslator::setRegisterContent(ConcreteCPU & cpu, const reginfo_t
}
LLVMtoFailTranslator* LLVMtoFailTranslator::createFromBinary(const std::string elf_path) {
llvm_shutdown_obj Y;
//llvm_shutdown_obj Y;
llvm::InitializeAllTargetInfos();
llvm::InitializeAllTargetMCs();
llvm::InitializeAllDisassemblers();
OwningPtr<Binary> binary;
llvm::error_code ret = createBinary(elf_path, binary);
assert (ret == 0);
(void) ret; // unused in release builds
assert (binary.get() != NULL);
Expected<OwningBinary<Binary>> BinaryOrErr = createBinary(elf_path);
assert (BinaryOrErr);
Binary *binary = BinaryOrErr.get().getBinary();
#ifndef __puma
LLVMDisassembler disas(dyn_cast<ObjectFile>(binary.get()));
return &disas.getTranslator();
LLVMDisassembler disas(dyn_cast<ObjectFile>(binary));
return disas.getTranslator();
#else
return 0;
#endif

View File

@ -1,3 +1,4 @@
#include "llvm/Support/raw_os_ostream.h"
#include "../LLVMDisassembler.hpp"
using namespace llvm;
@ -22,13 +23,16 @@ int main(int argc, char* argv[]) {
return -1;
}
OwningPtr<Binary> binary;
if (llvm::error_code ec = createBinary(file, binary)) {
std::cerr << "Dis" << ": '" << file << "': " << ec.message() << ".\n";
Expected<OwningBinary<Binary>> BinaryOrErr = createBinary(file);
if (!BinaryOrErr) {
std::cerr << "Dis: '" << file << "': ";
raw_os_ostream OS(std::cerr);
logAllUnhandledErrors(BinaryOrErr.takeError(), OS, "");
return -1;
}
Binary *binary = BinaryOrErr.get().getBinary();
ObjectFile *obj = dyn_cast<ObjectFile>(binary.get());
ObjectFile *obj = dyn_cast<ObjectFile>(binary);
LLVMDisassembler disas(obj);
disas.disassemble();
@ -40,26 +44,27 @@ int main(int argc, char* argv[]) {
const MCRegisterInfo &reg_info = disas.getRegisterInfo();
std::cout << std::endl << "Number of Registers: " << reg_info.getNumRegs() << std::endl;
// for(unsigned int i = 0; i < reg_info.getNumRegs(); ++i){
// std::cout << i << " - " << reg_info.getName(i) << std::endl;
// }
fail::LLVMtoFailTranslator & ltof = disas.getTranslator() ;
for (unsigned int i = 0; i < reg_info.getNumRegs(); ++i) {
std::cout << i << "=" << reg_info.getName(i) << " ";
}
std::cout << std::endl;
fail::LLVMtoFailTranslator *ltof = disas.getTranslator();
for(itr = instr_map.begin(); itr != instr_map.end(); ++itr){
for (itr = instr_map.begin(); itr != instr_map.end(); ++itr){
const LLVMDisassembler::Instr &instr = (*itr).second;
std::cout << std::hex << (*itr).first << " | " << instr.opcode << std::endl;
std::cout << std::dec << "USES: ";
for (std::vector<uint16_t>::const_iterator it = instr.reg_uses.begin();
it != instr.reg_uses.end(); ++it) {
std::cout << reg_info.getName(*it) <<"(" << *it << ") ";
std::cout << "Fail: " << ltof.getFailRegisterId(*it) << " ";
std::cout << reg_info.getName(*it)
<< "(" << *it << "->" << ltof->getFailRegisterId(*it) << ") ";
}
std::cout << std::endl;
std::cout << "DEFS: ";
std::cout << " | DEFS: ";
for (std::vector<uint16_t>::const_iterator it = instr.reg_defs.begin();
it != instr.reg_defs.end(); ++it) {
std::cout << reg_info.getName(*it) << "(" << *it << ") ";
std::cout << reg_info.getName(*it)
<< "(" << *it << "->" << ltof->getFailRegisterId(*it) << ") ";
}
if (instr.conditional_branch) {

View File

@ -104,14 +104,20 @@ bool AdvancedMemoryImporter::handle_ip_event(fail::simtime_t curtime, instructio
llvm::InitializeAllTargetMCs();
llvm::InitializeAllDisassemblers();
if (llvm::error_code ec = createBinary(m_elf->getFilename(), binary)) {
LOG << m_elf->getFilename() << "': " << ec.message() << ".\n";
Expected<OwningBinary<Binary>> BinaryOrErr = createBinary(m_elf->getFilename());
if (!BinaryOrErr) {
std::string Buf;
raw_string_ostream OS(Buf);
logAllUnhandledErrors(std::move(BinaryOrErr.takeError()), OS, "");
OS.flush();
LOG << m_elf->getFilename() << "': " << Buf << ".\n";
return false;
}
binary = &(*BinaryOrErr.get().getBinary());
// necessary due to an AspectC++ bug triggered by LLVM 3.3's dyn_cast()
#ifndef __puma
ObjectFile *obj = dyn_cast<ObjectFile>(binary.get());
ObjectFile *obj = dyn_cast<ObjectFile>(binary);
disas.reset(new LLVMDisassembler(obj));
#endif
disas->disassemble();

View File

@ -24,8 +24,8 @@
* operations with a set of new virtual functions that are called downwards.
*/
class AdvancedMemoryImporter : public MemoryImporter {
llvm::OwningPtr<llvm::object::Binary> binary;
llvm::OwningPtr<fail::LLVMDisassembler> disas;
llvm::object::Binary *binary = 0;
std::unique_ptr<fail::LLVMDisassembler> disas;
bool m_last_was_conditional_branch;
fail::guest_address_t m_ip_jump_not_taken;
std::vector<bool> branches_taken;

View File

@ -27,8 +27,8 @@
into the database.
*/
class ElfImporter : public Importer {
llvm::OwningPtr<llvm::object::Binary> binary;
llvm::OwningPtr<fail::LLVMDisassembler> disas;
std::unique_ptr<llvm::object::Binary> binary;
std::unique_ptr<fail::LLVMDisassembler> disas;
fail::CommandLine::option_handle OBJDUMP;
fail::CommandLine::option_handle SOURCECODE;

View File

@ -18,14 +18,20 @@ bool InstructionImporter::handle_ip_event(fail::simtime_t curtime, instruction_c
llvm::InitializeAllTargetMCs();
llvm::InitializeAllDisassemblers();
if (llvm::error_code ec = createBinary(m_elf->getFilename(), binary)) {
LOG << m_elf->getFilename() << "': " << ec.message() << ".\n";
Expected<OwningBinary<Binary>> BinaryOrErr = createBinary(m_elf->getFilename());
if (!BinaryOrErr) {
std::string Buf;
raw_string_ostream OS(Buf);
logAllUnhandledErrors(std::move(BinaryOrErr.takeError()), OS, "");
OS.flush();
LOG << m_elf->getFilename() << "': " << Buf << ".\n";
return false;
}
binary = &(*BinaryOrErr.get().getBinary());
// necessary due to an AspectC++ bug triggered by LLVM 3.3's dyn_cast()
#ifndef __puma
ObjectFile *obj = llvm::dyn_cast<ObjectFile>(binary.get());
ObjectFile *obj = llvm::dyn_cast<ObjectFile>(binary);
disas.reset(new LLVMDisassembler(obj));
#endif
disas->disassemble();

View File

@ -6,8 +6,8 @@
#include "util/llvmdisassembler/LLVMDisassembler.hpp"
class InstructionImporter : public Importer {
llvm::OwningPtr<llvm::object::Binary> binary;
llvm::OwningPtr<fail::LLVMDisassembler> disas;
llvm::object::Binary *binary = 0;
std::unique_ptr<fail::LLVMDisassembler> disas;
protected:
virtual bool handle_ip_event(fail::simtime_t curtime, instruction_count_t instr,

View File

@ -65,14 +65,20 @@ bool RandomJumpImporter::handle_ip_event(fail::simtime_t curtime, instruction_co
llvm::InitializeAllTargetMCs();
llvm::InitializeAllDisassemblers();
if (llvm::error_code ec = createBinary(m_elf->getFilename(), binary)) {
LOG << m_elf->getFilename() << "': " << ec.message() << ".\n";
Expected<OwningBinary<Binary>> BinaryOrErr = createBinary(m_elf->getFilename());
if (!BinaryOrErr) {
std::string Buf;
raw_string_ostream OS(Buf);
logAllUnhandledErrors(std::move(BinaryOrErr.takeError()), OS, "");
OS.flush();
LOG << m_elf->getFilename() << "': " << Buf << ".\n";
return false;
}
binary = &(*BinaryOrErr.get().getBinary());
// necessary due to an AspectC++ bug triggered by LLVM 3.3's dyn_cast()
#ifndef __puma
ObjectFile *obj = dyn_cast<ObjectFile>(binary.get());
ObjectFile *obj = dyn_cast<ObjectFile>(binary);
disas.reset(new LLVMDisassembler(obj));
#endif
disas->disassemble();

View File

@ -8,8 +8,8 @@
#include "util/llvmdisassembler/LLVMDisassembler.hpp"
class RandomJumpImporter : public Importer {
llvm::OwningPtr<llvm::object::Binary> binary;
llvm::OwningPtr<fail::LLVMDisassembler> disas;
llvm::object::Binary *binary = 0;
std::unique_ptr<fail::LLVMDisassembler> disas;
fail::CommandLine::option_handle FROM, TO;

View File

@ -133,19 +133,27 @@ bool RegisterImporter::handle_ip_event(fail::simtime_t curtime, instruction_coun
llvm::InitializeAllTargetMCs();
llvm::InitializeAllDisassemblers();
if (llvm::error_code ec = createBinary(m_elf->getFilename(), binary)) {
LOG << m_elf->getFilename() << "': " << ec.message() << ".\n";
Expected<OwningBinary<Binary>> BinaryOrErr = createBinary(m_elf->getFilename());
if (!BinaryOrErr) {
std::string Buf;
raw_string_ostream OS(Buf);
logAllUnhandledErrors(std::move(BinaryOrErr.takeError()), OS, "");
OS.flush();
LOG << m_elf->getFilename() << "': " << Buf << ".\n";
return false;
}
binary = BinaryOrErr.get().getBinary();
// necessary due to an AspectC++ bug triggered by LLVM 3.3's dyn_cast()
#ifndef __puma
ObjectFile *obj = dyn_cast<ObjectFile>(binary.get());
ObjectFile *obj = dyn_cast<ObjectFile>(binary);
disas.reset(new LLVMDisassembler(obj));
#endif
disas->disassemble();
LLVMDisassembler::InstrMap &instr_map = disas->getInstrMap();
LOG << "instructions disassembled: " << instr_map.size() << " Triple: " << disas->GetTriple() << std::endl;
m_ltof = disas->getTranslator() ;
}
// instruction pointer is read + written at each instruction
@ -165,12 +173,10 @@ bool RegisterImporter::handle_ip_event(fail::simtime_t curtime, instruction_coun
const LLVMDisassembler::Instr &opcode = instr_map.at(ev.ip());
//const MCRegisterInfo &reg_info = disas->getRegisterInfo();
fail::LLVMtoFailTranslator & ltof = disas->getTranslator() ;
for (std::vector<LLVMDisassembler::register_t>::const_iterator it = opcode.reg_uses.begin();
it != opcode.reg_uses.end(); ++it) {
const LLVMtoFailTranslator::reginfo_t &info = ltof.getFailRegisterID(*it);
if (&info == &ltof.notfound) {
const LLVMtoFailTranslator::reginfo_t &info = m_ltof->getFailRegisterID(*it);
if (&info == &m_ltof->notfound) {
LOG << "Could not find a mapping for LLVM input register #" << std::dec << *it
<< " at IP " << std::hex << ev.ip()
<< ", skipping" << std::endl;
@ -189,8 +195,8 @@ bool RegisterImporter::handle_ip_event(fail::simtime_t curtime, instruction_coun
for (std::vector<LLVMDisassembler::register_t>::const_iterator it = opcode.reg_defs.begin();
it != opcode.reg_defs.end(); ++it) {
const LLVMtoFailTranslator::reginfo_t &info = ltof.getFailRegisterID(*it);
if (&info == &ltof.notfound) {
const LLVMtoFailTranslator::reginfo_t &info = m_ltof->getFailRegisterID(*it);
if (&info == &m_ltof->notfound) {
LOG << "Could not find a mapping for LLVM output register #" << std::dec << *it
<< " at IP " << std::hex << ev.ip()
<< ", skipping" << std::endl;

View File

@ -9,8 +9,9 @@
class RegisterImporter : public Importer {
llvm::OwningPtr<llvm::object::Binary> binary;
llvm::OwningPtr<fail::LLVMDisassembler> disas;
llvm::object::Binary *binary = 0;
std::unique_ptr<fail::LLVMDisassembler> disas;
fail::LLVMtoFailTranslator *m_ltof = 0;
bool addRegisterTrace(fail::simtime_t curtime, instruction_count_t instr,
Trace_Event &ev,

View File

@ -11,6 +11,7 @@
#include "util/AliasedRegistry.hpp"
#ifdef BUILD_LLVM_DISASSEMBLER
#include "llvm/Support/ManagedStatic.h"
#include "InstructionImporter.hpp"
#include "RegisterImporter.hpp"
#include "RandomJumpImporter.hpp"
@ -67,6 +68,7 @@ int main(int argc, char *argv[]) {
registry.add(&fti);
#ifdef BUILD_LLVM_DISASSEMBLER
llvm::llvm_shutdown_obj Y;
RegisterImporter reg;
registry.add(&reg);
RandomJumpImporter rjump;