1 //===- ELFYAML.h - ELF YAMLIO implementation --------------------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 /// 10 /// \file 11 /// \brief This file declares classes for handling the YAML representation 12 /// of ELF. 13 /// 14 //===----------------------------------------------------------------------===// 15 16 #ifndef LLVM_OBJECT_ELFYAML_H 17 #define LLVM_OBJECT_ELFYAML_H 18 19 #include "llvm/Object/YAML.h" 20 #include "llvm/Support/ELF.h" 21 22 namespace llvm { 23 namespace ELFYAML { 24 25 // These types are invariant across 32/64-bit ELF, so for simplicity just 26 // directly give them their exact sizes. We don't need to worry about 27 // endianness because these are just the types in the YAMLIO structures, 28 // and are appropriately converted to the necessary endianness when 29 // reading/generating binary object files. 30 // The naming of these types is intended to be ELF_PREFIX, where PREFIX is 31 // the common prefix of the respective constants. E.g. ELF_EM corresponds 32 // to the `e_machine` constants, like `EM_X86_64`. 33 // In the future, these would probably be better suited by C++11 enum 34 // class's with appropriate fixed underlying type. 35 LLVM_YAML_STRONG_TYPEDEF(uint16_t, ELF_ET) 36 LLVM_YAML_STRONG_TYPEDEF(uint32_t, ELF_EM) 37 LLVM_YAML_STRONG_TYPEDEF(uint8_t, ELF_ELFCLASS) 38 LLVM_YAML_STRONG_TYPEDEF(uint8_t, ELF_ELFDATA) 39 LLVM_YAML_STRONG_TYPEDEF(uint8_t, ELF_ELFOSABI) 40 LLVM_YAML_STRONG_TYPEDEF(uint32_t, ELF_SHT) 41 // Just use 64, since it can hold 32-bit values too. 42 LLVM_YAML_STRONG_TYPEDEF(uint64_t, ELF_SHF) 43 LLVM_YAML_STRONG_TYPEDEF(uint8_t, ELF_STT) 44 45 // For now, hardcode 64 bits everywhere that 32 or 64 would be needed 46 // since 64-bit can hold 32-bit values too. 47 struct FileHeader { 48 ELF_ELFCLASS Class; 49 ELF_ELFDATA Data; 50 ELF_ELFOSABI OSABI; 51 ELF_ET Type; 52 ELF_EM Machine; 53 llvm::yaml::Hex64 Entry; 54 }; 55 struct Symbol { 56 StringRef Name; 57 ELF_STT Type; 58 StringRef Section; 59 llvm::yaml::Hex64 Value; 60 llvm::yaml::Hex64 Size; 61 }; 62 struct LocalGlobalWeakSymbols { 63 std::vector<Symbol> Local; 64 std::vector<Symbol> Global; 65 std::vector<Symbol> Weak; 66 }; 67 struct Section { 68 StringRef Name; 69 ELF_SHT Type; 70 ELF_SHF Flags; 71 llvm::yaml::Hex64 Address; 72 object::yaml::BinaryRef Content; 73 StringRef Link; 74 llvm::yaml::Hex64 AddressAlign; 75 }; 76 struct Object { 77 FileHeader Header; 78 std::vector<Section> Sections; 79 // Although in reality the symbols reside in a section, it is a lot 80 // cleaner and nicer if we read them from the YAML as a separate 81 // top-level key, which automatically ensures that invariants like there 82 // being a single SHT_SYMTAB section are upheld. 83 LocalGlobalWeakSymbols Symbols; 84 }; 85 86 } // end namespace ELFYAML 87 } // end namespace llvm 88 89 LLVM_YAML_IS_SEQUENCE_VECTOR(llvm::ELFYAML::Section) 90 LLVM_YAML_IS_SEQUENCE_VECTOR(llvm::ELFYAML::Symbol) 91 92 namespace llvm { 93 namespace yaml { 94 95 template <> 96 struct ScalarEnumerationTraits<ELFYAML::ELF_ET> { 97 static void enumeration(IO &IO, ELFYAML::ELF_ET &Value); 98 }; 99 100 template <> 101 struct ScalarEnumerationTraits<ELFYAML::ELF_EM> { 102 static void enumeration(IO &IO, ELFYAML::ELF_EM &Value); 103 }; 104 105 template <> 106 struct ScalarEnumerationTraits<ELFYAML::ELF_ELFCLASS> { 107 static void enumeration(IO &IO, ELFYAML::ELF_ELFCLASS &Value); 108 }; 109 110 template <> 111 struct ScalarEnumerationTraits<ELFYAML::ELF_ELFDATA> { 112 static void enumeration(IO &IO, ELFYAML::ELF_ELFDATA &Value); 113 }; 114 115 template <> 116 struct ScalarEnumerationTraits<ELFYAML::ELF_ELFOSABI> { 117 static void enumeration(IO &IO, ELFYAML::ELF_ELFOSABI &Value); 118 }; 119 120 template <> 121 struct ScalarEnumerationTraits<ELFYAML::ELF_SHT> { 122 static void enumeration(IO &IO, ELFYAML::ELF_SHT &Value); 123 }; 124 125 template <> 126 struct ScalarBitSetTraits<ELFYAML::ELF_SHF> { 127 static void bitset(IO &IO, ELFYAML::ELF_SHF &Value); 128 }; 129 130 template <> 131 struct ScalarEnumerationTraits<ELFYAML::ELF_STT> { 132 static void enumeration(IO &IO, ELFYAML::ELF_STT &Value); 133 }; 134 135 template <> 136 struct MappingTraits<ELFYAML::FileHeader> { 137 static void mapping(IO &IO, ELFYAML::FileHeader &FileHdr); 138 }; 139 140 template <> 141 struct MappingTraits<ELFYAML::Symbol> { 142 static void mapping(IO &IO, ELFYAML::Symbol &Symbol); 143 }; 144 145 template <> 146 struct MappingTraits<ELFYAML::LocalGlobalWeakSymbols> { 147 static void mapping(IO &IO, ELFYAML::LocalGlobalWeakSymbols &Symbols); 148 }; 149 150 template <> 151 struct MappingTraits<ELFYAML::Section> { 152 static void mapping(IO &IO, ELFYAML::Section &Section); 153 }; 154 155 template <> 156 struct MappingTraits<ELFYAML::Object> { 157 static void mapping(IO &IO, ELFYAML::Object &Object); 158 }; 159 160 } // end namespace yaml 161 } // end namespace llvm 162 163 #endif 164