1 //===- ELFAttribute.h -----------------------------------------------------===// 2 // 3 // The MCLinker Project 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 #ifndef MCLD_TARGET_ELFATTRIBUTE_H_ 10 #define MCLD_TARGET_ELFATTRIBUTE_H_ 11 12 #include "mcld/Support/MemoryRegion.h" 13 #include "mcld/Target/ELFAttributeData.h" 14 15 #include <llvm/ADT/SmallVector.h> 16 #include <llvm/ADT/StringRef.h> 17 18 namespace mcld { 19 20 class ELFAttributeData; 21 class GNULDBackend; 22 class Input; 23 class LDSection; 24 class LinkerConfig; 25 26 /** \class ELFAttribute 27 * \brief ELFAttribute is the attribute section in an ELF file. 28 */ 29 class ELFAttribute { 30 public: 31 // ARM [ABI-addenda], 2.2.3. 32 static const char FormatVersion = 'A'; 33 static const size_t FormatVersionFieldSize = sizeof(FormatVersion); // a byte 34 static const size_t SubsectionLengthFieldSize = 4; // a 4-byte integer 35 36 // MinimalELFAttributeSubsectionSize is the minimal number of bytes a valid 37 // subsection in ELF attribute section should have. 38 static const size_t MinimalELFAttributeSubsectionSize = 39 1 /* Tag_File, see ARM [ABI-addenda], 2.2.4 */ + 40 4 /* byte-size, see ARM [ABI-addenda], 2.2.4 */; 41 42 // MinimalELFAttributeSectionSize is the minimal number of bytes a valid ELF 43 // attribute section should have. 44 static const size_t MinimalELFAttributeSectionSize = 45 FormatVersionFieldSize + SubsectionLengthFieldSize + 46 2 /* vendor-name, a char plus '\0', see ARM [ABI-addenda], 2.2.3 */ + 47 1 * MinimalELFAttributeSubsectionSize; 48 49 public: ELFAttribute(const GNULDBackend & pBackend,const LinkerConfig & pConfig)50 ELFAttribute(const GNULDBackend& pBackend, const LinkerConfig& pConfig) 51 : m_Backend(pBackend), m_Config(pConfig) {} 52 53 ~ELFAttribute(); 54 55 public: 56 /// merge - merge attributes from input (attribute) section 57 bool merge(const Input& pInput, LDSection& pInputAttrSectHdr); 58 59 /// sizeOutput - calculate the number of bytes required to encode this 60 /// attribute data section 61 size_t sizeOutput() const; 62 63 /// emit - encode and write out this attribute section 64 size_t emit(MemoryRegion& pRegion) const; 65 backend()66 inline const GNULDBackend& backend() const { return m_Backend; } 67 config()68 inline const LinkerConfig& config() const { return m_Config; } 69 70 // Place vendor's attribute data under the management. 71 void registerAttributeData(ELFAttributeData& pAttrData); 72 73 private: 74 /** \class Subsection 75 * \brief A helper class to wrap ELFAttributeData and to provide general 76 * interfaces for ELFAttribute to operate on 77 */ 78 class Subsection { 79 public: Subsection(ELFAttribute & pParent,ELFAttributeData & pAttrData)80 Subsection(ELFAttribute& pParent, ELFAttributeData& pAttrData) 81 : m_Parent(pParent), m_AttrData(pAttrData) {} 82 83 public: isMyAttribute(llvm::StringRef pVendorName)84 bool isMyAttribute(llvm::StringRef pVendorName) const { 85 return (m_AttrData.getVendorName() == pVendorName); 86 } 87 88 /// merge - Merge the attributes from the section in the input data. 89 bool merge(const Input& pInput, ConstAddress pData, size_t pSize); 90 91 /// sizeOutput - calculate the number of bytes required to encode this 92 /// subsection 93 size_t sizeOutput() const; 94 95 /// emit - write out this attribute subsection to the buffer. 96 size_t emit(char* pBuf) const; 97 98 private: 99 // The attribute section this subsection belongs to 100 ELFAttribute& m_Parent; 101 102 // The attribute data containing in this subsection 103 ELFAttributeData& m_AttrData; 104 }; 105 106 // Obtain the corresponding subsection of the specified vendor 107 Subsection* getSubsection(llvm::StringRef pVendorName) const; 108 109 private: 110 const GNULDBackend& m_Backend; 111 112 const LinkerConfig& m_Config; 113 114 // There is at most two subsections ("aeabi" and "gnu") in most cases. 115 llvm::SmallVector<Subsection*, 2> m_Subsections; 116 }; 117 118 } // namespace mcld 119 120 #endif // MCLD_TARGET_ELFATTRIBUTE_H_ 121