Home | History | Annotate | Download | only in Object
      1 //===- ObjectLinker.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 //
     10 // ObjectLinker plays the same role as GNU collect2 to prepare all implicit
     11 // parameters for FragmentLinker.
     12 //
     13 //===----------------------------------------------------------------------===//
     14 #ifndef MCLD_OBJECT_OBJECT_LINKER_H
     15 #define MCLD_OBJECT_OBJECT_LINKER_H
     16 #ifdef ENABLE_UNITTEST
     17 #include <gtest.h>
     18 #endif
     19 #include <stddef.h>
     20 
     21 namespace mcld {
     22 
     23 class Module;
     24 class LinkerConfig;
     25 class IRBuilder;
     26 class FragmentLinker;
     27 class TargetLDBackend;
     28 class MemoryArea;
     29 class MemoryAreaFactory;
     30 class ObjectReader;
     31 class DynObjReader;
     32 class ArchiveReader;
     33 class GroupReader;
     34 class BinaryReader;
     35 class ObjectWriter;
     36 class DynObjWriter;
     37 class ExecWriter;
     38 class BinaryWriter;
     39 
     40 /** \class ObjectLinker
     41  *  \brief ObjectLinker prepares parameters for FragmentLinker.
     42  */
     43 class ObjectLinker
     44 {
     45 public:
     46   ObjectLinker(const LinkerConfig& pConfig,
     47                TargetLDBackend& pLDBackend);
     48 
     49   ~ObjectLinker();
     50 
     51   void setup(Module& pModule, IRBuilder& pBuilder);
     52 
     53   /// initFragmentLinker - initialize FragmentLinker
     54   ///  Connect all components in FragmentLinker
     55   bool initFragmentLinker();
     56 
     57   /// initStdSections - initialize standard sections of the output file.
     58   bool initStdSections();
     59 
     60   /// normalize - normalize the input files
     61   void normalize();
     62 
     63   /// linkable - check the linkability of current LinkerConfig
     64   ///  Check list:
     65   ///  - check the Attributes are not violate the constaint
     66   ///  - check every Input has a correct Attribute
     67   bool linkable() const;
     68 
     69   /// readRelocations - read all relocation entries
     70   bool readRelocations();
     71 
     72   /// mergeSections - put allinput sections into output sections
     73   bool mergeSections();
     74 
     75   /// allocateCommonSymobols - allocate fragments for common symbols to the
     76   /// corresponding sections
     77   bool allocateCommonSymbols();
     78 
     79   /// addStandardSymbols - shared object and executable files need some
     80   /// standard symbols
     81   ///   @return if there are some input symbols with the same name to the
     82   ///   standard symbols, return false
     83   bool addStandardSymbols();
     84 
     85   /// addTargetSymbols - some targets, such as MIPS and ARM, need some
     86   /// target-dependent symbols
     87   ///   @return if there are some input symbols with the same name to the
     88   ///   target symbols, return false
     89   bool addTargetSymbols();
     90 
     91   /// addScriptSymbols - define symbols from the command line option or linker
     92   /// scripts.
     93   ///   @return if there are some existing symbols with identical name to the
     94   ///   script symbols, return false.
     95   bool addScriptSymbols();
     96 
     97   /// scanRelocations - scan all relocation entries by output symbols.
     98   bool scanRelocations();
     99 
    100   /// initStubs - initialize stub-related stuff.
    101   bool initStubs();
    102 
    103   /// prelayout - help backend to do some modification before layout
    104   bool prelayout();
    105 
    106   /// layout - linearly layout all output sections and reserve some space
    107   /// for GOT/PLT
    108   ///   Because we do not support instruction relaxing in this early version,
    109   ///   if there is a branch can not jump to its target, we return false
    110   ///   directly
    111   bool layout();
    112 
    113   /// postlayout - help backend to do some modification after layout
    114   bool postlayout();
    115 
    116   /// relocate - applying relocation entries and create relocation
    117   /// section in the output files
    118   /// Create relocation section, asking TargetLDBackend to
    119   /// read the relocation information into RelocationEntry
    120   /// and push_back into the relocation section
    121   bool relocation();
    122 
    123   /// finalizeSymbolValue - finalize the symbol value
    124   bool finalizeSymbolValue();
    125 
    126   /// emitOutput - emit the output file.
    127   bool emitOutput(MemoryArea& pOutput);
    128 
    129   /// postProcessing - do modificatiion after all processes
    130   bool postProcessing(MemoryArea& pOutput);
    131 
    132   /// getLinker - get internal FragmentLinker object
    133   const FragmentLinker* getLinker() const { return m_pLinker; }
    134   FragmentLinker*       getLinker()       { return m_pLinker; }
    135 
    136   /// hasInitLinker - has Linker been initialized?
    137   bool hasInitLinker() const
    138   { return (NULL != m_pLinker); }
    139 
    140   // -----  readers and writers  ----- //
    141   const ObjectReader*  getObjectReader () const { return m_pObjectReader;  }
    142   ObjectReader*        getObjectReader ()       { return m_pObjectReader;  }
    143 
    144   const DynObjReader*  getDynObjReader () const { return m_pDynObjReader;  }
    145   DynObjReader*        getDynObjReader ()       { return m_pDynObjReader;  }
    146 
    147   const ArchiveReader* getArchiveReader() const { return m_pArchiveReader; }
    148   ArchiveReader*       getArchiveReader()       { return m_pArchiveReader; }
    149 
    150   const GroupReader*   getGroupReader  () const { return m_pGroupReader;   }
    151   GroupReader*         getGroupReader  ()       { return m_pGroupReader;   }
    152 
    153   const BinaryReader*  getBinaryReader () const { return m_pBinaryReader;  }
    154   BinaryReader*        getBinaryReader ()       { return m_pBinaryReader;  }
    155 
    156   const ObjectWriter*  getWriter () const { return m_pWriter;  }
    157   ObjectWriter*        getWriter ()       { return m_pWriter;  }
    158 
    159 private:
    160   const LinkerConfig& m_Config;
    161   FragmentLinker* m_pLinker;
    162   Module* m_pModule;
    163   IRBuilder* m_pBuilder;
    164 
    165   TargetLDBackend &m_LDBackend;
    166 
    167   // -----  readers and writers  ----- //
    168   ObjectReader*  m_pObjectReader;
    169   DynObjReader*  m_pDynObjReader;
    170   ArchiveReader* m_pArchiveReader;
    171   GroupReader*   m_pGroupReader;
    172   BinaryReader*  m_pBinaryReader;
    173   ObjectWriter*  m_pWriter;
    174 };
    175 
    176 } // end namespace mcld
    177 #endif
    178