Grammar.
[oota-llvm.git] / lib / ExecutionEngine / RuntimeDyld / RuntimeDyldELF.cpp
1 //===-- RuntimeDyldELF.cpp - Run-time dynamic linker for MC-JIT -*- 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 // Implementation of ELF support for the MC-JIT runtime dynamic linker.
11 //
12 //===----------------------------------------------------------------------===//
13
14 #define DEBUG_TYPE "dyld"
15 #include "RuntimeDyldELF.h"
16 #include "JITRegistrar.h"
17 #include "ObjectImageCommon.h"
18 #include "llvm/ADT/OwningPtr.h"
19 #include "llvm/ADT/StringRef.h"
20 #include "llvm/ADT/STLExtras.h"
21 #include "llvm/ADT/IntervalMap.h"
22 #include "llvm/Object/ObjectFile.h"
23 #include "llvm/ExecutionEngine/ObjectImage.h"
24 #include "llvm/ExecutionEngine/ObjectBuffer.h"
25 #include "llvm/Support/ELF.h"
26 #include "llvm/ADT/Triple.h"
27 #include "llvm/Object/ELF.h"
28 using namespace llvm;
29 using namespace llvm::object;
30
31 namespace {
32
33 template<support::endianness target_endianness, bool is64Bits>
34 class DyldELFObject : public ELFObjectFile<target_endianness, is64Bits> {
35   LLVM_ELF_IMPORT_TYPES(target_endianness, is64Bits)
36
37   typedef Elf_Shdr_Impl<target_endianness, is64Bits> Elf_Shdr;
38   typedef Elf_Sym_Impl<target_endianness, is64Bits> Elf_Sym;
39   typedef Elf_Rel_Impl<target_endianness, is64Bits, false> Elf_Rel;
40   typedef Elf_Rel_Impl<target_endianness, is64Bits, true> Elf_Rela;
41
42   typedef Elf_Ehdr_Impl<target_endianness, is64Bits> Elf_Ehdr;
43
44   typedef typename ELFDataTypeTypedefHelper<
45           target_endianness, is64Bits>::value_type addr_type;
46
47 public:
48   DyldELFObject(MemoryBuffer *Wrapper, error_code &ec);
49
50   void updateSectionAddress(const SectionRef &Sec, uint64_t Addr);
51   void updateSymbolAddress(const SymbolRef &Sym, uint64_t Addr);
52
53   // Methods for type inquiry through isa, cast and dyn_cast
54   static inline bool classof(const Binary *v) {
55     return (isa<ELFObjectFile<target_endianness, is64Bits> >(v)
56             && classof(cast<ELFObjectFile<target_endianness, is64Bits> >(v)));
57   }
58   static inline bool classof(
59       const ELFObjectFile<target_endianness, is64Bits> *v) {
60     return v->isDyldType();
61   }
62 };
63
64 template<support::endianness target_endianness, bool is64Bits>
65 class ELFObjectImage : public ObjectImageCommon {
66   protected:
67     DyldELFObject<target_endianness, is64Bits> *DyldObj;
68     bool Registered;
69
70   public:
71     ELFObjectImage(ObjectBuffer *Input,
72                    DyldELFObject<target_endianness, is64Bits> *Obj)
73     : ObjectImageCommon(Input, Obj),
74       DyldObj(Obj),
75       Registered(false) {}
76
77     virtual ~ELFObjectImage() {
78       if (Registered)
79         deregisterWithDebugger();
80     }
81
82     // Subclasses can override these methods to update the image with loaded
83     // addresses for sections and common symbols
84     virtual void updateSectionAddress(const SectionRef &Sec, uint64_t Addr)
85     {
86       DyldObj->updateSectionAddress(Sec, Addr);
87     }
88
89     virtual void updateSymbolAddress(const SymbolRef &Sym, uint64_t Addr)
90     {
91       DyldObj->updateSymbolAddress(Sym, Addr);
92     }
93
94     virtual void registerWithDebugger()
95     {
96       JITRegistrar::getGDBRegistrar().registerObject(*Buffer);
97       Registered = true;
98     }
99     virtual void deregisterWithDebugger()
100     {
101       JITRegistrar::getGDBRegistrar().deregisterObject(*Buffer);
102     }
103 };
104
105 // The MemoryBuffer passed into this constructor is just a wrapper around the
106 // actual memory.  Ultimately, the Binary parent class will take ownership of
107 // this MemoryBuffer object but not the underlying memory.
108 template<support::endianness target_endianness, bool is64Bits>
109 DyldELFObject<target_endianness, is64Bits>::DyldELFObject(MemoryBuffer *Wrapper,
110                                                           error_code &ec)
111   : ELFObjectFile<target_endianness, is64Bits>(Wrapper, ec) {
112   this->isDyldELFObject = true;
113 }
114
115 template<support::endianness target_endianness, bool is64Bits>
116 void DyldELFObject<target_endianness, is64Bits>::updateSectionAddress(
117                                                        const SectionRef &Sec,
118                                                        uint64_t Addr) {
119   DataRefImpl ShdrRef = Sec.getRawDataRefImpl();
120   Elf_Shdr *shdr = const_cast<Elf_Shdr*>(
121                           reinterpret_cast<const Elf_Shdr *>(ShdrRef.p));
122
123   // This assumes the address passed in matches the target address bitness
124   // The template-based type cast handles everything else.
125   shdr->sh_addr = static_cast<addr_type>(Addr);
126 }
127
128 template<support::endianness target_endianness, bool is64Bits>
129 void DyldELFObject<target_endianness, is64Bits>::updateSymbolAddress(
130                                                        const SymbolRef &SymRef,
131                                                        uint64_t Addr) {
132
133   Elf_Sym *sym = const_cast<Elf_Sym*>(
134                                  ELFObjectFile<target_endianness, is64Bits>::
135                                    getSymbol(SymRef.getRawDataRefImpl()));
136
137   // This assumes the address passed in matches the target address bitness
138   // The template-based type cast handles everything else.
139   sym->st_value = static_cast<addr_type>(Addr);
140 }
141
142 } // namespace
143
144
145 namespace llvm {
146
147 ObjectImage *RuntimeDyldELF::createObjectImage(ObjectBuffer *Buffer) {
148   if (Buffer->getBufferSize() < ELF::EI_NIDENT)
149     llvm_unreachable("Unexpected ELF object size");
150   std::pair<unsigned char, unsigned char> Ident = std::make_pair(
151                          (uint8_t)Buffer->getBufferStart()[ELF::EI_CLASS],
152                          (uint8_t)Buffer->getBufferStart()[ELF::EI_DATA]);
153   error_code ec;
154
155   if (Ident.first == ELF::ELFCLASS32 && Ident.second == ELF::ELFDATA2LSB) {
156     DyldELFObject<support::little, false> *Obj =
157            new DyldELFObject<support::little, false>(Buffer->getMemBuffer(), ec);
158     return new ELFObjectImage<support::little, false>(Buffer, Obj);
159   }
160   else if (Ident.first == ELF::ELFCLASS32 && Ident.second == ELF::ELFDATA2MSB) {
161     DyldELFObject<support::big, false> *Obj =
162            new DyldELFObject<support::big, false>(Buffer->getMemBuffer(), ec);
163     return new ELFObjectImage<support::big, false>(Buffer, Obj);
164   }
165   else if (Ident.first == ELF::ELFCLASS64 && Ident.second == ELF::ELFDATA2MSB) {
166     DyldELFObject<support::big, true> *Obj =
167            new DyldELFObject<support::big, true>(Buffer->getMemBuffer(), ec);
168     return new ELFObjectImage<support::big, true>(Buffer, Obj);
169   }
170   else if (Ident.first == ELF::ELFCLASS64 && Ident.second == ELF::ELFDATA2LSB) {
171     DyldELFObject<support::little, true> *Obj =
172            new DyldELFObject<support::little, true>(Buffer->getMemBuffer(), ec);
173     return new ELFObjectImage<support::little, true>(Buffer, Obj);
174   }
175   else
176     llvm_unreachable("Unexpected ELF format");
177 }
178
179 RuntimeDyldELF::~RuntimeDyldELF() {
180 }
181
182 void RuntimeDyldELF::resolveX86_64Relocation(uint8_t *LocalAddress,
183                                              uint64_t FinalAddress,
184                                              uint64_t Value,
185                                              uint32_t Type,
186                                              int64_t Addend) {
187   switch (Type) {
188   default:
189     llvm_unreachable("Relocation type not implemented yet!");
190   break;
191   case ELF::R_X86_64_64: {
192     uint64_t *Target = (uint64_t*)(LocalAddress);
193     *Target = Value + Addend;
194     break;
195   }
196   case ELF::R_X86_64_32:
197   case ELF::R_X86_64_32S: {
198     Value += Addend;
199     assert((Type == ELF::R_X86_64_32 && (Value <= UINT32_MAX)) ||
200            (Type == ELF::R_X86_64_32S && 
201              ((int64_t)Value <= INT32_MAX && (int64_t)Value >= INT32_MIN)));
202     uint32_t TruncatedAddr = (Value & 0xFFFFFFFF);
203     uint32_t *Target = reinterpret_cast<uint32_t*>(LocalAddress);
204     *Target = TruncatedAddr;
205     break;
206   }
207   case ELF::R_X86_64_PC32: {
208     uint32_t *Placeholder = reinterpret_cast<uint32_t*>(LocalAddress);
209     int64_t RealOffset = *Placeholder + Value + Addend - FinalAddress;
210     assert(RealOffset <= INT32_MAX && RealOffset >= INT32_MIN);
211     int32_t TruncOffset = (RealOffset & 0xFFFFFFFF);
212     *Placeholder = TruncOffset;
213     break;
214   }
215   }
216 }
217
218 void RuntimeDyldELF::resolveX86Relocation(uint8_t *LocalAddress,
219                                           uint32_t FinalAddress,
220                                           uint32_t Value,
221                                           uint32_t Type,
222                                           int32_t Addend) {
223   switch (Type) {
224   case ELF::R_386_32: {
225     uint32_t *Target = (uint32_t*)(LocalAddress);
226     uint32_t Placeholder = *Target;
227     *Target = Placeholder + Value + Addend;
228     break;
229   }
230   case ELF::R_386_PC32: {
231     uint32_t *Placeholder = reinterpret_cast<uint32_t*>(LocalAddress);
232     uint32_t RealOffset = *Placeholder + Value + Addend - FinalAddress;
233     *Placeholder = RealOffset;
234     break;
235     }
236     default:
237       // There are other relocation types, but it appears these are the
238       // only ones currently used by the LLVM ELF object writer
239       llvm_unreachable("Relocation type not implemented yet!");
240       break;
241   }
242 }
243
244 void RuntimeDyldELF::resolveARMRelocation(uint8_t *LocalAddress,
245                                           uint32_t FinalAddress,
246                                           uint32_t Value,
247                                           uint32_t Type,
248                                           int32_t Addend) {
249   // TODO: Add Thumb relocations.
250   uint32_t* TargetPtr = (uint32_t*)LocalAddress;
251   Value += Addend;
252
253   DEBUG(dbgs() << "resolveARMRelocation, LocalAddress: " << LocalAddress
254                << " FinalAddress: " << format("%p",FinalAddress)
255                << " Value: " << format("%x",Value)
256                << " Type: " << format("%x",Type)
257                << " Addend: " << format("%x",Addend)
258                << "\n");
259
260   switch(Type) {
261   default:
262     llvm_unreachable("Not implemented relocation type!");
263
264   // Write a 32bit value to relocation address, taking into account the 
265   // implicit addend encoded in the target.
266   case ELF::R_ARM_ABS32 :
267     *TargetPtr += Value;
268     break;
269
270   // Write first 16 bit of 32 bit value to the mov instruction.
271   // Last 4 bit should be shifted.
272   case ELF::R_ARM_MOVW_ABS_NC :
273     // We are not expecting any other addend in the relocation address.
274     // Using 0x000F0FFF because MOVW has its 16 bit immediate split into 2 
275     // non-contiguous fields.
276     assert((*TargetPtr & 0x000F0FFF) == 0);
277     Value = Value & 0xFFFF;
278     *TargetPtr |= Value & 0xFFF;
279     *TargetPtr |= ((Value >> 12) & 0xF) << 16;
280     break;
281
282   // Write last 16 bit of 32 bit value to the mov instruction.
283   // Last 4 bit should be shifted.
284   case ELF::R_ARM_MOVT_ABS :
285     // We are not expecting any other addend in the relocation address.
286     // Use 0x000F0FFF for the same reason as R_ARM_MOVW_ABS_NC.
287     assert((*TargetPtr & 0x000F0FFF) == 0);
288     Value = (Value >> 16) & 0xFFFF;
289     *TargetPtr |= Value & 0xFFF;
290     *TargetPtr |= ((Value >> 12) & 0xF) << 16;
291     break;
292
293   // Write 24 bit relative value to the branch instruction.
294   case ELF::R_ARM_PC24 :    // Fall through.
295   case ELF::R_ARM_CALL :    // Fall through.
296   case ELF::R_ARM_JUMP24 :
297     int32_t RelValue = static_cast<int32_t>(Value - FinalAddress - 8);
298     RelValue = (RelValue & 0x03FFFFFC) >> 2;
299     *TargetPtr &= 0xFF000000;
300     *TargetPtr |= RelValue;
301     break;
302   }
303 }
304
305 void RuntimeDyldELF::resolveMIPSRelocation(uint8_t *LocalAddress,
306                                            uint32_t FinalAddress,
307                                            uint32_t Value,
308                                            uint32_t Type,
309                                            int32_t Addend) {
310   uint32_t* TargetPtr = (uint32_t*)LocalAddress;
311   Value += Addend;
312
313   DEBUG(dbgs() << "resolveMipselocation, LocalAddress: " << LocalAddress
314                << " FinalAddress: " << format("%p",FinalAddress)
315                << " Value: " << format("%x",Value)
316                << " Type: " << format("%x",Type)
317                << " Addend: " << format("%x",Addend)
318                << "\n");
319
320   switch(Type) {
321   default:
322     llvm_unreachable("Not implemented relocation type!");
323     break;
324   case ELF::R_MIPS_32:
325     *TargetPtr = Value + (*TargetPtr);
326     break;
327   case ELF::R_MIPS_26:
328     *TargetPtr = ((*TargetPtr) & 0xfc000000) | (( Value & 0x0fffffff) >> 2);
329     break;
330   case ELF::R_MIPS_HI16:
331     // Get the higher 16-bits. Also add 1 if bit 15 is 1.
332     Value += ((*TargetPtr) & 0x0000ffff) << 16;
333     *TargetPtr = ((*TargetPtr) & 0xffff0000) |
334                  (((Value + 0x8000) >> 16) & 0xffff);
335     break;
336    case ELF::R_MIPS_LO16:
337     Value += ((*TargetPtr) & 0x0000ffff);
338     *TargetPtr = ((*TargetPtr) & 0xffff0000) | (Value & 0xffff);
339     break;
340    }
341 }
342
343 void RuntimeDyldELF::resolveRelocation(uint8_t *LocalAddress,
344                                        uint64_t FinalAddress,
345                                        uint64_t Value,
346                                        uint32_t Type,
347                                        int64_t Addend) {
348   switch (Arch) {
349   case Triple::x86_64:
350     resolveX86_64Relocation(LocalAddress, FinalAddress, Value, Type, Addend);
351     break;
352   case Triple::x86:
353     resolveX86Relocation(LocalAddress, (uint32_t)(FinalAddress & 0xffffffffL),
354                          (uint32_t)(Value & 0xffffffffL), Type,
355                          (uint32_t)(Addend & 0xffffffffL));
356     break;
357   case Triple::arm:    // Fall through.
358   case Triple::thumb:
359     resolveARMRelocation(LocalAddress, (uint32_t)(FinalAddress & 0xffffffffL),
360                          (uint32_t)(Value & 0xffffffffL), Type,
361                          (uint32_t)(Addend & 0xffffffffL));
362     break;
363   case Triple::mips:    // Fall through.
364   case Triple::mipsel:
365     resolveMIPSRelocation(LocalAddress, (uint32_t)(FinalAddress & 0xffffffffL),
366                           (uint32_t)(Value & 0xffffffffL), Type,
367                           (uint32_t)(Addend & 0xffffffffL));
368     break;
369   default: llvm_unreachable("Unsupported CPU type!");
370   }
371 }
372
373 void RuntimeDyldELF::processRelocationRef(const ObjRelocationInfo &Rel,
374                                           ObjectImage &Obj,
375                                           ObjSectionToIDMap &ObjSectionToID,
376                                           const SymbolTableMap &Symbols,
377                                           StubMap &Stubs) {
378
379   uint32_t RelType = (uint32_t)(Rel.Type & 0xffffffffL);
380   intptr_t Addend = (intptr_t)Rel.AdditionalInfo;
381   const SymbolRef &Symbol = Rel.Symbol;
382
383   // Obtain the symbol name which is referenced in the relocation
384   StringRef TargetName;
385   Symbol.getName(TargetName);
386   DEBUG(dbgs() << "\t\tRelType: " << RelType
387                << " Addend: " << Addend
388                << " TargetName: " << TargetName
389                << "\n");
390   RelocationValueRef Value;
391   // First search for the symbol in the local symbol table
392   SymbolTableMap::const_iterator lsi = Symbols.find(TargetName.data());
393   if (lsi != Symbols.end()) {
394     Value.SectionID = lsi->second.first;
395     Value.Addend = lsi->second.second;
396   } else {
397     // Search for the symbol in the global symbol table
398     SymbolTableMap::const_iterator gsi =
399         GlobalSymbolTable.find(TargetName.data());
400     if (gsi != GlobalSymbolTable.end()) {
401       Value.SectionID = gsi->second.first;
402       Value.Addend = gsi->second.second;
403     } else {
404       SymbolRef::Type SymType;
405       Symbol.getType(SymType);
406       switch (SymType) {
407         case SymbolRef::ST_Debug: {
408           // TODO: Now ELF SymbolRef::ST_Debug = STT_SECTION, it's not obviously
409           // and can be changed by another developers. Maybe best way is add
410           // a new symbol type ST_Section to SymbolRef and use it.
411           section_iterator si(Obj.end_sections());
412           Symbol.getSection(si);
413           if (si == Obj.end_sections())
414             llvm_unreachable("Symbol section not found, bad object file format!");
415           DEBUG(dbgs() << "\t\tThis is section symbol\n");
416           // Default to 'true' in case isText fails (though it never does).
417           bool isCode = true;
418           si->isText(isCode);
419           Value.SectionID = findOrEmitSection(Obj, 
420                                               (*si), 
421                                               isCode, 
422                                               ObjSectionToID);
423           Value.Addend = Addend;
424           break;
425         }
426         case SymbolRef::ST_Unknown: {
427           Value.SymbolName = TargetName.data();
428           Value.Addend = Addend;
429           break;
430         }
431         default:
432           llvm_unreachable("Unresolved symbol type!");
433           break;
434       }
435     }
436   }
437   DEBUG(dbgs() << "\t\tRel.SectionID: " << Rel.SectionID
438                << " Rel.Offset: " << Rel.Offset
439                << "\n");
440   if (Arch == Triple::arm &&
441       (RelType == ELF::R_ARM_PC24 ||
442        RelType == ELF::R_ARM_CALL ||
443        RelType == ELF::R_ARM_JUMP24)) {
444     // This is an ARM branch relocation, need to use a stub function.
445     DEBUG(dbgs() << "\t\tThis is an ARM branch relocation.");
446     SectionEntry &Section = Sections[Rel.SectionID];
447     uint8_t *Target = Section.Address + Rel.Offset;
448
449     // Look for an existing stub.
450     StubMap::const_iterator i = Stubs.find(Value);
451     if (i != Stubs.end()) {
452       resolveRelocation(Target, (uint64_t)Target, (uint64_t)Section.Address +
453                         i->second, RelType, 0);
454       DEBUG(dbgs() << " Stub function found\n");
455     } else {
456       // Create a new stub function.
457       DEBUG(dbgs() << " Create a new stub function\n");
458       Stubs[Value] = Section.StubOffset;
459       uint8_t *StubTargetAddr = createStubFunction(Section.Address +
460                                                    Section.StubOffset);
461       RelocationEntry RE(Rel.SectionID, StubTargetAddr - Section.Address,
462                          ELF::R_ARM_ABS32, Value.Addend);
463       if (Value.SymbolName)
464         addRelocationForSymbol(RE, Value.SymbolName);
465       else
466         addRelocationForSection(RE, Value.SectionID);
467
468       resolveRelocation(Target, (uint64_t)Target, (uint64_t)Section.Address +
469                         Section.StubOffset, RelType, 0);
470       Section.StubOffset += getMaxStubSize();
471     }
472   } else if (Arch == Triple::mipsel && RelType == ELF::R_MIPS_26) {
473     // This is an Mips branch relocation, need to use a stub function.
474     DEBUG(dbgs() << "\t\tThis is a Mips branch relocation.");
475     SectionEntry &Section = Sections[Rel.SectionID];
476     uint8_t *Target = Section.Address + Rel.Offset;
477     uint32_t *TargetAddress = (uint32_t *)Target;
478
479     // Extract the addend from the instruction.
480     uint32_t Addend = ((*TargetAddress) & 0x03ffffff) << 2;
481
482     Value.Addend += Addend;
483
484     //  Look up for existing stub.
485     StubMap::const_iterator i = Stubs.find(Value);
486     if (i != Stubs.end()) {
487       resolveRelocation(Target, (uint64_t)Target,
488                         (uint64_t)Section.Address +
489                         i->second, RelType, 0);
490       DEBUG(dbgs() << " Stub function found\n");
491     } else {
492       // Create a new stub function.
493       DEBUG(dbgs() << " Create a new stub function\n");
494       Stubs[Value] = Section.StubOffset;
495       uint8_t *StubTargetAddr = createStubFunction(Section.Address +
496                                                    Section.StubOffset);
497
498       // Creating Hi and Lo relocations for the filled stub instructions.
499       RelocationEntry REHi(Rel.SectionID,
500                            StubTargetAddr - Section.Address,
501                            ELF::R_MIPS_HI16, Value.Addend);
502       RelocationEntry RELo(Rel.SectionID,
503                            StubTargetAddr - Section.Address + 4,
504                            ELF::R_MIPS_LO16, Value.Addend);
505
506       if (Value.SymbolName) {
507         addRelocationForSymbol(REHi, Value.SymbolName);
508         addRelocationForSymbol(RELo, Value.SymbolName);
509       } else {
510         addRelocationForSection(REHi, Value.SectionID);
511         addRelocationForSection(RELo, Value.SectionID);
512       }
513
514       resolveRelocation(Target, (uint64_t)Target,
515                         (uint64_t)Section.Address +
516                         Section.StubOffset, RelType, 0);
517       Section.StubOffset += getMaxStubSize();
518     }
519   } else {
520     RelocationEntry RE(Rel.SectionID, Rel.Offset, RelType, Value.Addend);
521     if (Value.SymbolName)
522       addRelocationForSymbol(RE, Value.SymbolName);
523     else
524       addRelocationForSection(RE, Value.SectionID);
525   }
526 }
527
528 bool RuntimeDyldELF::isCompatibleFormat(const ObjectBuffer *Buffer) const {
529   if (Buffer->getBufferSize() < strlen(ELF::ElfMagic))
530     return false;
531   return (memcmp(Buffer->getBufferStart(), ELF::ElfMagic, strlen(ELF::ElfMagic))) == 0;
532 }
533 } // namespace llvm