187f34658dec9097d987d254a990ea7f311bfc95fStephen Hines//===- ELFAttributeData.h -------------------------------------------------===// 287f34658dec9097d987d254a990ea7f311bfc95fStephen Hines// 387f34658dec9097d987d254a990ea7f311bfc95fStephen Hines// The MCLinker Project 487f34658dec9097d987d254a990ea7f311bfc95fStephen Hines// 587f34658dec9097d987d254a990ea7f311bfc95fStephen Hines// This file is distributed under the University of Illinois Open Source 687f34658dec9097d987d254a990ea7f311bfc95fStephen Hines// License. See LICENSE.TXT for details. 787f34658dec9097d987d254a990ea7f311bfc95fStephen Hines// 887f34658dec9097d987d254a990ea7f311bfc95fStephen Hines//===----------------------------------------------------------------------===// 937b74a387bb3993387029859c2d9d051c41c724eStephen Hines#ifndef MCLD_TARGET_ELFATTRIBUTEDATA_H_ 1037b74a387bb3993387029859c2d9d051c41c724eStephen Hines#define MCLD_TARGET_ELFATTRIBUTEDATA_H_ 1187f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 1287f34658dec9097d987d254a990ea7f311bfc95fStephen Hines#include <stdint.h> 1387f34658dec9097d987d254a990ea7f311bfc95fStephen Hines#include <string> 1487f34658dec9097d987d254a990ea7f311bfc95fStephen Hines#include <utility> 1587f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 1687f34658dec9097d987d254a990ea7f311bfc95fStephen Hinesnamespace mcld { 1787f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 1887f34658dec9097d987d254a990ea7f311bfc95fStephen Hinesclass ELFAttributeValue; 1987f34658dec9097d987d254a990ea7f311bfc95fStephen Hinesclass Input; 2087f34658dec9097d987d254a990ea7f311bfc95fStephen Hinesclass LinkerConfig; 2187f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 2287f34658dec9097d987d254a990ea7f311bfc95fStephen Hines/** \class ELFAttributeData 2387f34658dec9097d987d254a990ea7f311bfc95fStephen Hines * \brief ELFAttributeData handles data in vendor attribute subsection. 2487f34658dec9097d987d254a990ea7f311bfc95fStephen Hines */ 2537b74a387bb3993387029859c2d9d051c41c724eStephen Hinesclass ELFAttributeData { 2637b74a387bb3993387029859c2d9d051c41c724eStephen Hines public: 2787f34658dec9097d987d254a990ea7f311bfc95fStephen Hines typedef uint32_t TagType; 2887f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 2987f34658dec9097d987d254a990ea7f311bfc95fStephen Hines // Generic attribute tags shared between all vendors 3087f34658dec9097d987d254a990ea7f311bfc95fStephen Hines enum { 3137b74a387bb3993387029859c2d9d051c41c724eStephen Hines Tag_NULL = 0, 3237b74a387bb3993387029859c2d9d051c41c724eStephen Hines Tag_File = 1, 3337b74a387bb3993387029859c2d9d051c41c724eStephen Hines Tag_Section = 2, 3437b74a387bb3993387029859c2d9d051c41c724eStephen Hines Tag_Symbol = 3, 3587f34658dec9097d987d254a990ea7f311bfc95fStephen Hines }; 3687f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 3737b74a387bb3993387029859c2d9d051c41c724eStephen Hines public: 3837b74a387bb3993387029859c2d9d051c41c724eStephen Hines explicit ELFAttributeData(const char* pVendor) : m_Vendor(pVendor) {} 3987f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 4037b74a387bb3993387029859c2d9d051c41c724eStephen Hines virtual ~ELFAttributeData() {} 4187f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 4237b74a387bb3993387029859c2d9d051c41c724eStephen Hines public: 4337b74a387bb3993387029859c2d9d051c41c724eStephen Hines inline const std::string& getVendorName() const { return m_Vendor; } 4487f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 4587f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// getAttributeValue - query the data store for the attribute value of the 4687f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// given tag. 4737b74a387bb3993387029859c2d9d051c41c724eStephen Hines virtual const ELFAttributeValue* getAttributeValue(TagType pTag) const = 0; 4887f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 4987f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// getOrCreateAttributeValue - obtain attribute value for the given tag and 5087f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// create if it does not exist. 5187f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// 5287f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// It returns a pair containing the attribute value instance (guaranteed to 5387f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// be non-NULL) and a boolean value indicating whether the instance is newly 5487f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// created (true) or not (false.) 5537b74a387bb3993387029859c2d9d051c41c724eStephen Hines virtual std::pair<ELFAttributeValue*, bool> getOrCreateAttributeValue( 5637b74a387bb3993387029859c2d9d051c41c724eStephen Hines TagType pTag) = 0; 5787f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 5887f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// preMerge - hooks to call before starting merge the attribute data in an 5987f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// input. 6037b74a387bb3993387029859c2d9d051c41c724eStephen Hines virtual bool preMerge(const Input& pInput) { return true; } 6187f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 6287f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// merge - implement logics to merge input attribute to the output. 6337b74a387bb3993387029859c2d9d051c41c724eStephen Hines virtual bool merge(const LinkerConfig& pConfig, 6437b74a387bb3993387029859c2d9d051c41c724eStephen Hines const Input& pInput, 6537b74a387bb3993387029859c2d9d051c41c724eStephen Hines TagType pTag, 6637b74a387bb3993387029859c2d9d051c41c724eStephen Hines const ELFAttributeValue& pInAttr) = 0; 6787f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 6887f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// postMerge - hooks to call after finishing merge the attribute data from an 6987f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// input. 7037b74a387bb3993387029859c2d9d051c41c724eStephen Hines virtual bool postMerge(const LinkerConfig& pConfig, const Input& pInput) { 7137b74a387bb3993387029859c2d9d051c41c724eStephen Hines return true; 7237b74a387bb3993387029859c2d9d051c41c724eStephen Hines } 7387f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 7487f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// sizeOutput - obtain number of bytes required to encode the attribute data. 7587f34658dec9097d987d254a990ea7f311bfc95fStephen Hines virtual size_t sizeOutput() const = 0; 7687f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 7787f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// emit - write out attribute data to the buffer and return the number of 7887f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// bytes written 7937b74a387bb3993387029859c2d9d051c41c724eStephen Hines virtual size_t emit(char* pBuf) const = 0; 8087f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 8137b74a387bb3993387029859c2d9d051c41c724eStephen Hines public: 8287f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// ReadTag - read an attribute tag from input buffer. 8387f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// 8487f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// If the read succeeds, pBuf moves to the new position just pass the end of 8587f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// the tag in the buffer and pBufSize decreases the size of tag in the 8687f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// buffer. Otherwise, this function will return false and change nothing 8787f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// except leaving undefined value in pTag. 8837b74a387bb3993387029859c2d9d051c41c724eStephen Hines static bool ReadTag(TagType& pTag, const char*& pBuf, size_t& pBufSize); 8987f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 9087f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// ReadValue - read an attribute value from input buffer 9187f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// 9287f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// Similar with ReadTag() while this reads attribute value from the input 9387f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// buffer. Note that the value type of the attribute must be properly set in 9487f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// pValue prior the call. 9537b74a387bb3993387029859c2d9d051c41c724eStephen Hines static bool ReadValue(ELFAttributeValue& pValue, 9637b74a387bb3993387029859c2d9d051c41c724eStephen Hines const char*& pBuf, 9737b74a387bb3993387029859c2d9d051c41c724eStephen Hines size_t& pBufSize); 9887f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 9987f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// WriteAttribute - write an attribute tag plus value to buffer. 10087f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// 10187f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// On success, the pBuf moves to the new position just pass the end of the 10287f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// attribute data just written. Otherwise, it returns false and leaves pBuf 10387f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// in an undefined position. Note that buffer is guaranteed to be able to 10487f34658dec9097d987d254a990ea7f311bfc95fStephen Hines /// contain the attribute data. 10537b74a387bb3993387029859c2d9d051c41c724eStephen Hines static bool WriteAttribute(TagType pTag, 10637b74a387bb3993387029859c2d9d051c41c724eStephen Hines const ELFAttributeValue& pValue, 10737b74a387bb3993387029859c2d9d051c41c724eStephen Hines char*& pBuf); 10887f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 10937b74a387bb3993387029859c2d9d051c41c724eStephen Hines private: 11087f34658dec9097d987d254a990ea7f311bfc95fStephen Hines const std::string m_Vendor; 11187f34658dec9097d987d254a990ea7f311bfc95fStephen Hines}; 11287f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 11337b74a387bb3993387029859c2d9d051c41c724eStephen Hines} // namespace mcld 11487f34658dec9097d987d254a990ea7f311bfc95fStephen Hines 11537b74a387bb3993387029859c2d9d051c41c724eStephen Hines#endif // MCLD_TARGET_ELFATTRIBUTEDATA_H_ 116