1//===- MCLDDriver.cpp -----------------------------------------------------===// 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#include <mcld/MC/InputTree.h> 10#include <mcld/MC/MCLinker.h> 11#include <mcld/MC/MCLDDriver.h> 12#include <mcld/MC/MCLDInfo.h> 13#include <mcld/LD/ArchiveReader.h> 14#include <mcld/LD/ObjectReader.h> 15#include <mcld/LD/DynObjReader.h> 16#include <mcld/LD/ObjectWriter.h> 17#include <mcld/LD/DynObjWriter.h> 18#include <mcld/LD/ExecWriter.h> 19#include <mcld/LD/ResolveInfo.h> 20#include <mcld/Support/RealPath.h> 21#include <mcld/Support/MemoryAreaFactory.h> 22#include <mcld/Target/TargetLDBackend.h> 23#include <mcld/Support/MsgHandling.h> 24#include <mcld/LD/Archive.h> 25 26using namespace llvm; 27using namespace mcld; 28 29MCLDDriver::MCLDDriver(MCLDInfo& pLDInfo, 30 TargetLDBackend& pLDBackend, 31 MemoryAreaFactory& pAreaFactory) 32 : m_LDInfo(pLDInfo), 33 m_LDBackend(pLDBackend), 34 m_pLinker(NULL), 35 m_AreaFactory(pAreaFactory) { 36 37} 38 39MCLDDriver::~MCLDDriver() 40{ 41 if (NULL != m_pLinker) 42 delete m_pLinker; 43} 44 45/// initMCLinker - initialize MCLinker 46/// Connect all components with MCLinker 47bool MCLDDriver::initMCLinker() 48{ 49 if (0 == m_pLinker) 50 m_pLinker = new MCLinker(m_LDBackend, 51 m_LDInfo, 52 m_SectionMap); 53 54 // initialize the readers and writers 55 // Because constructor can not be failed, we initalize all readers and 56 // writers outside the MCLinker constructors. 57 if (!m_LDBackend.initObjectReader(*m_pLinker) || 58 !m_LDBackend.initArchiveReader(*m_pLinker, m_LDInfo, m_AreaFactory) || 59 !m_LDBackend.initObjectReader(*m_pLinker) || 60 !m_LDBackend.initDynObjReader(*m_pLinker) || 61 !m_LDBackend.initObjectWriter(*m_pLinker) || 62 !m_LDBackend.initDynObjWriter(*m_pLinker) || 63 !m_LDBackend.initExecWriter(*m_pLinker)) 64 return false; 65 66 // initialize RelocationFactory 67 m_LDBackend.initRelocFactory(*m_pLinker); 68 return true; 69} 70 71/// initStdSections - initialize standard sections 72bool MCLDDriver::initStdSections() 73{ 74 /// initialize section mapping for standard format, target-dependent section, 75 /// (and user-defined mapping) 76 if (!m_SectionMap.initStdSectionMap() || 77 !m_LDBackend.initTargetSectionMap(m_SectionMap)) 78 return false; 79 80 /// A technical debt. We need to initialize section map here because 81 /// we do not separate output file and temporary data structure. So far, 82 /// MCLinker directly use output file's LDContext as the temporary data 83 /// structure. We will create a new data structure mcld::Module to collect 84 /// all temporary data structures togather. 85 m_pLinker->initSectionMap(); 86 87 // initialize standard sections 88 switch (m_LDInfo.output().type()) { 89 case Output::DynObj: { 90 // intialize standard and target-dependent sections 91 if (!m_LDBackend.initDynObjSections(*m_pLinker)) 92 return false; 93 break; 94 } 95 case Output::Exec: { 96 // intialize standard and target-dependent sections 97 if (!m_LDBackend.initExecSections(*m_pLinker)) 98 return false; 99 break; 100 } 101 case Output::Object: { 102 llvm::report_fatal_error(llvm::Twine("output type is not implemented yet. file: `") + 103 m_LDInfo.output().name() + 104 llvm::Twine("'.")); 105 return false; 106 } 107 default: { 108 llvm::report_fatal_error(llvm::Twine("unknown output type of file `") + 109 m_LDInfo.output().name() + 110 llvm::Twine("'.")); 111 return false; 112 } 113 } // end of switch 114 115 // initialize target-dependent sections 116 m_LDBackend.initTargetSections(*m_pLinker); 117 118 return true; 119} 120 121void MCLDDriver::normalize() 122{ 123 // ----- set up inputs ----- // 124 InputTree::iterator input, inEnd = m_LDInfo.inputs().end(); 125 for (input = m_LDInfo.inputs().begin(); input!=inEnd; ++input) { 126 // already got type - for example, bitcode or external OIR (object 127 // intermediate representation) 128 if ((*input)->type() == Input::Script || 129 (*input)->type() == Input::Object || 130 (*input)->type() == Input::DynObj || 131 (*input)->type() == Input::Archive || 132 (*input)->type() == Input::External) 133 continue; 134 135 // is a relocatable object file 136 if (m_LDBackend.getObjectReader()->isMyFormat(**input)) { 137 (*input)->setType(Input::Object); 138 m_LDBackend.getObjectReader()->readObject(**input); 139 m_LDBackend.getObjectReader()->readSections(**input); 140 m_LDBackend.getObjectReader()->readSymbols(**input); 141 } 142 // is a shared object file 143 else if (m_LDBackend.getDynObjReader()->isMyFormat(**input)) { 144 (*input)->setType(Input::DynObj); 145 m_LDBackend.getDynObjReader()->readDSO(**input); 146 m_LDBackend.getDynObjReader()->readSymbols(**input); 147 } 148 // is an archive 149 else if (m_LDBackend.getArchiveReader()->isMyFormat(**input)) { 150 (*input)->setType(Input::Archive); 151 Archive archive(**input, m_LDInfo.inputFactory()); 152 m_LDBackend.getArchiveReader()->readArchive(archive); 153 if(archive.numOfObjectMember() > 0) { 154 m_LDInfo.inputs().merge<InputTree::Inclusive>(input, archive.inputs()); 155 } 156 } 157 else { 158 fatal(diag::err_unrecognized_input_file) << (*input)->path() 159 << m_LDInfo.triple().str(); 160 } 161 } // end of for 162} 163 164bool MCLDDriver::linkable() const 165{ 166 // check we have input and output files 167 if (m_LDInfo.inputs().empty()) { 168 error(diag::err_no_inputs); 169 return false; 170 } 171 172 // check all attributes are legal 173 mcld::AttributeFactory::const_iterator attr, attrEnd = m_LDInfo.attrFactory().end(); 174 for (attr=m_LDInfo.attrFactory().begin(); attr!=attrEnd; ++attr) { 175 if (!m_LDInfo.attrFactory().constraint().isLegal((**attr))) { 176 return false; 177 } 178 } 179 180 // can not mix -static with shared objects 181 mcld::InputTree::const_bfs_iterator input, inEnd = m_LDInfo.inputs().bfs_end(); 182 for (input=m_LDInfo.inputs().bfs_begin(); input!=inEnd; ++input) { 183 if ((*input)->type() == mcld::Input::DynObj) { 184 if((*input)->attribute()->isStatic()) { 185 error(diag::err_mixed_shared_static_objects) 186 << (*input)->name() << (*input)->path(); 187 return false; 188 } 189 } 190 } 191 192 // can not mix -r with shared objects 193 return true; 194} 195 196/// mergeSections - put allinput sections into output sections 197bool MCLDDriver::mergeSections() 198{ 199 // TODO: when MCLinker can read other object files, we have to merge 200 // sections 201 return true; 202} 203 204/// addStandardSymbols - shared object and executable files need some 205/// standard symbols 206/// @return if there are some input symbols with the same name to the 207/// standard symbols, return false 208bool MCLDDriver::addStandardSymbols() 209{ 210 return m_LDBackend.initStandardSymbols(*m_pLinker, m_LDInfo.output()); 211} 212 213/// addTargetSymbols - some targets, such as MIPS and ARM, need some 214/// target-dependent symbols 215/// @return if there are some input symbols with the same name to the 216/// target symbols, return false 217bool MCLDDriver::addTargetSymbols() 218{ 219 m_LDBackend.initTargetSymbols(*m_pLinker, m_LDInfo.output()); 220 return true; 221} 222 223/// readRelocations - read all relocation entries 224/// 225/// All symbols should be read and resolved before this function. 226bool MCLDDriver::readRelocations() 227{ 228 // Bitcode is read by the other path. This function reads relocation sections 229 // in object files. 230 mcld::InputTree::bfs_iterator input, inEnd = m_LDInfo.inputs().bfs_end(); 231 for (input=m_LDInfo.inputs().bfs_begin(); input!=inEnd; ++input) { 232 if ((*input)->type() == Input::Object) { 233 if (!m_LDBackend.getObjectReader()->readRelocations(**input)) 234 return false; 235 } 236 // ignore the other kinds of files. 237 } 238 return true; 239} 240 241/// prelayout - help backend to do some modification before layout 242bool MCLDDriver::prelayout() 243{ 244 m_LDBackend.preLayout(m_LDInfo.output(), 245 m_LDInfo, 246 *m_pLinker); 247 248 m_LDBackend.allocateCommonSymbols(m_LDInfo, *m_pLinker); 249 250 /// check program interpreter - computer the name size of the runtime dyld 251 /// FIXME: check if we are doing static linking! 252 if (m_LDInfo.output().type() == Output::Exec) 253 m_LDBackend.sizeInterp(m_LDInfo.output(), m_LDInfo); 254 255 /// measure NamePools - compute the size of name pool sections 256 /// In ELF, will compute the size of.symtab, .strtab, .dynsym, .dynstr, 257 /// and .hash sections. 258 /// 259 /// dump all symbols and strings from MCLinker and build the format-dependent 260 /// hash table. 261 m_LDBackend.sizeNamePools(m_LDInfo.output(), m_pLinker->getOutputSymbols(), m_LDInfo); 262 263 return true; 264} 265 266/// layout - linearly layout all output sections and reserve some space 267/// for GOT/PLT 268/// Because we do not support instruction relaxing in this early version, 269/// if there is a branch can not jump to its target, we return false 270/// directly 271bool MCLDDriver::layout() 272{ 273 return m_pLinker->layout(); 274} 275 276/// prelayout - help backend to do some modification after layout 277bool MCLDDriver::postlayout() 278{ 279 m_LDBackend.postLayout(m_LDInfo.output(), 280 m_LDInfo, 281 *m_pLinker); 282 return true; 283} 284 285/// finalizeSymbolValue - finalize the resolved symbol value. 286/// Before relocate(), after layout(), MCLinker should correct value of all 287/// symbol. 288bool MCLDDriver::finalizeSymbolValue() 289{ 290 return m_pLinker->finalizeSymbols(); 291} 292 293/// relocate - applying relocation entries and create relocation 294/// section in the output files 295/// Create relocation section, asking TargetLDBackend to 296/// read the relocation information into RelocationEntry 297/// and push_back into the relocation section 298bool MCLDDriver::relocation() 299{ 300 return m_pLinker->applyRelocations(); 301} 302 303/// emitOutput - emit the output file. 304bool MCLDDriver::emitOutput() 305{ 306 switch(m_LDInfo.output().type()) { 307 case Output::Object: 308 m_LDBackend.getObjectWriter()->writeObject(m_LDInfo.output()); 309 return true; 310 case Output::DynObj: 311 m_LDBackend.getDynObjWriter()->writeDynObj(m_LDInfo.output()); 312 return true; 313 case Output::Exec: 314 m_LDBackend.getExecWriter()->writeExecutable(m_LDInfo.output()); 315 return true; 316 } 317 return false; 318} 319 320/// postProcessing - do modification after all processes 321bool MCLDDriver::postProcessing() 322{ 323 m_pLinker->syncRelocationResult(); 324 325 m_LDBackend.postProcessing(m_LDInfo.output(), 326 m_LDInfo, 327 *m_pLinker); 328 return true; 329} 330