Home | History | Annotate | Download | only in Object
      1 //===- COFF.h - COFF object file 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 // This file declares the COFFObjectFile class.
     11 //
     12 //===----------------------------------------------------------------------===//
     13 
     14 #ifndef LLVM_OBJECT_COFF_H
     15 #define LLVM_OBJECT_COFF_H
     16 
     17 #include "llvm/Object/ObjectFile.h"
     18 #include "llvm/Support/COFF.h"
     19 #include "llvm/Support/Endian.h"
     20 
     21 namespace llvm {
     22   template <typename T>
     23   class ArrayRef;
     24 
     25 namespace object {
     26 
     27 struct coff_file_header {
     28   support::ulittle16_t Machine;
     29   support::ulittle16_t NumberOfSections;
     30   support::ulittle32_t TimeDateStamp;
     31   support::ulittle32_t PointerToSymbolTable;
     32   support::ulittle32_t NumberOfSymbols;
     33   support::ulittle16_t SizeOfOptionalHeader;
     34   support::ulittle16_t Characteristics;
     35 };
     36 
     37 struct coff_symbol {
     38   struct StringTableOffset {
     39     support::ulittle32_t Zeroes;
     40     support::ulittle32_t Offset;
     41   };
     42 
     43   union {
     44     char ShortName[8];
     45     StringTableOffset Offset;
     46   } Name;
     47 
     48   support::ulittle32_t Value;
     49   support::little16_t SectionNumber;
     50 
     51   support::ulittle16_t Type;
     52 
     53   support::ulittle8_t  StorageClass;
     54   support::ulittle8_t  NumberOfAuxSymbols;
     55 
     56   uint8_t getBaseType() const {
     57     return Type & 0x0F;
     58   }
     59 
     60   uint8_t getComplexType() const {
     61     return (Type & 0xF0) >> 4;
     62   }
     63 };
     64 
     65 struct coff_section {
     66   char Name[8];
     67   support::ulittle32_t VirtualSize;
     68   support::ulittle32_t VirtualAddress;
     69   support::ulittle32_t SizeOfRawData;
     70   support::ulittle32_t PointerToRawData;
     71   support::ulittle32_t PointerToRelocations;
     72   support::ulittle32_t PointerToLinenumbers;
     73   support::ulittle16_t NumberOfRelocations;
     74   support::ulittle16_t NumberOfLinenumbers;
     75   support::ulittle32_t Characteristics;
     76 };
     77 
     78 struct coff_relocation {
     79   support::ulittle32_t VirtualAddress;
     80   support::ulittle32_t SymbolTableIndex;
     81   support::ulittle16_t Type;
     82 };
     83 
     84 struct coff_aux_section_definition {
     85   support::ulittle32_t Length;
     86   support::ulittle16_t NumberOfRelocations;
     87   support::ulittle16_t NumberOfLinenumbers;
     88   support::ulittle32_t CheckSum;
     89   support::ulittle16_t Number;
     90   support::ulittle8_t Selection;
     91   char Unused[3];
     92 };
     93 
     94 class COFFObjectFile : public ObjectFile {
     95 private:
     96   const coff_file_header *Header;
     97   const coff_section     *SectionTable;
     98   const coff_symbol      *SymbolTable;
     99   const char             *StringTable;
    100         uint32_t          StringTableSize;
    101 
    102         error_code        getString(uint32_t offset, StringRef &Res) const;
    103 
    104   const coff_symbol      *toSymb(DataRefImpl Symb) const;
    105   const coff_section     *toSec(DataRefImpl Sec) const;
    106   const coff_relocation  *toRel(DataRefImpl Rel) const;
    107 
    108 protected:
    109   virtual error_code getSymbolNext(DataRefImpl Symb, SymbolRef &Res) const;
    110   virtual error_code getSymbolName(DataRefImpl Symb, StringRef &Res) const;
    111   virtual error_code getSymbolFileOffset(DataRefImpl Symb, uint64_t &Res) const;
    112   virtual error_code getSymbolAddress(DataRefImpl Symb, uint64_t &Res) const;
    113   virtual error_code getSymbolSize(DataRefImpl Symb, uint64_t &Res) const;
    114   virtual error_code getSymbolNMTypeChar(DataRefImpl Symb, char &Res) const;
    115   virtual error_code getSymbolFlags(DataRefImpl Symb, uint32_t &Res) const;
    116   virtual error_code getSymbolType(DataRefImpl Symb, SymbolRef::Type &Res) const;
    117   virtual error_code getSymbolSection(DataRefImpl Symb,
    118                                       section_iterator &Res) const;
    119   virtual error_code getSymbolValue(DataRefImpl Symb, uint64_t &Val) const;
    120 
    121   virtual error_code getSectionNext(DataRefImpl Sec, SectionRef &Res) const;
    122   virtual error_code getSectionName(DataRefImpl Sec, StringRef &Res) const;
    123   virtual error_code getSectionAddress(DataRefImpl Sec, uint64_t &Res) const;
    124   virtual error_code getSectionSize(DataRefImpl Sec, uint64_t &Res) const;
    125   virtual error_code getSectionContents(DataRefImpl Sec, StringRef &Res) const;
    126   virtual error_code getSectionAlignment(DataRefImpl Sec, uint64_t &Res) const;
    127   virtual error_code isSectionText(DataRefImpl Sec, bool &Res) const;
    128   virtual error_code isSectionData(DataRefImpl Sec, bool &Res) const;
    129   virtual error_code isSectionBSS(DataRefImpl Sec, bool &Res) const;
    130   virtual error_code isSectionVirtual(DataRefImpl Sec, bool &Res) const;
    131   virtual error_code isSectionZeroInit(DataRefImpl Sec, bool &Res) const;
    132   virtual error_code isSectionReadOnlyData(DataRefImpl Sec, bool &Res) const;
    133   virtual error_code isSectionRequiredForExecution(DataRefImpl Sec,
    134                                                    bool &Res) const;
    135   virtual error_code sectionContainsSymbol(DataRefImpl Sec, DataRefImpl Symb,
    136                                            bool &Result) const;
    137   virtual relocation_iterator getSectionRelBegin(DataRefImpl Sec) const;
    138   virtual relocation_iterator getSectionRelEnd(DataRefImpl Sec) const;
    139 
    140   virtual error_code getRelocationNext(DataRefImpl Rel,
    141                                        RelocationRef &Res) const;
    142   virtual error_code getRelocationAddress(DataRefImpl Rel,
    143                                           uint64_t &Res) const;
    144   virtual error_code getRelocationOffset(DataRefImpl Rel,
    145                                          uint64_t &Res) const;
    146   virtual error_code getRelocationSymbol(DataRefImpl Rel,
    147                                          SymbolRef &Res) const;
    148   virtual error_code getRelocationType(DataRefImpl Rel,
    149                                        uint64_t &Res) const;
    150   virtual error_code getRelocationTypeName(DataRefImpl Rel,
    151                                            SmallVectorImpl<char> &Result) const;
    152   virtual error_code getRelocationAdditionalInfo(DataRefImpl Rel,
    153                                                  int64_t &Res) const;
    154   virtual error_code getRelocationValueString(DataRefImpl Rel,
    155                                            SmallVectorImpl<char> &Result) const;
    156 
    157   virtual error_code getLibraryNext(DataRefImpl LibData,
    158                                     LibraryRef &Result) const;
    159   virtual error_code getLibraryPath(DataRefImpl LibData,
    160                                     StringRef &Result) const;
    161 
    162 public:
    163   COFFObjectFile(MemoryBuffer *Object, error_code &ec);
    164   virtual symbol_iterator begin_symbols() const;
    165   virtual symbol_iterator end_symbols() const;
    166   virtual symbol_iterator begin_dynamic_symbols() const;
    167   virtual symbol_iterator end_dynamic_symbols() const;
    168   virtual library_iterator begin_libraries_needed() const;
    169   virtual library_iterator end_libraries_needed() const;
    170   virtual section_iterator begin_sections() const;
    171   virtual section_iterator end_sections() const;
    172 
    173   const coff_section *getCOFFSection(section_iterator &It) const;
    174   const coff_symbol *getCOFFSymbol(symbol_iterator &It) const;
    175   const coff_relocation *getCOFFRelocation(relocation_iterator &It) const;
    176 
    177   virtual uint8_t getBytesInAddress() const;
    178   virtual StringRef getFileFormatName() const;
    179   virtual unsigned getArch() const;
    180   virtual StringRef getLoadName() const;
    181 
    182   error_code getHeader(const coff_file_header *&Res) const;
    183   error_code getSection(int32_t index, const coff_section *&Res) const;
    184   error_code getSymbol(uint32_t index, const coff_symbol *&Res) const;
    185   template <typename T>
    186   error_code getAuxSymbol(uint32_t index, const T *&Res) const {
    187     const coff_symbol *s;
    188     error_code ec = getSymbol(index, s);
    189     Res = reinterpret_cast<const T*>(s);
    190     return ec;
    191   }
    192   error_code getSymbolName(const coff_symbol *symbol, StringRef &Res) const;
    193   ArrayRef<uint8_t> getSymbolAuxData(const coff_symbol *symbol) const;
    194 
    195   error_code getSectionName(const coff_section *Sec, StringRef &Res) const;
    196   error_code getSectionContents(const coff_section *Sec,
    197                                 ArrayRef<uint8_t> &Res) const;
    198 
    199   static inline bool classof(const Binary *v) {
    200     return v->isCOFF();
    201   }
    202 };
    203 
    204 }
    205 }
    206 
    207 #endif
    208