Index: llvm/trunk/include/llvm/CodeGen/FaultMaps.h =================================================================== --- llvm/trunk/include/llvm/CodeGen/FaultMaps.h +++ llvm/trunk/include/llvm/CodeGen/FaultMaps.h @@ -12,8 +12,6 @@ #include "llvm/ADT/DenseMap.h" #include "llvm/MC/MCSymbol.h" -#include "llvm/Support/Endian.h" -#include "llvm/Support/Format.h" #include #include @@ -71,150 +69,6 @@ void emitFunctionInfo(const MCSymbol *FnLabel, const FunctionFaultInfos &FFI); }; -/// A parser for the __llvm_faultmaps section generated by the FaultMaps class -/// above. This parser is version locked with with the __llvm_faultmaps section -/// generated by the version of LLVM that includes it. No guarantees are made -/// with respect to forward or backward compatibility. -class FaultMapParser { - typedef uint8_t FaultMapVersionType; - static const size_t FaultMapVersionOffset = 0; - - typedef uint8_t Reserved0Type; - static const size_t Reserved0Offset = - FaultMapVersionOffset + sizeof(FaultMapVersionType); - - typedef uint16_t Reserved1Type; - static const size_t Reserved1Offset = Reserved0Offset + sizeof(Reserved0Type); - - typedef uint32_t NumFunctionsType; - static const size_t NumFunctionsOffset = - Reserved1Offset + sizeof(Reserved1Type); - - static const size_t FunctionInfosOffset = - NumFunctionsOffset + sizeof(NumFunctionsType); - - const uint8_t *P; - const uint8_t *E; - - template static T read(const uint8_t *P, const uint8_t *E) { - assert(P + sizeof(T) <= E && "out of bounds read!"); - return support::endian::read(P); - } - -public: - class FunctionFaultInfoAccessor { - typedef uint32_t FaultKindType; - static const size_t FaultKindOffset = 0; - - typedef uint32_t FaultingPCOffsetType; - static const size_t FaultingPCOffsetOffset = - FaultKindOffset + sizeof(FaultKindType); - - typedef uint32_t HandlerPCOffsetType; - static const size_t HandlerPCOffsetOffset = - FaultingPCOffsetOffset + sizeof(FaultingPCOffsetType); - - const uint8_t *P; - const uint8_t *E; - - public: - static const size_t Size = - HandlerPCOffsetOffset + sizeof(HandlerPCOffsetType); - - explicit FunctionFaultInfoAccessor(const uint8_t *P, const uint8_t *E) - : P(P), E(E) {} - - FaultKindType getFaultKind() const { - return read(P + FaultKindOffset, E); - } - - FaultingPCOffsetType getFaultingPCOffset() const { - return read(P + FaultingPCOffsetOffset, E); - } - - HandlerPCOffsetType getHandlerPCOffset() const { - return read(P + HandlerPCOffsetOffset, E); - } - }; - - class FunctionInfoAccessor { - typedef uint64_t FunctionAddrType; - static const size_t FunctionAddrOffset = 0; - - typedef uint32_t NumFaultingPCsType; - static const size_t NumFaultingPCsOffset = - FunctionAddrOffset + sizeof(FunctionAddrType); - - typedef uint32_t ReservedType; - static const size_t ReservedOffset = - NumFaultingPCsOffset + sizeof(NumFaultingPCsType); - - static const size_t FunctionFaultInfosOffset = - ReservedOffset + sizeof(ReservedType); - - static const size_t FunctionInfoHeaderSize = FunctionFaultInfosOffset; - - const uint8_t *P; - const uint8_t *E; - - public: - FunctionInfoAccessor() : P(nullptr), E(nullptr) {} - - explicit FunctionInfoAccessor(const uint8_t *P, const uint8_t *E) - : P(P), E(E) {} - - FunctionAddrType getFunctionAddr() const { - return read(P + FunctionAddrOffset, E); - } - - NumFaultingPCsType getNumFaultingPCs() const { - return read(P + NumFaultingPCsOffset, E); - } - - FunctionFaultInfoAccessor getFunctionFaultInfoAt(uint32_t Index) const { - assert(Index < getNumFaultingPCs() && "index out of bounds!"); - const uint8_t *Begin = P + FunctionFaultInfosOffset + - FunctionFaultInfoAccessor::Size * Index; - return FunctionFaultInfoAccessor(Begin, E); - } - - FunctionInfoAccessor getNextFunctionInfo() const { - size_t MySize = FunctionInfoHeaderSize + - getNumFaultingPCs() * FunctionFaultInfoAccessor::Size; - - const uint8_t *Begin = P + MySize; - assert(Begin < E && "out of bounds!"); - return FunctionInfoAccessor(Begin, E); - } - }; - - explicit FaultMapParser(const uint8_t *Begin, const uint8_t *End) - : P(Begin), E(End) {} - - FaultMapVersionType getFaultMapVersion() const { - auto Version = read(P + FaultMapVersionOffset, E); - assert(Version == 1 && "only version 1 supported!"); - return Version; - } - - NumFunctionsType getNumFunctions() const { - return read(P + NumFunctionsOffset, E); - } - - FunctionInfoAccessor getFirstFunctionInfo() const { - const uint8_t *Begin = P + FunctionInfosOffset; - return FunctionInfoAccessor(Begin, E); - } -}; - -raw_ostream & -operator<<(raw_ostream &OS, const FaultMapParser::FunctionFaultInfoAccessor &); - -raw_ostream &operator<<(raw_ostream &OS, - const FaultMapParser::FunctionInfoAccessor &); - -raw_ostream &operator<<(raw_ostream &OS, const FaultMapParser &); - } // namespace llvm #endif Index: llvm/trunk/include/llvm/Object/FaultMapParser.h =================================================================== --- llvm/trunk/include/llvm/Object/FaultMapParser.h +++ llvm/trunk/include/llvm/Object/FaultMapParser.h @@ -0,0 +1,167 @@ +//===-- FaultMapParser.h - Parser for the "FaultMaps" section --*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "llvm/Support/Endian.h" +#include "llvm/Support/raw_ostream.h" + +#ifndef LLVM_OBJECT_FAULTMAPPARSER_H +#define LLVM_OBJECT_FAULTMAPPARSER_H + +namespace llvm { + +/// A parser for the __llvm_faultmaps section generated by the FaultMaps class +/// declared in llvm/CodeGen/FaultMaps.h. This parser is version locked with +/// with the __llvm_faultmaps section generated by the version of LLVM that +/// includes it. No guarantees are made with respect to forward or backward +/// compatibility. +class FaultMapParser { + typedef uint8_t FaultMapVersionType; + static const size_t FaultMapVersionOffset = 0; + + typedef uint8_t Reserved0Type; + static const size_t Reserved0Offset = + FaultMapVersionOffset + sizeof(FaultMapVersionType); + + typedef uint16_t Reserved1Type; + static const size_t Reserved1Offset = Reserved0Offset + sizeof(Reserved0Type); + + typedef uint32_t NumFunctionsType; + static const size_t NumFunctionsOffset = + Reserved1Offset + sizeof(Reserved1Type); + + static const size_t FunctionInfosOffset = + NumFunctionsOffset + sizeof(NumFunctionsType); + + const uint8_t *P; + const uint8_t *E; + + template static T read(const uint8_t *P, const uint8_t *E) { + assert(P + sizeof(T) <= E && "out of bounds read!"); + return support::endian::read(P); + } + +public: + enum FaultKind { FaultingLoad = 1, FaultKindMax }; + + class FunctionFaultInfoAccessor { + typedef uint32_t FaultKindType; + static const size_t FaultKindOffset = 0; + + typedef uint32_t FaultingPCOffsetType; + static const size_t FaultingPCOffsetOffset = + FaultKindOffset + sizeof(FaultKindType); + + typedef uint32_t HandlerPCOffsetType; + static const size_t HandlerPCOffsetOffset = + FaultingPCOffsetOffset + sizeof(FaultingPCOffsetType); + + const uint8_t *P; + const uint8_t *E; + + public: + static const size_t Size = + HandlerPCOffsetOffset + sizeof(HandlerPCOffsetType); + + explicit FunctionFaultInfoAccessor(const uint8_t *P, const uint8_t *E) + : P(P), E(E) {} + + FaultKindType getFaultKind() const { + return read(P + FaultKindOffset, E); + } + + FaultingPCOffsetType getFaultingPCOffset() const { + return read(P + FaultingPCOffsetOffset, E); + } + + HandlerPCOffsetType getHandlerPCOffset() const { + return read(P + HandlerPCOffsetOffset, E); + } + }; + + class FunctionInfoAccessor { + typedef uint64_t FunctionAddrType; + static const size_t FunctionAddrOffset = 0; + + typedef uint32_t NumFaultingPCsType; + static const size_t NumFaultingPCsOffset = + FunctionAddrOffset + sizeof(FunctionAddrType); + + typedef uint32_t ReservedType; + static const size_t ReservedOffset = + NumFaultingPCsOffset + sizeof(NumFaultingPCsType); + + static const size_t FunctionFaultInfosOffset = + ReservedOffset + sizeof(ReservedType); + + static const size_t FunctionInfoHeaderSize = FunctionFaultInfosOffset; + + const uint8_t *P; + const uint8_t *E; + + public: + FunctionInfoAccessor() : P(nullptr), E(nullptr) {} + + explicit FunctionInfoAccessor(const uint8_t *P, const uint8_t *E) + : P(P), E(E) {} + + FunctionAddrType getFunctionAddr() const { + return read(P + FunctionAddrOffset, E); + } + + NumFaultingPCsType getNumFaultingPCs() const { + return read(P + NumFaultingPCsOffset, E); + } + + FunctionFaultInfoAccessor getFunctionFaultInfoAt(uint32_t Index) const { + assert(Index < getNumFaultingPCs() && "index out of bounds!"); + const uint8_t *Begin = P + FunctionFaultInfosOffset + + FunctionFaultInfoAccessor::Size * Index; + return FunctionFaultInfoAccessor(Begin, E); + } + + FunctionInfoAccessor getNextFunctionInfo() const { + size_t MySize = FunctionInfoHeaderSize + + getNumFaultingPCs() * FunctionFaultInfoAccessor::Size; + + const uint8_t *Begin = P + MySize; + assert(Begin < E && "out of bounds!"); + return FunctionInfoAccessor(Begin, E); + } + }; + + explicit FaultMapParser(const uint8_t *Begin, const uint8_t *End) + : P(Begin), E(End) {} + + FaultMapVersionType getFaultMapVersion() const { + auto Version = read(P + FaultMapVersionOffset, E); + assert(Version == 1 && "only version 1 supported!"); + return Version; + } + + NumFunctionsType getNumFunctions() const { + return read(P + NumFunctionsOffset, E); + } + + FunctionInfoAccessor getFirstFunctionInfo() const { + const uint8_t *Begin = P + FunctionInfosOffset; + return FunctionInfoAccessor(Begin, E); + } +}; + +raw_ostream & +operator<<(raw_ostream &OS, const FaultMapParser::FunctionFaultInfoAccessor &); + +raw_ostream &operator<<(raw_ostream &OS, + const FaultMapParser::FunctionInfoAccessor &); + +raw_ostream &operator<<(raw_ostream &OS, const FaultMapParser &); + +} // namespace llvm + +#endif Index: llvm/trunk/lib/CodeGen/FaultMaps.cpp =================================================================== --- llvm/trunk/lib/CodeGen/FaultMaps.cpp +++ llvm/trunk/lib/CodeGen/FaultMaps.cpp @@ -112,39 +112,3 @@ return "FaultingLoad"; } } - -raw_ostream &llvm:: -operator<<(raw_ostream &OS, - const FaultMapParser::FunctionFaultInfoAccessor &FFI) { - OS << "Fault kind: " - << FaultMaps::faultTypeToString((FaultMaps::FaultKind)FFI.getFaultKind()) - << ", faulting PC offset: " << FFI.getFaultingPCOffset() - << ", handling PC offset: " << FFI.getHandlerPCOffset(); - return OS; -} - -raw_ostream &llvm:: -operator<<(raw_ostream &OS, const FaultMapParser::FunctionInfoAccessor &FI) { - OS << "FunctionAddress: " << format_hex(FI.getFunctionAddr(), 8) - << ", NumFaultingPCs: " << FI.getNumFaultingPCs() << "\n"; - for (unsigned i = 0, e = FI.getNumFaultingPCs(); i != e; ++i) - OS << FI.getFunctionFaultInfoAt(i) << "\n"; - return OS; -} - -raw_ostream &llvm::operator<<(raw_ostream &OS, const FaultMapParser &FMP) { - OS << "Version: " << format_hex(FMP.getFaultMapVersion(), 2) << "\n"; - OS << "NumFunctions: " << FMP.getNumFunctions() << "\n"; - - if (FMP.getNumFunctions() == 0) - return OS; - - FaultMapParser::FunctionInfoAccessor FI; - - for (unsigned i = 0, e = FMP.getNumFunctions(); i != e; ++i) { - FI = (i == 0) ? FMP.getFirstFunctionInfo() : FI.getNextFunctionInfo(); - OS << FI; - } - - return OS; -} Index: llvm/trunk/lib/Object/CMakeLists.txt =================================================================== --- llvm/trunk/lib/Object/CMakeLists.txt +++ llvm/trunk/lib/Object/CMakeLists.txt @@ -8,6 +8,7 @@ ELFObjectFile.cpp ELFYAML.cpp Error.cpp + FaultMapParser.cpp IRObjectFile.cpp MachOObjectFile.cpp MachOUniversal.cpp Index: llvm/trunk/lib/Object/FaultMapParser.cpp =================================================================== --- llvm/trunk/lib/Object/FaultMapParser.cpp +++ llvm/trunk/lib/Object/FaultMapParser.cpp @@ -0,0 +1,61 @@ +//===----------------------- FaultMapParser.cpp ---------------------------===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "llvm/Object/FaultMapParser.h" + +#include "llvm/Support/ErrorHandling.h" +#include "llvm/Support/Format.h" + +using namespace llvm; + +const char *faultKindToString(FaultMapParser::FaultKind FT) { + switch (FT) { + default: + llvm_unreachable("unhandled fault type!"); + + case FaultMapParser::FaultingLoad: + return "FaultingLoad"; + } +} + +raw_ostream &llvm:: +operator<<(raw_ostream &OS, + const FaultMapParser::FunctionFaultInfoAccessor &FFI) { + OS << "Fault kind: " + << faultKindToString((FaultMapParser::FaultKind)FFI.getFaultKind()) + << ", faulting PC offset: " << FFI.getFaultingPCOffset() + << ", handling PC offset: " << FFI.getHandlerPCOffset(); + return OS; +} + +raw_ostream &llvm:: +operator<<(raw_ostream &OS, const FaultMapParser::FunctionInfoAccessor &FI) { + OS << "FunctionAddress: " << format_hex(FI.getFunctionAddr(), 8) + << ", NumFaultingPCs: " << FI.getNumFaultingPCs() << "\n"; + for (unsigned i = 0, e = FI.getNumFaultingPCs(); i != e; ++i) + OS << FI.getFunctionFaultInfoAt(i) << "\n"; + return OS; +} + +raw_ostream &llvm::operator<<(raw_ostream &OS, const FaultMapParser &FMP) { + OS << "Version: " << format_hex(FMP.getFaultMapVersion(), 2) << "\n"; + OS << "NumFunctions: " << FMP.getNumFunctions() << "\n"; + + if (FMP.getNumFunctions() == 0) + return OS; + + FaultMapParser::FunctionInfoAccessor FI; + + for (unsigned i = 0, e = FMP.getNumFunctions(); i != e; ++i) { + FI = (i == 0) ? FMP.getFirstFunctionInfo() : FI.getNextFunctionInfo(); + OS << FI; + } + + return OS; +} Index: llvm/trunk/tools/llvm-objdump/llvm-objdump.cpp =================================================================== --- llvm/trunk/tools/llvm-objdump/llvm-objdump.cpp +++ llvm/trunk/tools/llvm-objdump/llvm-objdump.cpp @@ -21,7 +21,6 @@ #include "llvm/ADT/STLExtras.h" #include "llvm/ADT/StringExtras.h" #include "llvm/ADT/Triple.h" -#include "llvm/CodeGen/FaultMaps.h" #include "llvm/MC/MCAsmInfo.h" #include "llvm/MC/MCContext.h" #include "llvm/MC/MCDisassembler.h" @@ -35,6 +34,7 @@ #include "llvm/MC/MCSubtargetInfo.h" #include "llvm/Object/Archive.h" #include "llvm/Object/ELFObjectFile.h" +#include "llvm/Object/FaultMapParser.h" #include "llvm/Object/COFF.h" #include "llvm/Object/MachO.h" #include "llvm/Object/ObjectFile.h"