xref: /llvm-project/llvm/lib/Object/MachOObjectFile.cpp (revision 86d8bd1da5eb34b922ff6d1d615bfbabd5d0f188)
1 //===- MachOObjectFile.cpp - Mach-O object file binding ---------*- 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 defines the MachOObjectFile class, which binds the MachOObject
11 // class to the generic ObjectFile wrapper.
12 //
13 //===----------------------------------------------------------------------===//
14 
15 #include "llvm/Object/MachO.h"
16 #include "llvm/ADT/STLExtras.h"
17 #include "llvm/ADT/StringSwitch.h"
18 #include "llvm/ADT/Triple.h"
19 #include "llvm/Support/DataExtractor.h"
20 #include "llvm/Support/Debug.h"
21 #include "llvm/Support/Format.h"
22 #include "llvm/Support/Host.h"
23 #include "llvm/Support/LEB128.h"
24 #include "llvm/Support/MachO.h"
25 #include "llvm/Support/MemoryBuffer.h"
26 #include "llvm/Support/raw_ostream.h"
27 #include <cctype>
28 #include <cstring>
29 #include <limits>
30 #include <list>
31 
32 using namespace llvm;
33 using namespace object;
34 
35 namespace {
36   struct section_base {
37     char sectname[16];
38     char segname[16];
39   };
40 }
41 
42 static Error
43 malformedError(Twine Msg) {
44   std::string StringMsg = "truncated or malformed object (" + Msg.str() + ")";
45   return make_error<GenericBinaryError>(std::move(StringMsg),
46                                         object_error::parse_failed);
47 }
48 
49 // FIXME: Replace all uses of this function with getStructOrErr.
50 template <typename T>
51 static T getStruct(const MachOObjectFile &O, const char *P) {
52   // Don't read before the beginning or past the end of the file
53   if (P < O.getData().begin() || P + sizeof(T) > O.getData().end())
54     report_fatal_error("Malformed MachO file.");
55 
56   T Cmd;
57   memcpy(&Cmd, P, sizeof(T));
58   if (O.isLittleEndian() != sys::IsLittleEndianHost)
59     MachO::swapStruct(Cmd);
60   return Cmd;
61 }
62 
63 template <typename T>
64 static Expected<T> getStructOrErr(const MachOObjectFile &O, const char *P) {
65   // Don't read before the beginning or past the end of the file
66   if (P < O.getData().begin() || P + sizeof(T) > O.getData().end())
67     return malformedError("Structure read out-of-range");
68 
69   T Cmd;
70   memcpy(&Cmd, P, sizeof(T));
71   if (O.isLittleEndian() != sys::IsLittleEndianHost)
72     MachO::swapStruct(Cmd);
73   return Cmd;
74 }
75 
76 static const char *
77 getSectionPtr(const MachOObjectFile &O, MachOObjectFile::LoadCommandInfo L,
78               unsigned Sec) {
79   uintptr_t CommandAddr = reinterpret_cast<uintptr_t>(L.Ptr);
80 
81   bool Is64 = O.is64Bit();
82   unsigned SegmentLoadSize = Is64 ? sizeof(MachO::segment_command_64) :
83                                     sizeof(MachO::segment_command);
84   unsigned SectionSize = Is64 ? sizeof(MachO::section_64) :
85                                 sizeof(MachO::section);
86 
87   uintptr_t SectionAddr = CommandAddr + SegmentLoadSize + Sec * SectionSize;
88   return reinterpret_cast<const char*>(SectionAddr);
89 }
90 
91 static const char *getPtr(const MachOObjectFile &O, size_t Offset) {
92   return O.getData().substr(Offset, 1).data();
93 }
94 
95 static MachO::nlist_base
96 getSymbolTableEntryBase(const MachOObjectFile &O, DataRefImpl DRI) {
97   const char *P = reinterpret_cast<const char *>(DRI.p);
98   return getStruct<MachO::nlist_base>(O, P);
99 }
100 
101 static StringRef parseSegmentOrSectionName(const char *P) {
102   if (P[15] == 0)
103     // Null terminated.
104     return P;
105   // Not null terminated, so this is a 16 char string.
106   return StringRef(P, 16);
107 }
108 
109 // Helper to advance a section or symbol iterator multiple increments at a time.
110 template<class T>
111 static void advance(T &it, size_t Val) {
112   while (Val--)
113     ++it;
114 }
115 
116 static unsigned getCPUType(const MachOObjectFile &O) {
117   return O.getHeader().cputype;
118 }
119 
120 static uint32_t
121 getPlainRelocationAddress(const MachO::any_relocation_info &RE) {
122   return RE.r_word0;
123 }
124 
125 static unsigned
126 getScatteredRelocationAddress(const MachO::any_relocation_info &RE) {
127   return RE.r_word0 & 0xffffff;
128 }
129 
130 static bool getPlainRelocationPCRel(const MachOObjectFile &O,
131                                     const MachO::any_relocation_info &RE) {
132   if (O.isLittleEndian())
133     return (RE.r_word1 >> 24) & 1;
134   return (RE.r_word1 >> 7) & 1;
135 }
136 
137 static bool
138 getScatteredRelocationPCRel(const MachO::any_relocation_info &RE) {
139   return (RE.r_word0 >> 30) & 1;
140 }
141 
142 static unsigned getPlainRelocationLength(const MachOObjectFile &O,
143                                          const MachO::any_relocation_info &RE) {
144   if (O.isLittleEndian())
145     return (RE.r_word1 >> 25) & 3;
146   return (RE.r_word1 >> 5) & 3;
147 }
148 
149 static unsigned
150 getScatteredRelocationLength(const MachO::any_relocation_info &RE) {
151   return (RE.r_word0 >> 28) & 3;
152 }
153 
154 static unsigned getPlainRelocationType(const MachOObjectFile &O,
155                                        const MachO::any_relocation_info &RE) {
156   if (O.isLittleEndian())
157     return RE.r_word1 >> 28;
158   return RE.r_word1 & 0xf;
159 }
160 
161 static uint32_t getSectionFlags(const MachOObjectFile &O,
162                                 DataRefImpl Sec) {
163   if (O.is64Bit()) {
164     MachO::section_64 Sect = O.getSection64(Sec);
165     return Sect.flags;
166   }
167   MachO::section Sect = O.getSection(Sec);
168   return Sect.flags;
169 }
170 
171 static Expected<MachOObjectFile::LoadCommandInfo>
172 getLoadCommandInfo(const MachOObjectFile &Obj, const char *Ptr,
173                    uint32_t LoadCommandIndex) {
174   if (auto CmdOrErr = getStructOrErr<MachO::load_command>(Obj, Ptr)) {
175     if (CmdOrErr->cmdsize < 8)
176       return malformedError("load command " + Twine(LoadCommandIndex) +
177                             " with size less than 8 bytes");
178     return MachOObjectFile::LoadCommandInfo({Ptr, *CmdOrErr});
179   } else
180     return CmdOrErr.takeError();
181 }
182 
183 static Expected<MachOObjectFile::LoadCommandInfo>
184 getFirstLoadCommandInfo(const MachOObjectFile &Obj) {
185   unsigned HeaderSize = Obj.is64Bit() ? sizeof(MachO::mach_header_64)
186                                       : sizeof(MachO::mach_header);
187   if (sizeof(MachO::load_command) > Obj.getHeader().sizeofcmds)
188     return malformedError("load command 0 extends past the end all load "
189                           "commands in the file");
190   return getLoadCommandInfo(Obj, getPtr(Obj, HeaderSize), 0);
191 }
192 
193 static Expected<MachOObjectFile::LoadCommandInfo>
194 getNextLoadCommandInfo(const MachOObjectFile &Obj, uint32_t LoadCommandIndex,
195                        const MachOObjectFile::LoadCommandInfo &L) {
196   unsigned HeaderSize = Obj.is64Bit() ? sizeof(MachO::mach_header_64)
197                                       : sizeof(MachO::mach_header);
198   if (L.Ptr + L.C.cmdsize + sizeof(MachO::load_command) >
199       Obj.getData().data() + HeaderSize + Obj.getHeader().sizeofcmds)
200     return malformedError("load command " + Twine(LoadCommandIndex + 1) +
201                           " extends past the end all load commands in the file");
202   return getLoadCommandInfo(Obj, L.Ptr + L.C.cmdsize, LoadCommandIndex + 1);
203 }
204 
205 template <typename T>
206 static void parseHeader(const MachOObjectFile &Obj, T &Header,
207                         Error &Err) {
208   if (sizeof(T) > Obj.getData().size()) {
209     Err = malformedError("the mach header extends past the end of the "
210                          "file");
211     return;
212   }
213   if (auto HeaderOrErr = getStructOrErr<T>(Obj, getPtr(Obj, 0)))
214     Header = *HeaderOrErr;
215   else
216     Err = HeaderOrErr.takeError();
217 }
218 
219 // This is used to check for overlapping of Mach-O elements.
220 struct MachOElement {
221   uint64_t Offset;
222   uint64_t Size;
223   const char *Name;
224 };
225 
226 static Error checkOverlappingElement(std::list<MachOElement> &Elements,
227                                      uint64_t Offset, uint64_t Size,
228                                      const char *Name) {
229   if (Size == 0)
230     return Error::success();
231 
232   for (auto it=Elements.begin() ; it != Elements.end(); ++it) {
233     auto E = *it;
234     if ((Offset >= E.Offset && Offset < E.Offset + E.Size) ||
235         (Offset + Size > E.Offset && Offset + Size < E.Offset + E.Size) ||
236         (Offset <= E.Offset && Offset + Size >= E.Offset + E.Size))
237       return malformedError(Twine(Name) + " at offset " + Twine(Offset) +
238                             " with a size of " + Twine(Size) + ", overlaps " +
239                             E.Name + " at offset " + Twine(E.Offset) + " with "
240                             "a size of " + Twine(E.Size));
241     auto nt = it;
242     nt++;
243     if (nt != Elements.end()) {
244       auto N = *nt;
245       if (Offset + Size <= N.Offset) {
246         Elements.insert(nt, {Offset, Size, Name});
247         return Error::success();
248       }
249     }
250   }
251   Elements.push_back({Offset, Size, Name});
252   return Error::success();
253 }
254 
255 // Parses LC_SEGMENT or LC_SEGMENT_64 load command, adds addresses of all
256 // sections to \param Sections, and optionally sets
257 // \param IsPageZeroSegment to true.
258 template <typename Segment, typename Section>
259 static Error parseSegmentLoadCommand(
260     const MachOObjectFile &Obj, const MachOObjectFile::LoadCommandInfo &Load,
261     SmallVectorImpl<const char *> &Sections, bool &IsPageZeroSegment,
262     uint32_t LoadCommandIndex, const char *CmdName, uint64_t SizeOfHeaders,
263     std::list<MachOElement> &Elements) {
264   const unsigned SegmentLoadSize = sizeof(Segment);
265   if (Load.C.cmdsize < SegmentLoadSize)
266     return malformedError("load command " + Twine(LoadCommandIndex) +
267                           " " + CmdName + " cmdsize too small");
268   if (auto SegOrErr = getStructOrErr<Segment>(Obj, Load.Ptr)) {
269     Segment S = SegOrErr.get();
270     const unsigned SectionSize = sizeof(Section);
271     uint64_t FileSize = Obj.getData().size();
272     if (S.nsects > std::numeric_limits<uint32_t>::max() / SectionSize ||
273         S.nsects * SectionSize > Load.C.cmdsize - SegmentLoadSize)
274       return malformedError("load command " + Twine(LoadCommandIndex) +
275                             " inconsistent cmdsize in " + CmdName +
276                             " for the number of sections");
277     for (unsigned J = 0; J < S.nsects; ++J) {
278       const char *Sec = getSectionPtr(Obj, Load, J);
279       Sections.push_back(Sec);
280       Section s = getStruct<Section>(Obj, Sec);
281       if (Obj.getHeader().filetype != MachO::MH_DYLIB_STUB &&
282           Obj.getHeader().filetype != MachO::MH_DSYM &&
283           s.flags != MachO::S_ZEROFILL &&
284           s.flags != MachO::S_THREAD_LOCAL_ZEROFILL &&
285           s.offset > FileSize)
286         return malformedError("offset field of section " + Twine(J) + " in " +
287                               CmdName + " command " + Twine(LoadCommandIndex) +
288                               " extends past the end of the file");
289       if (Obj.getHeader().filetype != MachO::MH_DYLIB_STUB &&
290           Obj.getHeader().filetype != MachO::MH_DSYM &&
291           s.flags != MachO::S_ZEROFILL &&
292           s.flags != MachO::S_THREAD_LOCAL_ZEROFILL && S.fileoff == 0 &&
293           s.offset < SizeOfHeaders && s.size != 0)
294         return malformedError("offset field of section " + Twine(J) + " in " +
295                               CmdName + " command " + Twine(LoadCommandIndex) +
296                               " not past the headers of the file");
297       uint64_t BigSize = s.offset;
298       BigSize += s.size;
299       if (Obj.getHeader().filetype != MachO::MH_DYLIB_STUB &&
300           Obj.getHeader().filetype != MachO::MH_DSYM &&
301           s.flags != MachO::S_ZEROFILL &&
302           s.flags != MachO::S_THREAD_LOCAL_ZEROFILL &&
303           BigSize > FileSize)
304         return malformedError("offset field plus size field of section " +
305                               Twine(J) + " in " + CmdName + " command " +
306                               Twine(LoadCommandIndex) +
307                               " extends past the end of the file");
308       if (Obj.getHeader().filetype != MachO::MH_DYLIB_STUB &&
309           Obj.getHeader().filetype != MachO::MH_DSYM &&
310           s.flags != MachO::S_ZEROFILL &&
311           s.flags != MachO::S_THREAD_LOCAL_ZEROFILL &&
312           s.size > S.filesize)
313         return malformedError("size field of section " +
314                               Twine(J) + " in " + CmdName + " command " +
315                               Twine(LoadCommandIndex) +
316                               " greater than the segment");
317       if (Obj.getHeader().filetype != MachO::MH_DYLIB_STUB &&
318           Obj.getHeader().filetype != MachO::MH_DSYM && s.size != 0 &&
319           s.addr < S.vmaddr)
320         return malformedError("addr field of section " + Twine(J) + " in " +
321                               CmdName + " command " + Twine(LoadCommandIndex) +
322                               " less than the segment's vmaddr");
323       BigSize = s.addr;
324       BigSize += s.size;
325       uint64_t BigEnd = S.vmaddr;
326       BigEnd += S.vmsize;
327       if (S.vmsize != 0 && s.size != 0 && BigSize > BigEnd)
328         return malformedError("addr field plus size of section " + Twine(J) +
329                               " in " + CmdName + " command " +
330                               Twine(LoadCommandIndex) +
331                               " greater than than "
332                               "the segment's vmaddr plus vmsize");
333       if (Obj.getHeader().filetype != MachO::MH_DYLIB_STUB &&
334           Obj.getHeader().filetype != MachO::MH_DSYM &&
335           s.flags != MachO::S_ZEROFILL &&
336           s.flags != MachO::S_THREAD_LOCAL_ZEROFILL)
337         if (Error Err = checkOverlappingElement(Elements, s.offset, s.size,
338                                                 "section contents"))
339           return Err;
340       if (s.reloff > FileSize)
341         return malformedError("reloff field of section " + Twine(J) + " in " +
342                               CmdName + " command " + Twine(LoadCommandIndex) +
343                               " extends past the end of the file");
344       BigSize = s.nreloc;
345       BigSize *= sizeof(struct MachO::relocation_info);
346       BigSize += s.reloff;
347       if (BigSize > FileSize)
348         return malformedError("reloff field plus nreloc field times sizeof("
349                               "struct relocation_info) of section " +
350                               Twine(J) + " in " + CmdName + " command " +
351                               Twine(LoadCommandIndex) +
352                               " extends past the end of the file");
353       if (Error Err = checkOverlappingElement(Elements, s.reloff, s.nreloc *
354                                               sizeof(struct
355                                               MachO::relocation_info),
356                                               "section relocation entries"))
357         return Err;
358     }
359     if (S.fileoff > FileSize)
360       return malformedError("load command " + Twine(LoadCommandIndex) +
361                             " fileoff field in " + CmdName +
362                             " extends past the end of the file");
363     uint64_t BigSize = S.fileoff;
364     BigSize += S.filesize;
365     if (BigSize > FileSize)
366       return malformedError("load command " + Twine(LoadCommandIndex) +
367                             " fileoff field plus filesize field in " +
368                             CmdName + " extends past the end of the file");
369     if (S.vmsize != 0 && S.filesize > S.vmsize)
370       return malformedError("load command " + Twine(LoadCommandIndex) +
371                             " filesize field in " + CmdName +
372                             " greater than vmsize field");
373     IsPageZeroSegment |= StringRef("__PAGEZERO").equals(S.segname);
374   } else
375     return SegOrErr.takeError();
376 
377   return Error::success();
378 }
379 
380 static Error checkSymtabCommand(const MachOObjectFile &Obj,
381                                 const MachOObjectFile::LoadCommandInfo &Load,
382                                 uint32_t LoadCommandIndex,
383                                 const char **SymtabLoadCmd,
384                                 std::list<MachOElement> &Elements) {
385   if (Load.C.cmdsize < sizeof(MachO::symtab_command))
386     return malformedError("load command " + Twine(LoadCommandIndex) +
387                           " LC_SYMTAB cmdsize too small");
388   if (*SymtabLoadCmd != nullptr)
389     return malformedError("more than one LC_SYMTAB command");
390   MachO::symtab_command Symtab =
391     getStruct<MachO::symtab_command>(Obj, Load.Ptr);
392   if (Symtab.cmdsize != sizeof(MachO::symtab_command))
393     return malformedError("LC_SYMTAB command " + Twine(LoadCommandIndex) +
394                           " has incorrect cmdsize");
395   uint64_t FileSize = Obj.getData().size();
396   if (Symtab.symoff > FileSize)
397     return malformedError("symoff field of LC_SYMTAB command " +
398                           Twine(LoadCommandIndex) + " extends past the end "
399                           "of the file");
400   uint64_t SymtabSize = Symtab.nsyms;
401   const char *struct_nlist_name;
402   if (Obj.is64Bit()) {
403     SymtabSize *= sizeof(MachO::nlist_64);
404     struct_nlist_name = "struct nlist_64";
405   } else {
406     SymtabSize *= sizeof(MachO::nlist);
407     struct_nlist_name = "struct nlist";
408   }
409   uint64_t BigSize = SymtabSize;
410   BigSize += Symtab.symoff;
411   if (BigSize > FileSize)
412     return malformedError("symoff field plus nsyms field times sizeof(" +
413                           Twine(struct_nlist_name) + ") of LC_SYMTAB command " +
414                           Twine(LoadCommandIndex) + " extends past the end "
415                           "of the file");
416   if (Error Err = checkOverlappingElement(Elements, Symtab.symoff, SymtabSize,
417                                           "symbol table"))
418     return Err;
419   if (Symtab.stroff > FileSize)
420     return malformedError("stroff field of LC_SYMTAB command " +
421                           Twine(LoadCommandIndex) + " extends past the end "
422                           "of the file");
423   BigSize = Symtab.stroff;
424   BigSize += Symtab.strsize;
425   if (BigSize > FileSize)
426     return malformedError("stroff field plus strsize field of LC_SYMTAB "
427                           "command " + Twine(LoadCommandIndex) + " extends "
428                           "past the end of the file");
429   if (Error Err = checkOverlappingElement(Elements, Symtab.stroff,
430                                           Symtab.strsize, "string table"))
431     return Err;
432   *SymtabLoadCmd = Load.Ptr;
433   return Error::success();
434 }
435 
436 static Error checkDysymtabCommand(const MachOObjectFile &Obj,
437                                   const MachOObjectFile::LoadCommandInfo &Load,
438                                   uint32_t LoadCommandIndex,
439                                   const char **DysymtabLoadCmd,
440                                   std::list<MachOElement> &Elements) {
441   if (Load.C.cmdsize < sizeof(MachO::dysymtab_command))
442     return malformedError("load command " + Twine(LoadCommandIndex) +
443                           " LC_DYSYMTAB cmdsize too small");
444   if (*DysymtabLoadCmd != nullptr)
445     return malformedError("more than one LC_DYSYMTAB command");
446   MachO::dysymtab_command Dysymtab =
447     getStruct<MachO::dysymtab_command>(Obj, Load.Ptr);
448   if (Dysymtab.cmdsize != sizeof(MachO::dysymtab_command))
449     return malformedError("LC_DYSYMTAB command " + Twine(LoadCommandIndex) +
450                           " has incorrect cmdsize");
451   uint64_t FileSize = Obj.getData().size();
452   if (Dysymtab.tocoff > FileSize)
453     return malformedError("tocoff field of LC_DYSYMTAB command " +
454                           Twine(LoadCommandIndex) + " extends past the end of "
455                           "the file");
456   uint64_t BigSize = Dysymtab.ntoc;
457   BigSize *= sizeof(MachO::dylib_table_of_contents);
458   BigSize += Dysymtab.tocoff;
459   if (BigSize > FileSize)
460     return malformedError("tocoff field plus ntoc field times sizeof(struct "
461                           "dylib_table_of_contents) of LC_DYSYMTAB command " +
462                           Twine(LoadCommandIndex) + " extends past the end of "
463                           "the file");
464   if (Error Err = checkOverlappingElement(Elements, Dysymtab.tocoff,
465                                           Dysymtab.ntoc * sizeof(struct
466 					  MachO::dylib_table_of_contents),
467 					  "table of contents"))
468     return Err;
469   if (Dysymtab.modtaboff > FileSize)
470     return malformedError("modtaboff field of LC_DYSYMTAB command " +
471                           Twine(LoadCommandIndex) + " extends past the end of "
472                           "the file");
473   BigSize = Dysymtab.nmodtab;
474   const char *struct_dylib_module_name;
475   uint64_t sizeof_modtab;
476   if (Obj.is64Bit()) {
477     sizeof_modtab = sizeof(MachO::dylib_module_64);
478     struct_dylib_module_name = "struct dylib_module_64";
479   } else {
480     sizeof_modtab = sizeof(MachO::dylib_module);
481     struct_dylib_module_name = "struct dylib_module";
482   }
483   BigSize *= sizeof_modtab;
484   BigSize += Dysymtab.modtaboff;
485   if (BigSize > FileSize)
486     return malformedError("modtaboff field plus nmodtab field times sizeof(" +
487                           Twine(struct_dylib_module_name) + ") of LC_DYSYMTAB "
488                           "command " + Twine(LoadCommandIndex) + " extends "
489                           "past the end of the file");
490   if (Error Err = checkOverlappingElement(Elements, Dysymtab.modtaboff,
491                                           Dysymtab.nmodtab * sizeof_modtab,
492 					  "module table"))
493     return Err;
494   if (Dysymtab.extrefsymoff > FileSize)
495     return malformedError("extrefsymoff field of LC_DYSYMTAB command " +
496                           Twine(LoadCommandIndex) + " extends past the end of "
497                           "the file");
498   BigSize = Dysymtab.nextrefsyms;
499   BigSize *= sizeof(MachO::dylib_reference);
500   BigSize += Dysymtab.extrefsymoff;
501   if (BigSize > FileSize)
502     return malformedError("extrefsymoff field plus nextrefsyms field times "
503                           "sizeof(struct dylib_reference) of LC_DYSYMTAB "
504                           "command " + Twine(LoadCommandIndex) + " extends "
505                           "past the end of the file");
506   if (Error Err = checkOverlappingElement(Elements, Dysymtab.extrefsymoff,
507                                           Dysymtab.nextrefsyms *
508                                           sizeof(MachO::dylib_reference),
509 					  "reference table"))
510     return Err;
511   if (Dysymtab.indirectsymoff > FileSize)
512     return malformedError("indirectsymoff field of LC_DYSYMTAB command " +
513                           Twine(LoadCommandIndex) + " extends past the end of "
514                           "the file");
515   BigSize = Dysymtab.nindirectsyms;
516   BigSize *= sizeof(uint32_t);
517   BigSize += Dysymtab.indirectsymoff;
518   if (BigSize > FileSize)
519     return malformedError("indirectsymoff field plus nindirectsyms field times "
520                           "sizeof(uint32_t) of LC_DYSYMTAB command " +
521                           Twine(LoadCommandIndex) + " extends past the end of "
522                           "the file");
523   if (Error Err = checkOverlappingElement(Elements, Dysymtab.indirectsymoff,
524                                           Dysymtab.nindirectsyms *
525                                           sizeof(uint32_t),
526 					  "indirect table"))
527     return Err;
528   if (Dysymtab.extreloff > FileSize)
529     return malformedError("extreloff field of LC_DYSYMTAB command " +
530                           Twine(LoadCommandIndex) + " extends past the end of "
531                           "the file");
532   BigSize = Dysymtab.nextrel;
533   BigSize *= sizeof(MachO::relocation_info);
534   BigSize += Dysymtab.extreloff;
535   if (BigSize > FileSize)
536     return malformedError("extreloff field plus nextrel field times sizeof"
537                           "(struct relocation_info) of LC_DYSYMTAB command " +
538                           Twine(LoadCommandIndex) + " extends past the end of "
539                           "the file");
540   if (Error Err = checkOverlappingElement(Elements, Dysymtab.extreloff,
541                                           Dysymtab.nextrel *
542                                           sizeof(MachO::relocation_info),
543 					  "external relocation table"))
544     return Err;
545   if (Dysymtab.locreloff > FileSize)
546     return malformedError("locreloff field of LC_DYSYMTAB command " +
547                           Twine(LoadCommandIndex) + " extends past the end of "
548                           "the file");
549   BigSize = Dysymtab.nlocrel;
550   BigSize *= sizeof(MachO::relocation_info);
551   BigSize += Dysymtab.locreloff;
552   if (BigSize > FileSize)
553     return malformedError("locreloff field plus nlocrel field times sizeof"
554                           "(struct relocation_info) of LC_DYSYMTAB command " +
555                           Twine(LoadCommandIndex) + " extends past the end of "
556                           "the file");
557   if (Error Err = checkOverlappingElement(Elements, Dysymtab.locreloff,
558                                           Dysymtab.nlocrel *
559                                           sizeof(MachO::relocation_info),
560 					  "local relocation table"))
561     return Err;
562   *DysymtabLoadCmd = Load.Ptr;
563   return Error::success();
564 }
565 
566 static Error checkLinkeditDataCommand(const MachOObjectFile &Obj,
567                                  const MachOObjectFile::LoadCommandInfo &Load,
568                                  uint32_t LoadCommandIndex,
569                                  const char **LoadCmd, const char *CmdName,
570                                  std::list<MachOElement> &Elements,
571                                  const char *ElementName) {
572   if (Load.C.cmdsize < sizeof(MachO::linkedit_data_command))
573     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
574                           CmdName + " cmdsize too small");
575   if (*LoadCmd != nullptr)
576     return malformedError("more than one " + Twine(CmdName) + " command");
577   MachO::linkedit_data_command LinkData =
578     getStruct<MachO::linkedit_data_command>(Obj, Load.Ptr);
579   if (LinkData.cmdsize != sizeof(MachO::linkedit_data_command))
580     return malformedError(Twine(CmdName) + " command " +
581                           Twine(LoadCommandIndex) + " has incorrect cmdsize");
582   uint64_t FileSize = Obj.getData().size();
583   if (LinkData.dataoff > FileSize)
584     return malformedError("dataoff field of " + Twine(CmdName) + " command " +
585                           Twine(LoadCommandIndex) + " extends past the end of "
586                           "the file");
587   uint64_t BigSize = LinkData.dataoff;
588   BigSize += LinkData.datasize;
589   if (BigSize > FileSize)
590     return malformedError("dataoff field plus datasize field of " +
591                           Twine(CmdName) + " command " +
592                           Twine(LoadCommandIndex) + " extends past the end of "
593                           "the file");
594   if (Error Err = checkOverlappingElement(Elements, LinkData.dataoff,
595                                           LinkData.datasize, ElementName))
596     return Err;
597   *LoadCmd = Load.Ptr;
598   return Error::success();
599 }
600 
601 static Error checkDyldInfoCommand(const MachOObjectFile &Obj,
602                                   const MachOObjectFile::LoadCommandInfo &Load,
603                                   uint32_t LoadCommandIndex,
604                                   const char **LoadCmd, const char *CmdName,
605                                   std::list<MachOElement> &Elements) {
606   if (Load.C.cmdsize < sizeof(MachO::dyld_info_command))
607     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
608                           CmdName + " cmdsize too small");
609   if (*LoadCmd != nullptr)
610     return malformedError("more than one LC_DYLD_INFO and or LC_DYLD_INFO_ONLY "
611                           "command");
612   MachO::dyld_info_command DyldInfo =
613     getStruct<MachO::dyld_info_command>(Obj, Load.Ptr);
614   if (DyldInfo.cmdsize != sizeof(MachO::dyld_info_command))
615     return malformedError(Twine(CmdName) + " command " +
616                           Twine(LoadCommandIndex) + " has incorrect cmdsize");
617   uint64_t FileSize = Obj.getData().size();
618   if (DyldInfo.rebase_off > FileSize)
619     return malformedError("rebase_off field of " + Twine(CmdName) +
620                           " command " + Twine(LoadCommandIndex) + " extends "
621                           "past the end of the file");
622   uint64_t BigSize = DyldInfo.rebase_off;
623   BigSize += DyldInfo.rebase_size;
624   if (BigSize > FileSize)
625     return malformedError("rebase_off field plus rebase_size field of " +
626                           Twine(CmdName) + " command " +
627                           Twine(LoadCommandIndex) + " extends past the end of "
628                           "the file");
629   if (Error Err = checkOverlappingElement(Elements, DyldInfo.rebase_off,
630                                           DyldInfo.rebase_size,
631                                           "dyld rebase info"))
632     return Err;
633   if (DyldInfo.bind_off > FileSize)
634     return malformedError("bind_off field of " + Twine(CmdName) +
635                           " command " + Twine(LoadCommandIndex) + " extends "
636                           "past the end of the file");
637   BigSize = DyldInfo.bind_off;
638   BigSize += DyldInfo.bind_size;
639   if (BigSize > FileSize)
640     return malformedError("bind_off field plus bind_size field of " +
641                           Twine(CmdName) + " command " +
642                           Twine(LoadCommandIndex) + " extends past the end of "
643                           "the file");
644   if (Error Err = checkOverlappingElement(Elements, DyldInfo.bind_off,
645                                           DyldInfo.bind_size,
646                                           "dyld bind info"))
647     return Err;
648   if (DyldInfo.weak_bind_off > FileSize)
649     return malformedError("weak_bind_off field of " + Twine(CmdName) +
650                           " command " + Twine(LoadCommandIndex) + " extends "
651                           "past the end of the file");
652   BigSize = DyldInfo.weak_bind_off;
653   BigSize += DyldInfo.weak_bind_size;
654   if (BigSize > FileSize)
655     return malformedError("weak_bind_off field plus weak_bind_size field of " +
656                           Twine(CmdName) + " command " +
657                           Twine(LoadCommandIndex) + " extends past the end of "
658                           "the file");
659   if (Error Err = checkOverlappingElement(Elements, DyldInfo.weak_bind_off,
660                                           DyldInfo.weak_bind_size,
661                                           "dyld weak bind info"))
662     return Err;
663   if (DyldInfo.lazy_bind_off > FileSize)
664     return malformedError("lazy_bind_off field of " + Twine(CmdName) +
665                           " command " + Twine(LoadCommandIndex) + " extends "
666                           "past the end of the file");
667   BigSize = DyldInfo.lazy_bind_off;
668   BigSize += DyldInfo.lazy_bind_size;
669   if (BigSize > FileSize)
670     return malformedError("lazy_bind_off field plus lazy_bind_size field of " +
671                           Twine(CmdName) + " command " +
672                           Twine(LoadCommandIndex) + " extends past the end of "
673                           "the file");
674   if (Error Err = checkOverlappingElement(Elements, DyldInfo.lazy_bind_off,
675                                           DyldInfo.lazy_bind_size,
676                                           "dyld lazy bind info"))
677     return Err;
678   if (DyldInfo.export_off > FileSize)
679     return malformedError("export_off field of " + Twine(CmdName) +
680                           " command " + Twine(LoadCommandIndex) + " extends "
681                           "past the end of the file");
682   BigSize = DyldInfo.export_off;
683   BigSize += DyldInfo.export_size;
684   if (BigSize > FileSize)
685     return malformedError("export_off field plus export_size field of " +
686                           Twine(CmdName) + " command " +
687                           Twine(LoadCommandIndex) + " extends past the end of "
688                           "the file");
689   if (Error Err = checkOverlappingElement(Elements, DyldInfo.export_off,
690                                           DyldInfo.export_size,
691                                           "dyld export info"))
692     return Err;
693   *LoadCmd = Load.Ptr;
694   return Error::success();
695 }
696 
697 static Error checkDylibCommand(const MachOObjectFile &Obj,
698                                const MachOObjectFile::LoadCommandInfo &Load,
699                                uint32_t LoadCommandIndex, const char *CmdName) {
700   if (Load.C.cmdsize < sizeof(MachO::dylib_command))
701     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
702                           CmdName + " cmdsize too small");
703   MachO::dylib_command D = getStruct<MachO::dylib_command>(Obj, Load.Ptr);
704   if (D.dylib.name < sizeof(MachO::dylib_command))
705     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
706                           CmdName + " name.offset field too small, not past "
707                           "the end of the dylib_command struct");
708   if (D.dylib.name >= D.cmdsize)
709     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
710                           CmdName + " name.offset field extends past the end "
711                           "of the load command");
712   // Make sure there is a null between the starting offset of the name and
713   // the end of the load command.
714   uint32_t i;
715   const char *P = (const char *)Load.Ptr;
716   for (i = D.dylib.name; i < D.cmdsize; i++)
717     if (P[i] == '\0')
718       break;
719   if (i >= D.cmdsize)
720     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
721                           CmdName + " library name extends past the end of the "
722                           "load command");
723   return Error::success();
724 }
725 
726 static Error checkDylibIdCommand(const MachOObjectFile &Obj,
727                                  const MachOObjectFile::LoadCommandInfo &Load,
728                                  uint32_t LoadCommandIndex,
729                                  const char **LoadCmd) {
730   if (Error Err = checkDylibCommand(Obj, Load, LoadCommandIndex,
731                                      "LC_ID_DYLIB"))
732     return Err;
733   if (*LoadCmd != nullptr)
734     return malformedError("more than one LC_ID_DYLIB command");
735   if (Obj.getHeader().filetype != MachO::MH_DYLIB &&
736       Obj.getHeader().filetype != MachO::MH_DYLIB_STUB)
737     return malformedError("LC_ID_DYLIB load command in non-dynamic library "
738                           "file type");
739   *LoadCmd = Load.Ptr;
740   return Error::success();
741 }
742 
743 static Error checkDyldCommand(const MachOObjectFile &Obj,
744                               const MachOObjectFile::LoadCommandInfo &Load,
745                               uint32_t LoadCommandIndex, const char *CmdName) {
746   if (Load.C.cmdsize < sizeof(MachO::dylinker_command))
747     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
748                           CmdName + " cmdsize too small");
749   MachO::dylinker_command D = getStruct<MachO::dylinker_command>(Obj, Load.Ptr);
750   if (D.name < sizeof(MachO::dylinker_command))
751     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
752                           CmdName + " name.offset field too small, not past "
753                           "the end of the dylinker_command struct");
754   if (D.name >= D.cmdsize)
755     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
756                           CmdName + " name.offset field extends past the end "
757                           "of the load command");
758   // Make sure there is a null between the starting offset of the name and
759   // the end of the load command.
760   uint32_t i;
761   const char *P = (const char *)Load.Ptr;
762   for (i = D.name; i < D.cmdsize; i++)
763     if (P[i] == '\0')
764       break;
765   if (i >= D.cmdsize)
766     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
767                           CmdName + " dyld name extends past the end of the "
768                           "load command");
769   return Error::success();
770 }
771 
772 static Error checkVersCommand(const MachOObjectFile &Obj,
773                               const MachOObjectFile::LoadCommandInfo &Load,
774                               uint32_t LoadCommandIndex,
775                               const char **LoadCmd, const char *CmdName) {
776   if (Load.C.cmdsize != sizeof(MachO::version_min_command))
777     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
778                           CmdName + " has incorrect cmdsize");
779   if (*LoadCmd != nullptr)
780     return malformedError("more than one LC_VERSION_MIN_MACOSX, "
781                           "LC_VERSION_MIN_IPHONEOS, LC_VERSION_MIN_TVOS or "
782                           "LC_VERSION_MIN_WATCHOS command");
783   *LoadCmd = Load.Ptr;
784   return Error::success();
785 }
786 
787 static Error checkNoteCommand(const MachOObjectFile &Obj,
788                               const MachOObjectFile::LoadCommandInfo &Load,
789                               uint32_t LoadCommandIndex,
790                               std::list<MachOElement> &Elements) {
791   if (Load.C.cmdsize != sizeof(MachO::note_command))
792     return malformedError("load command " + Twine(LoadCommandIndex) +
793                           " LC_NOTE has incorrect cmdsize");
794   MachO::note_command Nt = getStruct<MachO::note_command>(Obj, Load.Ptr);
795   uint64_t FileSize = Obj.getData().size();
796   if (Nt.offset > FileSize)
797     return malformedError("offset field of LC_NOTE command " +
798                           Twine(LoadCommandIndex) + " extends "
799                           "past the end of the file");
800   uint64_t BigSize = Nt.offset;
801   BigSize += Nt.size;
802   if (BigSize > FileSize)
803     return malformedError("size field plus offset field of LC_NOTE command " +
804                           Twine(LoadCommandIndex) + " extends past the end of "
805                           "the file");
806   if (Error Err = checkOverlappingElement(Elements, Nt.offset, Nt.size,
807                                           "LC_NOTE data"))
808     return Err;
809   return Error::success();
810 }
811 
812 static Error
813 parseBuildVersionCommand(const MachOObjectFile &Obj,
814                          const MachOObjectFile::LoadCommandInfo &Load,
815                          SmallVectorImpl<const char*> &BuildTools,
816                          uint32_t LoadCommandIndex) {
817   MachO::build_version_command BVC =
818       getStruct<MachO::build_version_command>(Obj, Load.Ptr);
819   if (Load.C.cmdsize !=
820       sizeof(MachO::build_version_command) +
821           BVC.ntools * sizeof(MachO::build_tool_version))
822     return malformedError("load command " + Twine(LoadCommandIndex) +
823                           " LC_BUILD_VERSION_COMMAND has incorrect cmdsize");
824 
825   auto Start = Load.Ptr + sizeof(MachO::build_version_command);
826   BuildTools.resize(BVC.ntools);
827   for (unsigned i = 0; i < BVC.ntools; ++i)
828     BuildTools[i] = Start + i * sizeof(MachO::build_tool_version);
829 
830   return Error::success();
831 }
832 
833 static Error checkRpathCommand(const MachOObjectFile &Obj,
834                                const MachOObjectFile::LoadCommandInfo &Load,
835                                uint32_t LoadCommandIndex) {
836   if (Load.C.cmdsize < sizeof(MachO::rpath_command))
837     return malformedError("load command " + Twine(LoadCommandIndex) +
838                           " LC_RPATH cmdsize too small");
839   MachO::rpath_command R = getStruct<MachO::rpath_command>(Obj, Load.Ptr);
840   if (R.path < sizeof(MachO::rpath_command))
841     return malformedError("load command " + Twine(LoadCommandIndex) +
842                           " LC_RPATH path.offset field too small, not past "
843                           "the end of the rpath_command struct");
844   if (R.path >= R.cmdsize)
845     return malformedError("load command " + Twine(LoadCommandIndex) +
846                           " LC_RPATH path.offset field extends past the end "
847                           "of the load command");
848   // Make sure there is a null between the starting offset of the path and
849   // the end of the load command.
850   uint32_t i;
851   const char *P = (const char *)Load.Ptr;
852   for (i = R.path; i < R.cmdsize; i++)
853     if (P[i] == '\0')
854       break;
855   if (i >= R.cmdsize)
856     return malformedError("load command " + Twine(LoadCommandIndex) +
857                           " LC_RPATH library name extends past the end of the "
858                           "load command");
859   return Error::success();
860 }
861 
862 static Error checkEncryptCommand(const MachOObjectFile &Obj,
863                                  const MachOObjectFile::LoadCommandInfo &Load,
864                                  uint32_t LoadCommandIndex,
865                                  uint64_t cryptoff, uint64_t cryptsize,
866                                  const char **LoadCmd, const char *CmdName) {
867   if (*LoadCmd != nullptr)
868     return malformedError("more than one LC_ENCRYPTION_INFO and or "
869                           "LC_ENCRYPTION_INFO_64 command");
870   uint64_t FileSize = Obj.getData().size();
871   if (cryptoff > FileSize)
872     return malformedError("cryptoff field of " + Twine(CmdName) +
873                           " command " + Twine(LoadCommandIndex) + " extends "
874                           "past the end of the file");
875   uint64_t BigSize = cryptoff;
876   BigSize += cryptsize;
877   if (BigSize > FileSize)
878     return malformedError("cryptoff field plus cryptsize field of " +
879                           Twine(CmdName) + " command " +
880                           Twine(LoadCommandIndex) + " extends past the end of "
881                           "the file");
882   *LoadCmd = Load.Ptr;
883   return Error::success();
884 }
885 
886 static Error checkLinkerOptCommand(const MachOObjectFile &Obj,
887                                    const MachOObjectFile::LoadCommandInfo &Load,
888                                    uint32_t LoadCommandIndex) {
889   if (Load.C.cmdsize < sizeof(MachO::linker_option_command))
890     return malformedError("load command " + Twine(LoadCommandIndex) +
891                           " LC_LINKER_OPTION cmdsize too small");
892   MachO::linker_option_command L =
893     getStruct<MachO::linker_option_command>(Obj, Load.Ptr);
894   // Make sure the count of strings is correct.
895   const char *string = (const char *)Load.Ptr +
896                        sizeof(struct MachO::linker_option_command);
897   uint32_t left = L.cmdsize - sizeof(struct MachO::linker_option_command);
898   uint32_t i = 0;
899   while (left > 0) {
900     while (*string == '\0' && left > 0) {
901       string++;
902       left--;
903     }
904     if (left > 0) {
905       i++;
906       uint32_t NullPos = StringRef(string, left).find('\0');
907       uint32_t len = std::min(NullPos, left) + 1;
908       string += len;
909       left -= len;
910     }
911   }
912   if (L.count != i)
913     return malformedError("load command " + Twine(LoadCommandIndex) +
914                           " LC_LINKER_OPTION string count " + Twine(L.count) +
915                           " does not match number of strings");
916   return Error::success();
917 }
918 
919 static Error checkSubCommand(const MachOObjectFile &Obj,
920                              const MachOObjectFile::LoadCommandInfo &Load,
921                              uint32_t LoadCommandIndex, const char *CmdName,
922                              size_t SizeOfCmd, const char *CmdStructName,
923                              uint32_t PathOffset, const char *PathFieldName) {
924   if (PathOffset < SizeOfCmd)
925     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
926                           CmdName + " " + PathFieldName + ".offset field too "
927                           "small, not past the end of the " + CmdStructName);
928   if (PathOffset >= Load.C.cmdsize)
929     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
930                           CmdName + " " + PathFieldName + ".offset field "
931                           "extends past the end of the load command");
932   // Make sure there is a null between the starting offset of the path and
933   // the end of the load command.
934   uint32_t i;
935   const char *P = (const char *)Load.Ptr;
936   for (i = PathOffset; i < Load.C.cmdsize; i++)
937     if (P[i] == '\0')
938       break;
939   if (i >= Load.C.cmdsize)
940     return malformedError("load command " + Twine(LoadCommandIndex) + " " +
941                           CmdName + " " + PathFieldName + " name extends past "
942                           "the end of the load command");
943   return Error::success();
944 }
945 
946 static Error checkThreadCommand(const MachOObjectFile &Obj,
947                                 const MachOObjectFile::LoadCommandInfo &Load,
948                                 uint32_t LoadCommandIndex,
949                                 const char *CmdName) {
950   if (Load.C.cmdsize < sizeof(MachO::thread_command))
951     return malformedError("load command " + Twine(LoadCommandIndex) +
952                           CmdName + " cmdsize too small");
953   MachO::thread_command T =
954     getStruct<MachO::thread_command>(Obj, Load.Ptr);
955   const char *state = Load.Ptr + sizeof(MachO::thread_command);
956   const char *end = Load.Ptr + T.cmdsize;
957   uint32_t nflavor = 0;
958   uint32_t cputype = getCPUType(Obj);
959   while (state < end) {
960     if(state + sizeof(uint32_t) > end)
961       return malformedError("load command " + Twine(LoadCommandIndex) +
962                             "flavor in " + CmdName + " extends past end of "
963                             "command");
964     uint32_t flavor;
965     memcpy(&flavor, state, sizeof(uint32_t));
966     if (Obj.isLittleEndian() != sys::IsLittleEndianHost)
967       sys::swapByteOrder(flavor);
968     state += sizeof(uint32_t);
969 
970     if(state + sizeof(uint32_t) > end)
971       return malformedError("load command " + Twine(LoadCommandIndex) +
972                             " count in " + CmdName + " extends past end of "
973                             "command");
974     uint32_t count;
975     memcpy(&count, state, sizeof(uint32_t));
976     if (Obj.isLittleEndian() != sys::IsLittleEndianHost)
977       sys::swapByteOrder(count);
978     state += sizeof(uint32_t);
979 
980     if (cputype == MachO::CPU_TYPE_I386) {
981       if (flavor == MachO::x86_THREAD_STATE32) {
982         if (count != MachO::x86_THREAD_STATE32_COUNT)
983           return malformedError("load command " + Twine(LoadCommandIndex) +
984                                 " count not x86_THREAD_STATE32_COUNT for "
985                                 "flavor number " + Twine(nflavor) + " which is "
986                                 "a x86_THREAD_STATE32 flavor in " + CmdName +
987                                 " command");
988         if (state + sizeof(MachO::x86_thread_state32_t) > end)
989           return malformedError("load command " + Twine(LoadCommandIndex) +
990                                 " x86_THREAD_STATE32 extends past end of "
991                                 "command in " + CmdName + " command");
992         state += sizeof(MachO::x86_thread_state32_t);
993       } else {
994         return malformedError("load command " + Twine(LoadCommandIndex) +
995                               " unknown flavor (" + Twine(flavor) + ") for "
996                               "flavor number " + Twine(nflavor) + " in " +
997                               CmdName + " command");
998       }
999     } else if (cputype == MachO::CPU_TYPE_X86_64) {
1000       if (flavor == MachO::x86_THREAD_STATE64) {
1001         if (count != MachO::x86_THREAD_STATE64_COUNT)
1002           return malformedError("load command " + Twine(LoadCommandIndex) +
1003                                 " count not x86_THREAD_STATE64_COUNT for "
1004                                 "flavor number " + Twine(nflavor) + " which is "
1005                                 "a x86_THREAD_STATE64 flavor in " + CmdName +
1006                                 " command");
1007         if (state + sizeof(MachO::x86_thread_state64_t) > end)
1008           return malformedError("load command " + Twine(LoadCommandIndex) +
1009                                 " x86_THREAD_STATE64 extends past end of "
1010                                 "command in " + CmdName + " command");
1011         state += sizeof(MachO::x86_thread_state64_t);
1012       } else {
1013         return malformedError("load command " + Twine(LoadCommandIndex) +
1014                               " unknown flavor (" + Twine(flavor) + ") for "
1015                               "flavor number " + Twine(nflavor) + " in " +
1016                               CmdName + " command");
1017       }
1018     } else if (cputype == MachO::CPU_TYPE_ARM) {
1019       if (flavor == MachO::ARM_THREAD_STATE) {
1020         if (count != MachO::ARM_THREAD_STATE_COUNT)
1021           return malformedError("load command " + Twine(LoadCommandIndex) +
1022                                 " count not ARM_THREAD_STATE_COUNT for "
1023                                 "flavor number " + Twine(nflavor) + " which is "
1024                                 "a ARM_THREAD_STATE flavor in " + CmdName +
1025                                 " command");
1026         if (state + sizeof(MachO::arm_thread_state32_t) > end)
1027           return malformedError("load command " + Twine(LoadCommandIndex) +
1028                                 " ARM_THREAD_STATE extends past end of "
1029                                 "command in " + CmdName + " command");
1030         state += sizeof(MachO::arm_thread_state32_t);
1031       } else {
1032         return malformedError("load command " + Twine(LoadCommandIndex) +
1033                               " unknown flavor (" + Twine(flavor) + ") for "
1034                               "flavor number " + Twine(nflavor) + " in " +
1035                               CmdName + " command");
1036       }
1037     } else if (cputype == MachO::CPU_TYPE_ARM64) {
1038       if (flavor == MachO::ARM_THREAD_STATE64) {
1039         if (count != MachO::ARM_THREAD_STATE64_COUNT)
1040           return malformedError("load command " + Twine(LoadCommandIndex) +
1041                                 " count not ARM_THREAD_STATE64_COUNT for "
1042                                 "flavor number " + Twine(nflavor) + " which is "
1043                                 "a ARM_THREAD_STATE64 flavor in " + CmdName +
1044                                 " command");
1045         if (state + sizeof(MachO::arm_thread_state64_t) > end)
1046           return malformedError("load command " + Twine(LoadCommandIndex) +
1047                                 " ARM_THREAD_STATE64 extends past end of "
1048                                 "command in " + CmdName + " command");
1049         state += sizeof(MachO::arm_thread_state64_t);
1050       } else {
1051         return malformedError("load command " + Twine(LoadCommandIndex) +
1052                               " unknown flavor (" + Twine(flavor) + ") for "
1053                               "flavor number " + Twine(nflavor) + " in " +
1054                               CmdName + " command");
1055       }
1056     } else if (cputype == MachO::CPU_TYPE_POWERPC) {
1057       if (flavor == MachO::PPC_THREAD_STATE) {
1058         if (count != MachO::PPC_THREAD_STATE_COUNT)
1059           return malformedError("load command " + Twine(LoadCommandIndex) +
1060                                 " count not PPC_THREAD_STATE_COUNT for "
1061                                 "flavor number " + Twine(nflavor) + " which is "
1062                                 "a PPC_THREAD_STATE flavor in " + CmdName +
1063                                 " command");
1064         if (state + sizeof(MachO::ppc_thread_state32_t) > end)
1065           return malformedError("load command " + Twine(LoadCommandIndex) +
1066                                 " PPC_THREAD_STATE extends past end of "
1067                                 "command in " + CmdName + " command");
1068         state += sizeof(MachO::ppc_thread_state32_t);
1069       } else {
1070         return malformedError("load command " + Twine(LoadCommandIndex) +
1071                               " unknown flavor (" + Twine(flavor) + ") for "
1072                               "flavor number " + Twine(nflavor) + " in " +
1073                               CmdName + " command");
1074       }
1075     } else {
1076       return malformedError("unknown cputype (" + Twine(cputype) + ") load "
1077                             "command " + Twine(LoadCommandIndex) + " for " +
1078                             CmdName + " command can't be checked");
1079     }
1080     nflavor++;
1081   }
1082   return Error::success();
1083 }
1084 
1085 static Error checkTwoLevelHintsCommand(const MachOObjectFile &Obj,
1086                                        const MachOObjectFile::LoadCommandInfo
1087                                          &Load,
1088                                        uint32_t LoadCommandIndex,
1089                                        const char **LoadCmd,
1090                                        std::list<MachOElement> &Elements) {
1091   if (Load.C.cmdsize != sizeof(MachO::twolevel_hints_command))
1092     return malformedError("load command " + Twine(LoadCommandIndex) +
1093                           " LC_TWOLEVEL_HINTS has incorrect cmdsize");
1094   if (*LoadCmd != nullptr)
1095     return malformedError("more than one LC_TWOLEVEL_HINTS command");
1096   MachO::twolevel_hints_command Hints =
1097     getStruct<MachO::twolevel_hints_command>(Obj, Load.Ptr);
1098   uint64_t FileSize = Obj.getData().size();
1099   if (Hints.offset > FileSize)
1100     return malformedError("offset field of LC_TWOLEVEL_HINTS command " +
1101                           Twine(LoadCommandIndex) + " extends past the end of "
1102                           "the file");
1103   uint64_t BigSize = Hints.nhints;
1104   BigSize *= Hints.nhints * sizeof(MachO::twolevel_hint);
1105   BigSize += Hints.offset;
1106   if (BigSize > FileSize)
1107     return malformedError("offset field plus nhints times sizeof(struct "
1108                           "twolevel_hint) field of LC_TWOLEVEL_HINTS command " +
1109                           Twine(LoadCommandIndex) + " extends past the end of "
1110                           "the file");
1111   if (Error Err = checkOverlappingElement(Elements, Hints.offset, Hints.nhints *
1112                                           sizeof(MachO::twolevel_hint),
1113                                           "two level hints"))
1114     return Err;
1115   *LoadCmd = Load.Ptr;
1116   return Error::success();
1117 }
1118 
1119 // Returns true if the libObject code does not support the load command and its
1120 // contents.  The cmd value it is treated as an unknown load command but with
1121 // an error message that says the cmd value is obsolete.
1122 static bool isLoadCommandObsolete(uint32_t cmd) {
1123   if (cmd == MachO::LC_SYMSEG ||
1124       cmd == MachO::LC_LOADFVMLIB ||
1125       cmd == MachO::LC_IDFVMLIB ||
1126       cmd == MachO::LC_IDENT ||
1127       cmd == MachO::LC_FVMFILE ||
1128       cmd == MachO::LC_PREPAGE ||
1129       cmd == MachO::LC_PREBOUND_DYLIB ||
1130       cmd == MachO::LC_TWOLEVEL_HINTS ||
1131       cmd == MachO::LC_PREBIND_CKSUM)
1132     return true;
1133   return false;
1134 }
1135 
1136 Expected<std::unique_ptr<MachOObjectFile>>
1137 MachOObjectFile::create(MemoryBufferRef Object, bool IsLittleEndian,
1138                         bool Is64Bits, uint32_t UniversalCputype,
1139                         uint32_t UniversalIndex) {
1140   Error Err = Error::success();
1141   std::unique_ptr<MachOObjectFile> Obj(
1142       new MachOObjectFile(std::move(Object), IsLittleEndian,
1143                           Is64Bits, Err, UniversalCputype,
1144                           UniversalIndex));
1145   if (Err)
1146     return std::move(Err);
1147   return std::move(Obj);
1148 }
1149 
1150 MachOObjectFile::MachOObjectFile(MemoryBufferRef Object, bool IsLittleEndian,
1151                                  bool Is64bits, Error &Err,
1152                                  uint32_t UniversalCputype,
1153                                  uint32_t UniversalIndex)
1154     : ObjectFile(getMachOType(IsLittleEndian, Is64bits), Object),
1155       SymtabLoadCmd(nullptr), DysymtabLoadCmd(nullptr),
1156       DataInCodeLoadCmd(nullptr), LinkOptHintsLoadCmd(nullptr),
1157       DyldInfoLoadCmd(nullptr), UuidLoadCmd(nullptr),
1158       HasPageZeroSegment(false) {
1159   ErrorAsOutParameter ErrAsOutParam(&Err);
1160   uint64_t SizeOfHeaders;
1161   uint32_t cputype;
1162   if (is64Bit()) {
1163     parseHeader(*this, Header64, Err);
1164     SizeOfHeaders = sizeof(MachO::mach_header_64);
1165     cputype = Header64.cputype;
1166   } else {
1167     parseHeader(*this, Header, Err);
1168     SizeOfHeaders = sizeof(MachO::mach_header);
1169     cputype = Header.cputype;
1170   }
1171   if (Err)
1172     return;
1173   SizeOfHeaders += getHeader().sizeofcmds;
1174   if (getData().data() + SizeOfHeaders > getData().end()) {
1175     Err = malformedError("load commands extend past the end of the file");
1176     return;
1177   }
1178   if (UniversalCputype != 0 && cputype != UniversalCputype) {
1179     Err = malformedError("universal header architecture: " +
1180                          Twine(UniversalIndex) + "'s cputype does not match "
1181                          "object file's mach header");
1182     return;
1183   }
1184   std::list<MachOElement> Elements;
1185   Elements.push_back({0, SizeOfHeaders, "Mach-O headers"});
1186 
1187   uint32_t LoadCommandCount = getHeader().ncmds;
1188   LoadCommandInfo Load;
1189   if (LoadCommandCount != 0) {
1190     if (auto LoadOrErr = getFirstLoadCommandInfo(*this))
1191       Load = *LoadOrErr;
1192     else {
1193       Err = LoadOrErr.takeError();
1194       return;
1195     }
1196   }
1197 
1198   const char *DyldIdLoadCmd = nullptr;
1199   const char *FuncStartsLoadCmd = nullptr;
1200   const char *SplitInfoLoadCmd = nullptr;
1201   const char *CodeSignDrsLoadCmd = nullptr;
1202   const char *CodeSignLoadCmd = nullptr;
1203   const char *VersLoadCmd = nullptr;
1204   const char *SourceLoadCmd = nullptr;
1205   const char *EntryPointLoadCmd = nullptr;
1206   const char *EncryptLoadCmd = nullptr;
1207   const char *RoutinesLoadCmd = nullptr;
1208   const char *UnixThreadLoadCmd = nullptr;
1209   const char *TwoLevelHintsLoadCmd = nullptr;
1210   for (unsigned I = 0; I < LoadCommandCount; ++I) {
1211     if (is64Bit()) {
1212       if (Load.C.cmdsize % 8 != 0) {
1213         // We have a hack here to allow 64-bit Mach-O core files to have
1214         // LC_THREAD commands that are only a multiple of 4 and not 8 to be
1215         // allowed since the macOS kernel produces them.
1216         if (getHeader().filetype != MachO::MH_CORE ||
1217             Load.C.cmd != MachO::LC_THREAD || Load.C.cmdsize % 4) {
1218           Err = malformedError("load command " + Twine(I) + " cmdsize not a "
1219                                "multiple of 8");
1220           return;
1221         }
1222       }
1223     } else {
1224       if (Load.C.cmdsize % 4 != 0) {
1225         Err = malformedError("load command " + Twine(I) + " cmdsize not a "
1226                              "multiple of 4");
1227         return;
1228       }
1229     }
1230     LoadCommands.push_back(Load);
1231     if (Load.C.cmd == MachO::LC_SYMTAB) {
1232       if ((Err = checkSymtabCommand(*this, Load, I, &SymtabLoadCmd, Elements)))
1233         return;
1234     } else if (Load.C.cmd == MachO::LC_DYSYMTAB) {
1235       if ((Err = checkDysymtabCommand(*this, Load, I, &DysymtabLoadCmd,
1236                                       Elements)))
1237         return;
1238     } else if (Load.C.cmd == MachO::LC_DATA_IN_CODE) {
1239       if ((Err = checkLinkeditDataCommand(*this, Load, I, &DataInCodeLoadCmd,
1240                                           "LC_DATA_IN_CODE", Elements,
1241                                           "data in code info")))
1242         return;
1243     } else if (Load.C.cmd == MachO::LC_LINKER_OPTIMIZATION_HINT) {
1244       if ((Err = checkLinkeditDataCommand(*this, Load, I, &LinkOptHintsLoadCmd,
1245                                           "LC_LINKER_OPTIMIZATION_HINT",
1246                                           Elements, "linker optimization "
1247                                           "hints")))
1248         return;
1249     } else if (Load.C.cmd == MachO::LC_FUNCTION_STARTS) {
1250       if ((Err = checkLinkeditDataCommand(*this, Load, I, &FuncStartsLoadCmd,
1251                                           "LC_FUNCTION_STARTS", Elements,
1252                                           "function starts data")))
1253         return;
1254     } else if (Load.C.cmd == MachO::LC_SEGMENT_SPLIT_INFO) {
1255       if ((Err = checkLinkeditDataCommand(*this, Load, I, &SplitInfoLoadCmd,
1256                                           "LC_SEGMENT_SPLIT_INFO", Elements,
1257                                           "split info data")))
1258         return;
1259     } else if (Load.C.cmd == MachO::LC_DYLIB_CODE_SIGN_DRS) {
1260       if ((Err = checkLinkeditDataCommand(*this, Load, I, &CodeSignDrsLoadCmd,
1261                                           "LC_DYLIB_CODE_SIGN_DRS", Elements,
1262                                           "code signing RDs data")))
1263         return;
1264     } else if (Load.C.cmd == MachO::LC_CODE_SIGNATURE) {
1265       if ((Err = checkLinkeditDataCommand(*this, Load, I, &CodeSignLoadCmd,
1266                                           "LC_CODE_SIGNATURE", Elements,
1267                                           "code signature data")))
1268         return;
1269     } else if (Load.C.cmd == MachO::LC_DYLD_INFO) {
1270       if ((Err = checkDyldInfoCommand(*this, Load, I, &DyldInfoLoadCmd,
1271                                       "LC_DYLD_INFO", Elements)))
1272         return;
1273     } else if (Load.C.cmd == MachO::LC_DYLD_INFO_ONLY) {
1274       if ((Err = checkDyldInfoCommand(*this, Load, I, &DyldInfoLoadCmd,
1275                                       "LC_DYLD_INFO_ONLY", Elements)))
1276         return;
1277     } else if (Load.C.cmd == MachO::LC_UUID) {
1278       if (Load.C.cmdsize != sizeof(MachO::uuid_command)) {
1279         Err = malformedError("LC_UUID command " + Twine(I) + " has incorrect "
1280                              "cmdsize");
1281         return;
1282       }
1283       if (UuidLoadCmd) {
1284         Err = malformedError("more than one LC_UUID command");
1285         return;
1286       }
1287       UuidLoadCmd = Load.Ptr;
1288     } else if (Load.C.cmd == MachO::LC_SEGMENT_64) {
1289       if ((Err = parseSegmentLoadCommand<MachO::segment_command_64,
1290                                          MachO::section_64>(
1291                    *this, Load, Sections, HasPageZeroSegment, I,
1292                    "LC_SEGMENT_64", SizeOfHeaders, Elements)))
1293         return;
1294     } else if (Load.C.cmd == MachO::LC_SEGMENT) {
1295       if ((Err = parseSegmentLoadCommand<MachO::segment_command,
1296                                          MachO::section>(
1297                    *this, Load, Sections, HasPageZeroSegment, I,
1298                    "LC_SEGMENT", SizeOfHeaders, Elements)))
1299         return;
1300     } else if (Load.C.cmd == MachO::LC_ID_DYLIB) {
1301       if ((Err = checkDylibIdCommand(*this, Load, I, &DyldIdLoadCmd)))
1302         return;
1303     } else if (Load.C.cmd == MachO::LC_LOAD_DYLIB) {
1304       if ((Err = checkDylibCommand(*this, Load, I, "LC_LOAD_DYLIB")))
1305         return;
1306       Libraries.push_back(Load.Ptr);
1307     } else if (Load.C.cmd == MachO::LC_LOAD_WEAK_DYLIB) {
1308       if ((Err = checkDylibCommand(*this, Load, I, "LC_LOAD_WEAK_DYLIB")))
1309         return;
1310       Libraries.push_back(Load.Ptr);
1311     } else if (Load.C.cmd == MachO::LC_LAZY_LOAD_DYLIB) {
1312       if ((Err = checkDylibCommand(*this, Load, I, "LC_LAZY_LOAD_DYLIB")))
1313         return;
1314       Libraries.push_back(Load.Ptr);
1315     } else if (Load.C.cmd == MachO::LC_REEXPORT_DYLIB) {
1316       if ((Err = checkDylibCommand(*this, Load, I, "LC_REEXPORT_DYLIB")))
1317         return;
1318       Libraries.push_back(Load.Ptr);
1319     } else if (Load.C.cmd == MachO::LC_LOAD_UPWARD_DYLIB) {
1320       if ((Err = checkDylibCommand(*this, Load, I, "LC_LOAD_UPWARD_DYLIB")))
1321         return;
1322       Libraries.push_back(Load.Ptr);
1323     } else if (Load.C.cmd == MachO::LC_ID_DYLINKER) {
1324       if ((Err = checkDyldCommand(*this, Load, I, "LC_ID_DYLINKER")))
1325         return;
1326     } else if (Load.C.cmd == MachO::LC_LOAD_DYLINKER) {
1327       if ((Err = checkDyldCommand(*this, Load, I, "LC_LOAD_DYLINKER")))
1328         return;
1329     } else if (Load.C.cmd == MachO::LC_DYLD_ENVIRONMENT) {
1330       if ((Err = checkDyldCommand(*this, Load, I, "LC_DYLD_ENVIRONMENT")))
1331         return;
1332     } else if (Load.C.cmd == MachO::LC_VERSION_MIN_MACOSX) {
1333       if ((Err = checkVersCommand(*this, Load, I, &VersLoadCmd,
1334                                   "LC_VERSION_MIN_MACOSX")))
1335         return;
1336     } else if (Load.C.cmd == MachO::LC_VERSION_MIN_IPHONEOS) {
1337       if ((Err = checkVersCommand(*this, Load, I, &VersLoadCmd,
1338                                   "LC_VERSION_MIN_IPHONEOS")))
1339         return;
1340     } else if (Load.C.cmd == MachO::LC_VERSION_MIN_TVOS) {
1341       if ((Err = checkVersCommand(*this, Load, I, &VersLoadCmd,
1342                                   "LC_VERSION_MIN_TVOS")))
1343         return;
1344     } else if (Load.C.cmd == MachO::LC_VERSION_MIN_WATCHOS) {
1345       if ((Err = checkVersCommand(*this, Load, I, &VersLoadCmd,
1346                                   "LC_VERSION_MIN_WATCHOS")))
1347         return;
1348     } else if (Load.C.cmd == MachO::LC_NOTE) {
1349       if ((Err = checkNoteCommand(*this, Load, I, Elements)))
1350         return;
1351     } else if (Load.C.cmd == MachO::LC_BUILD_VERSION) {
1352       if ((Err = parseBuildVersionCommand(*this, Load, BuildTools, I)))
1353         return;
1354     } else if (Load.C.cmd == MachO::LC_RPATH) {
1355       if ((Err = checkRpathCommand(*this, Load, I)))
1356         return;
1357     } else if (Load.C.cmd == MachO::LC_SOURCE_VERSION) {
1358       if (Load.C.cmdsize != sizeof(MachO::source_version_command)) {
1359         Err = malformedError("LC_SOURCE_VERSION command " + Twine(I) +
1360                              " has incorrect cmdsize");
1361         return;
1362       }
1363       if (SourceLoadCmd) {
1364         Err = malformedError("more than one LC_SOURCE_VERSION command");
1365         return;
1366       }
1367       SourceLoadCmd = Load.Ptr;
1368     } else if (Load.C.cmd == MachO::LC_MAIN) {
1369       if (Load.C.cmdsize != sizeof(MachO::entry_point_command)) {
1370         Err = malformedError("LC_MAIN command " + Twine(I) +
1371                              " has incorrect cmdsize");
1372         return;
1373       }
1374       if (EntryPointLoadCmd) {
1375         Err = malformedError("more than one LC_MAIN command");
1376         return;
1377       }
1378       EntryPointLoadCmd = Load.Ptr;
1379     } else if (Load.C.cmd == MachO::LC_ENCRYPTION_INFO) {
1380       if (Load.C.cmdsize != sizeof(MachO::encryption_info_command)) {
1381         Err = malformedError("LC_ENCRYPTION_INFO command " + Twine(I) +
1382                              " has incorrect cmdsize");
1383         return;
1384       }
1385       MachO::encryption_info_command E =
1386         getStruct<MachO::encryption_info_command>(*this, Load.Ptr);
1387       if ((Err = checkEncryptCommand(*this, Load, I, E.cryptoff, E.cryptsize,
1388                                      &EncryptLoadCmd, "LC_ENCRYPTION_INFO")))
1389         return;
1390     } else if (Load.C.cmd == MachO::LC_ENCRYPTION_INFO_64) {
1391       if (Load.C.cmdsize != sizeof(MachO::encryption_info_command_64)) {
1392         Err = malformedError("LC_ENCRYPTION_INFO_64 command " + Twine(I) +
1393                              " has incorrect cmdsize");
1394         return;
1395       }
1396       MachO::encryption_info_command_64 E =
1397         getStruct<MachO::encryption_info_command_64>(*this, Load.Ptr);
1398       if ((Err = checkEncryptCommand(*this, Load, I, E.cryptoff, E.cryptsize,
1399                                      &EncryptLoadCmd, "LC_ENCRYPTION_INFO_64")))
1400         return;
1401     } else if (Load.C.cmd == MachO::LC_LINKER_OPTION) {
1402       if ((Err = checkLinkerOptCommand(*this, Load, I)))
1403         return;
1404     } else if (Load.C.cmd == MachO::LC_SUB_FRAMEWORK) {
1405       if (Load.C.cmdsize < sizeof(MachO::sub_framework_command)) {
1406         Err =  malformedError("load command " + Twine(I) +
1407                               " LC_SUB_FRAMEWORK cmdsize too small");
1408         return;
1409       }
1410       MachO::sub_framework_command S =
1411         getStruct<MachO::sub_framework_command>(*this, Load.Ptr);
1412       if ((Err = checkSubCommand(*this, Load, I, "LC_SUB_FRAMEWORK",
1413                                  sizeof(MachO::sub_framework_command),
1414                                  "sub_framework_command", S.umbrella,
1415                                  "umbrella")))
1416         return;
1417     } else if (Load.C.cmd == MachO::LC_SUB_UMBRELLA) {
1418       if (Load.C.cmdsize < sizeof(MachO::sub_umbrella_command)) {
1419         Err =  malformedError("load command " + Twine(I) +
1420                               " LC_SUB_UMBRELLA cmdsize too small");
1421         return;
1422       }
1423       MachO::sub_umbrella_command S =
1424         getStruct<MachO::sub_umbrella_command>(*this, Load.Ptr);
1425       if ((Err = checkSubCommand(*this, Load, I, "LC_SUB_UMBRELLA",
1426                                  sizeof(MachO::sub_umbrella_command),
1427                                  "sub_umbrella_command", S.sub_umbrella,
1428                                  "sub_umbrella")))
1429         return;
1430     } else if (Load.C.cmd == MachO::LC_SUB_LIBRARY) {
1431       if (Load.C.cmdsize < sizeof(MachO::sub_library_command)) {
1432         Err =  malformedError("load command " + Twine(I) +
1433                               " LC_SUB_LIBRARY cmdsize too small");
1434         return;
1435       }
1436       MachO::sub_library_command S =
1437         getStruct<MachO::sub_library_command>(*this, Load.Ptr);
1438       if ((Err = checkSubCommand(*this, Load, I, "LC_SUB_LIBRARY",
1439                                  sizeof(MachO::sub_library_command),
1440                                  "sub_library_command", S.sub_library,
1441                                  "sub_library")))
1442         return;
1443     } else if (Load.C.cmd == MachO::LC_SUB_CLIENT) {
1444       if (Load.C.cmdsize < sizeof(MachO::sub_client_command)) {
1445         Err =  malformedError("load command " + Twine(I) +
1446                               " LC_SUB_CLIENT cmdsize too small");
1447         return;
1448       }
1449       MachO::sub_client_command S =
1450         getStruct<MachO::sub_client_command>(*this, Load.Ptr);
1451       if ((Err = checkSubCommand(*this, Load, I, "LC_SUB_CLIENT",
1452                                  sizeof(MachO::sub_client_command),
1453                                  "sub_client_command", S.client, "client")))
1454         return;
1455     } else if (Load.C.cmd == MachO::LC_ROUTINES) {
1456       if (Load.C.cmdsize != sizeof(MachO::routines_command)) {
1457         Err = malformedError("LC_ROUTINES command " + Twine(I) +
1458                              " has incorrect cmdsize");
1459         return;
1460       }
1461       if (RoutinesLoadCmd) {
1462         Err = malformedError("more than one LC_ROUTINES and or LC_ROUTINES_64 "
1463                              "command");
1464         return;
1465       }
1466       RoutinesLoadCmd = Load.Ptr;
1467     } else if (Load.C.cmd == MachO::LC_ROUTINES_64) {
1468       if (Load.C.cmdsize != sizeof(MachO::routines_command_64)) {
1469         Err = malformedError("LC_ROUTINES_64 command " + Twine(I) +
1470                              " has incorrect cmdsize");
1471         return;
1472       }
1473       if (RoutinesLoadCmd) {
1474         Err = malformedError("more than one LC_ROUTINES_64 and or LC_ROUTINES "
1475                              "command");
1476         return;
1477       }
1478       RoutinesLoadCmd = Load.Ptr;
1479     } else if (Load.C.cmd == MachO::LC_UNIXTHREAD) {
1480       if ((Err = checkThreadCommand(*this, Load, I, "LC_UNIXTHREAD")))
1481         return;
1482       if (UnixThreadLoadCmd) {
1483         Err = malformedError("more than one LC_UNIXTHREAD command");
1484         return;
1485       }
1486       UnixThreadLoadCmd = Load.Ptr;
1487     } else if (Load.C.cmd == MachO::LC_THREAD) {
1488       if ((Err = checkThreadCommand(*this, Load, I, "LC_THREAD")))
1489         return;
1490     // Note: LC_TWOLEVEL_HINTS is really obsolete and is not supported.
1491     } else if (Load.C.cmd == MachO::LC_TWOLEVEL_HINTS) {
1492        if ((Err = checkTwoLevelHintsCommand(*this, Load, I,
1493                                             &TwoLevelHintsLoadCmd, Elements)))
1494          return;
1495     } else if (isLoadCommandObsolete(Load.C.cmd)) {
1496       Err = malformedError("load command " + Twine(I) + " for cmd value of: " +
1497                            Twine(Load.C.cmd) + " is obsolete and not "
1498                            "supported");
1499       return;
1500     }
1501     // TODO: generate a error for unknown load commands by default.  But still
1502     // need work out an approach to allow or not allow unknown values like this
1503     // as an option for some uses like lldb.
1504     if (I < LoadCommandCount - 1) {
1505       if (auto LoadOrErr = getNextLoadCommandInfo(*this, I, Load))
1506         Load = *LoadOrErr;
1507       else {
1508         Err = LoadOrErr.takeError();
1509         return;
1510       }
1511     }
1512   }
1513   if (!SymtabLoadCmd) {
1514     if (DysymtabLoadCmd) {
1515       Err = malformedError("contains LC_DYSYMTAB load command without a "
1516                            "LC_SYMTAB load command");
1517       return;
1518     }
1519   } else if (DysymtabLoadCmd) {
1520     MachO::symtab_command Symtab =
1521       getStruct<MachO::symtab_command>(*this, SymtabLoadCmd);
1522     MachO::dysymtab_command Dysymtab =
1523       getStruct<MachO::dysymtab_command>(*this, DysymtabLoadCmd);
1524     if (Dysymtab.nlocalsym != 0 && Dysymtab.ilocalsym > Symtab.nsyms) {
1525       Err = malformedError("ilocalsym in LC_DYSYMTAB load command "
1526                            "extends past the end of the symbol table");
1527       return;
1528     }
1529     uint64_t BigSize = Dysymtab.ilocalsym;
1530     BigSize += Dysymtab.nlocalsym;
1531     if (Dysymtab.nlocalsym != 0 && BigSize > Symtab.nsyms) {
1532       Err = malformedError("ilocalsym plus nlocalsym in LC_DYSYMTAB load "
1533                            "command extends past the end of the symbol table");
1534       return;
1535     }
1536     if (Dysymtab.nextdefsym != 0 && Dysymtab.ilocalsym > Symtab.nsyms) {
1537       Err = malformedError("nextdefsym in LC_DYSYMTAB load command "
1538                            "extends past the end of the symbol table");
1539       return;
1540     }
1541     BigSize = Dysymtab.iextdefsym;
1542     BigSize += Dysymtab.nextdefsym;
1543     if (Dysymtab.nextdefsym != 0 && BigSize > Symtab.nsyms) {
1544       Err = malformedError("iextdefsym plus nextdefsym in LC_DYSYMTAB "
1545                            "load command extends past the end of the symbol "
1546                            "table");
1547       return;
1548     }
1549     if (Dysymtab.nundefsym != 0 && Dysymtab.iundefsym > Symtab.nsyms) {
1550       Err = malformedError("nundefsym in LC_DYSYMTAB load command "
1551                            "extends past the end of the symbol table");
1552       return;
1553     }
1554     BigSize = Dysymtab.iundefsym;
1555     BigSize += Dysymtab.nundefsym;
1556     if (Dysymtab.nundefsym != 0 && BigSize > Symtab.nsyms) {
1557       Err = malformedError("iundefsym plus nundefsym in LC_DYSYMTAB load "
1558                            " command extends past the end of the symbol table");
1559       return;
1560     }
1561   }
1562   if ((getHeader().filetype == MachO::MH_DYLIB ||
1563        getHeader().filetype == MachO::MH_DYLIB_STUB) &&
1564        DyldIdLoadCmd == nullptr) {
1565     Err = malformedError("no LC_ID_DYLIB load command in dynamic library "
1566                          "filetype");
1567     return;
1568   }
1569   assert(LoadCommands.size() == LoadCommandCount);
1570 
1571   Err = Error::success();
1572 }
1573 
1574 Error MachOObjectFile::checkSymbolTable() const {
1575   uint32_t Flags = 0;
1576   if (is64Bit()) {
1577     MachO::mach_header_64 H_64 = MachOObjectFile::getHeader64();
1578     Flags = H_64.flags;
1579   } else {
1580     MachO::mach_header H = MachOObjectFile::getHeader();
1581     Flags = H.flags;
1582   }
1583   uint8_t NType = 0;
1584   uint8_t NSect = 0;
1585   uint16_t NDesc = 0;
1586   uint32_t NStrx = 0;
1587   uint64_t NValue = 0;
1588   uint32_t SymbolIndex = 0;
1589   MachO::symtab_command S = getSymtabLoadCommand();
1590   for (const SymbolRef &Symbol : symbols()) {
1591     DataRefImpl SymDRI = Symbol.getRawDataRefImpl();
1592     if (is64Bit()) {
1593       MachO::nlist_64 STE_64 = getSymbol64TableEntry(SymDRI);
1594       NType = STE_64.n_type;
1595       NSect = STE_64.n_sect;
1596       NDesc = STE_64.n_desc;
1597       NStrx = STE_64.n_strx;
1598       NValue = STE_64.n_value;
1599     } else {
1600       MachO::nlist STE = getSymbolTableEntry(SymDRI);
1601       NType = STE.n_type;
1602       NType = STE.n_type;
1603       NSect = STE.n_sect;
1604       NDesc = STE.n_desc;
1605       NStrx = STE.n_strx;
1606       NValue = STE.n_value;
1607     }
1608     if ((NType & MachO::N_STAB) == 0 &&
1609         (NType & MachO::N_TYPE) == MachO::N_SECT) {
1610       if (NSect == 0 || NSect > Sections.size())
1611         return malformedError("bad section index: " + Twine((int)NSect) +
1612                               " for symbol at index " + Twine(SymbolIndex));
1613     }
1614     if ((NType & MachO::N_STAB) == 0 &&
1615         (NType & MachO::N_TYPE) == MachO::N_INDR) {
1616       if (NValue >= S.strsize)
1617         return malformedError("bad n_value: " + Twine((int)NValue) + " past "
1618                               "the end of string table, for N_INDR symbol at "
1619                               "index " + Twine(SymbolIndex));
1620     }
1621     if ((Flags & MachO::MH_TWOLEVEL) == MachO::MH_TWOLEVEL &&
1622         (((NType & MachO::N_TYPE) == MachO::N_UNDF && NValue == 0) ||
1623          (NType & MachO::N_TYPE) == MachO::N_PBUD)) {
1624       uint32_t LibraryOrdinal = MachO::GET_LIBRARY_ORDINAL(NDesc);
1625       if (LibraryOrdinal != 0 &&
1626           LibraryOrdinal != MachO::EXECUTABLE_ORDINAL &&
1627           LibraryOrdinal != MachO::DYNAMIC_LOOKUP_ORDINAL &&
1628           LibraryOrdinal - 1 >= Libraries.size() ) {
1629         return malformedError("bad library ordinal: " + Twine(LibraryOrdinal) +
1630                             " for symbol at index " + Twine(SymbolIndex));
1631       }
1632     }
1633     if (NStrx >= S.strsize)
1634       return malformedError("bad string table index: " + Twine((int)NStrx) +
1635                             " past the end of string table, for symbol at "
1636                             "index " + Twine(SymbolIndex));
1637     SymbolIndex++;
1638   }
1639   return Error::success();
1640 }
1641 
1642 void MachOObjectFile::moveSymbolNext(DataRefImpl &Symb) const {
1643   unsigned SymbolTableEntrySize = is64Bit() ?
1644     sizeof(MachO::nlist_64) :
1645     sizeof(MachO::nlist);
1646   Symb.p += SymbolTableEntrySize;
1647 }
1648 
1649 Expected<StringRef> MachOObjectFile::getSymbolName(DataRefImpl Symb) const {
1650   StringRef StringTable = getStringTableData();
1651   MachO::nlist_base Entry = getSymbolTableEntryBase(*this, Symb);
1652   const char *Start = &StringTable.data()[Entry.n_strx];
1653   if (Start < getData().begin() || Start >= getData().end()) {
1654     return malformedError("bad string index: " + Twine(Entry.n_strx) +
1655                           " for symbol at index " + Twine(getSymbolIndex(Symb)));
1656   }
1657   return StringRef(Start);
1658 }
1659 
1660 unsigned MachOObjectFile::getSectionType(SectionRef Sec) const {
1661   DataRefImpl DRI = Sec.getRawDataRefImpl();
1662   uint32_t Flags = getSectionFlags(*this, DRI);
1663   return Flags & MachO::SECTION_TYPE;
1664 }
1665 
1666 uint64_t MachOObjectFile::getNValue(DataRefImpl Sym) const {
1667   if (is64Bit()) {
1668     MachO::nlist_64 Entry = getSymbol64TableEntry(Sym);
1669     return Entry.n_value;
1670   }
1671   MachO::nlist Entry = getSymbolTableEntry(Sym);
1672   return Entry.n_value;
1673 }
1674 
1675 // getIndirectName() returns the name of the alias'ed symbol who's string table
1676 // index is in the n_value field.
1677 std::error_code MachOObjectFile::getIndirectName(DataRefImpl Symb,
1678                                                  StringRef &Res) const {
1679   StringRef StringTable = getStringTableData();
1680   MachO::nlist_base Entry = getSymbolTableEntryBase(*this, Symb);
1681   if ((Entry.n_type & MachO::N_TYPE) != MachO::N_INDR)
1682     return object_error::parse_failed;
1683   uint64_t NValue = getNValue(Symb);
1684   if (NValue >= StringTable.size())
1685     return object_error::parse_failed;
1686   const char *Start = &StringTable.data()[NValue];
1687   Res = StringRef(Start);
1688   return std::error_code();
1689 }
1690 
1691 uint64_t MachOObjectFile::getSymbolValueImpl(DataRefImpl Sym) const {
1692   return getNValue(Sym);
1693 }
1694 
1695 Expected<uint64_t> MachOObjectFile::getSymbolAddress(DataRefImpl Sym) const {
1696   return getSymbolValue(Sym);
1697 }
1698 
1699 uint32_t MachOObjectFile::getSymbolAlignment(DataRefImpl DRI) const {
1700   uint32_t flags = getSymbolFlags(DRI);
1701   if (flags & SymbolRef::SF_Common) {
1702     MachO::nlist_base Entry = getSymbolTableEntryBase(*this, DRI);
1703     return 1 << MachO::GET_COMM_ALIGN(Entry.n_desc);
1704   }
1705   return 0;
1706 }
1707 
1708 uint64_t MachOObjectFile::getCommonSymbolSizeImpl(DataRefImpl DRI) const {
1709   return getNValue(DRI);
1710 }
1711 
1712 Expected<SymbolRef::Type>
1713 MachOObjectFile::getSymbolType(DataRefImpl Symb) const {
1714   MachO::nlist_base Entry = getSymbolTableEntryBase(*this, Symb);
1715   uint8_t n_type = Entry.n_type;
1716 
1717   // If this is a STAB debugging symbol, we can do nothing more.
1718   if (n_type & MachO::N_STAB)
1719     return SymbolRef::ST_Debug;
1720 
1721   switch (n_type & MachO::N_TYPE) {
1722     case MachO::N_UNDF :
1723       return SymbolRef::ST_Unknown;
1724     case MachO::N_SECT :
1725       Expected<section_iterator> SecOrError = getSymbolSection(Symb);
1726       if (!SecOrError)
1727         return SecOrError.takeError();
1728       section_iterator Sec = *SecOrError;
1729       if (Sec->isData() || Sec->isBSS())
1730         return SymbolRef::ST_Data;
1731       return SymbolRef::ST_Function;
1732   }
1733   return SymbolRef::ST_Other;
1734 }
1735 
1736 uint32_t MachOObjectFile::getSymbolFlags(DataRefImpl DRI) const {
1737   MachO::nlist_base Entry = getSymbolTableEntryBase(*this, DRI);
1738 
1739   uint8_t MachOType = Entry.n_type;
1740   uint16_t MachOFlags = Entry.n_desc;
1741 
1742   uint32_t Result = SymbolRef::SF_None;
1743 
1744   if ((MachOType & MachO::N_TYPE) == MachO::N_INDR)
1745     Result |= SymbolRef::SF_Indirect;
1746 
1747   if (MachOType & MachO::N_STAB)
1748     Result |= SymbolRef::SF_FormatSpecific;
1749 
1750   if (MachOType & MachO::N_EXT) {
1751     Result |= SymbolRef::SF_Global;
1752     if ((MachOType & MachO::N_TYPE) == MachO::N_UNDF) {
1753       if (getNValue(DRI))
1754         Result |= SymbolRef::SF_Common;
1755       else
1756         Result |= SymbolRef::SF_Undefined;
1757     }
1758 
1759     if (!(MachOType & MachO::N_PEXT))
1760       Result |= SymbolRef::SF_Exported;
1761   }
1762 
1763   if (MachOFlags & (MachO::N_WEAK_REF | MachO::N_WEAK_DEF))
1764     Result |= SymbolRef::SF_Weak;
1765 
1766   if (MachOFlags & (MachO::N_ARM_THUMB_DEF))
1767     Result |= SymbolRef::SF_Thumb;
1768 
1769   if ((MachOType & MachO::N_TYPE) == MachO::N_ABS)
1770     Result |= SymbolRef::SF_Absolute;
1771 
1772   return Result;
1773 }
1774 
1775 Expected<section_iterator>
1776 MachOObjectFile::getSymbolSection(DataRefImpl Symb) const {
1777   MachO::nlist_base Entry = getSymbolTableEntryBase(*this, Symb);
1778   uint8_t index = Entry.n_sect;
1779 
1780   if (index == 0)
1781     return section_end();
1782   DataRefImpl DRI;
1783   DRI.d.a = index - 1;
1784   if (DRI.d.a >= Sections.size()){
1785     return malformedError("bad section index: " + Twine((int)index) +
1786                           " for symbol at index " + Twine(getSymbolIndex(Symb)));
1787   }
1788   return section_iterator(SectionRef(DRI, this));
1789 }
1790 
1791 unsigned MachOObjectFile::getSymbolSectionID(SymbolRef Sym) const {
1792   MachO::nlist_base Entry =
1793       getSymbolTableEntryBase(*this, Sym.getRawDataRefImpl());
1794   return Entry.n_sect - 1;
1795 }
1796 
1797 void MachOObjectFile::moveSectionNext(DataRefImpl &Sec) const {
1798   Sec.d.a++;
1799 }
1800 
1801 std::error_code MachOObjectFile::getSectionName(DataRefImpl Sec,
1802                                                 StringRef &Result) const {
1803   ArrayRef<char> Raw = getSectionRawName(Sec);
1804   Result = parseSegmentOrSectionName(Raw.data());
1805   return std::error_code();
1806 }
1807 
1808 uint64_t MachOObjectFile::getSectionAddress(DataRefImpl Sec) const {
1809   if (is64Bit())
1810     return getSection64(Sec).addr;
1811   return getSection(Sec).addr;
1812 }
1813 
1814 uint64_t MachOObjectFile::getSectionSize(DataRefImpl Sec) const {
1815   // In the case if a malformed Mach-O file where the section offset is past
1816   // the end of the file or some part of the section size is past the end of
1817   // the file return a size of zero or a size that covers the rest of the file
1818   // but does not extend past the end of the file.
1819   uint32_t SectOffset, SectType;
1820   uint64_t SectSize;
1821 
1822   if (is64Bit()) {
1823     MachO::section_64 Sect = getSection64(Sec);
1824     SectOffset = Sect.offset;
1825     SectSize = Sect.size;
1826     SectType = Sect.flags & MachO::SECTION_TYPE;
1827   } else {
1828     MachO::section Sect = getSection(Sec);
1829     SectOffset = Sect.offset;
1830     SectSize = Sect.size;
1831     SectType = Sect.flags & MachO::SECTION_TYPE;
1832   }
1833   if (SectType == MachO::S_ZEROFILL || SectType == MachO::S_GB_ZEROFILL)
1834     return SectSize;
1835   uint64_t FileSize = getData().size();
1836   if (SectOffset > FileSize)
1837     return 0;
1838   if (FileSize - SectOffset < SectSize)
1839     return FileSize - SectOffset;
1840   return SectSize;
1841 }
1842 
1843 std::error_code MachOObjectFile::getSectionContents(DataRefImpl Sec,
1844                                                     StringRef &Res) const {
1845   uint32_t Offset;
1846   uint64_t Size;
1847 
1848   if (is64Bit()) {
1849     MachO::section_64 Sect = getSection64(Sec);
1850     Offset = Sect.offset;
1851     Size = Sect.size;
1852   } else {
1853     MachO::section Sect = getSection(Sec);
1854     Offset = Sect.offset;
1855     Size = Sect.size;
1856   }
1857 
1858   Res = this->getData().substr(Offset, Size);
1859   return std::error_code();
1860 }
1861 
1862 uint64_t MachOObjectFile::getSectionAlignment(DataRefImpl Sec) const {
1863   uint32_t Align;
1864   if (is64Bit()) {
1865     MachO::section_64 Sect = getSection64(Sec);
1866     Align = Sect.align;
1867   } else {
1868     MachO::section Sect = getSection(Sec);
1869     Align = Sect.align;
1870   }
1871 
1872   return uint64_t(1) << Align;
1873 }
1874 
1875 bool MachOObjectFile::isSectionCompressed(DataRefImpl Sec) const {
1876   return false;
1877 }
1878 
1879 bool MachOObjectFile::isSectionText(DataRefImpl Sec) const {
1880   uint32_t Flags = getSectionFlags(*this, Sec);
1881   return Flags & MachO::S_ATTR_PURE_INSTRUCTIONS;
1882 }
1883 
1884 bool MachOObjectFile::isSectionData(DataRefImpl Sec) const {
1885   uint32_t Flags = getSectionFlags(*this, Sec);
1886   unsigned SectionType = Flags & MachO::SECTION_TYPE;
1887   return !(Flags & MachO::S_ATTR_PURE_INSTRUCTIONS) &&
1888          !(SectionType == MachO::S_ZEROFILL ||
1889            SectionType == MachO::S_GB_ZEROFILL);
1890 }
1891 
1892 bool MachOObjectFile::isSectionBSS(DataRefImpl Sec) const {
1893   uint32_t Flags = getSectionFlags(*this, Sec);
1894   unsigned SectionType = Flags & MachO::SECTION_TYPE;
1895   return !(Flags & MachO::S_ATTR_PURE_INSTRUCTIONS) &&
1896          (SectionType == MachO::S_ZEROFILL ||
1897           SectionType == MachO::S_GB_ZEROFILL);
1898 }
1899 
1900 unsigned MachOObjectFile::getSectionID(SectionRef Sec) const {
1901   return Sec.getRawDataRefImpl().d.a;
1902 }
1903 
1904 bool MachOObjectFile::isSectionVirtual(DataRefImpl Sec) const {
1905   // FIXME: Unimplemented.
1906   return false;
1907 }
1908 
1909 bool MachOObjectFile::isSectionBitcode(DataRefImpl Sec) const {
1910   StringRef SegmentName = getSectionFinalSegmentName(Sec);
1911   StringRef SectName;
1912   if (!getSectionName(Sec, SectName))
1913     return (SegmentName == "__LLVM" && SectName == "__bitcode");
1914   return false;
1915 }
1916 
1917 relocation_iterator MachOObjectFile::section_rel_begin(DataRefImpl Sec) const {
1918   DataRefImpl Ret;
1919   Ret.d.a = Sec.d.a;
1920   Ret.d.b = 0;
1921   return relocation_iterator(RelocationRef(Ret, this));
1922 }
1923 
1924 relocation_iterator
1925 MachOObjectFile::section_rel_end(DataRefImpl Sec) const {
1926   uint32_t Num;
1927   if (is64Bit()) {
1928     MachO::section_64 Sect = getSection64(Sec);
1929     Num = Sect.nreloc;
1930   } else {
1931     MachO::section Sect = getSection(Sec);
1932     Num = Sect.nreloc;
1933   }
1934 
1935   DataRefImpl Ret;
1936   Ret.d.a = Sec.d.a;
1937   Ret.d.b = Num;
1938   return relocation_iterator(RelocationRef(Ret, this));
1939 }
1940 
1941 void MachOObjectFile::moveRelocationNext(DataRefImpl &Rel) const {
1942   ++Rel.d.b;
1943 }
1944 
1945 uint64_t MachOObjectFile::getRelocationOffset(DataRefImpl Rel) const {
1946   assert(getHeader().filetype == MachO::MH_OBJECT &&
1947          "Only implemented for MH_OBJECT");
1948   MachO::any_relocation_info RE = getRelocation(Rel);
1949   return getAnyRelocationAddress(RE);
1950 }
1951 
1952 symbol_iterator
1953 MachOObjectFile::getRelocationSymbol(DataRefImpl Rel) const {
1954   MachO::any_relocation_info RE = getRelocation(Rel);
1955   if (isRelocationScattered(RE))
1956     return symbol_end();
1957 
1958   uint32_t SymbolIdx = getPlainRelocationSymbolNum(RE);
1959   bool isExtern = getPlainRelocationExternal(RE);
1960   if (!isExtern)
1961     return symbol_end();
1962 
1963   MachO::symtab_command S = getSymtabLoadCommand();
1964   unsigned SymbolTableEntrySize = is64Bit() ?
1965     sizeof(MachO::nlist_64) :
1966     sizeof(MachO::nlist);
1967   uint64_t Offset = S.symoff + SymbolIdx * SymbolTableEntrySize;
1968   DataRefImpl Sym;
1969   Sym.p = reinterpret_cast<uintptr_t>(getPtr(*this, Offset));
1970   return symbol_iterator(SymbolRef(Sym, this));
1971 }
1972 
1973 section_iterator
1974 MachOObjectFile::getRelocationSection(DataRefImpl Rel) const {
1975   return section_iterator(getAnyRelocationSection(getRelocation(Rel)));
1976 }
1977 
1978 uint64_t MachOObjectFile::getRelocationType(DataRefImpl Rel) const {
1979   MachO::any_relocation_info RE = getRelocation(Rel);
1980   return getAnyRelocationType(RE);
1981 }
1982 
1983 void MachOObjectFile::getRelocationTypeName(
1984     DataRefImpl Rel, SmallVectorImpl<char> &Result) const {
1985   StringRef res;
1986   uint64_t RType = getRelocationType(Rel);
1987 
1988   unsigned Arch = this->getArch();
1989 
1990   switch (Arch) {
1991     case Triple::x86: {
1992       static const char *const Table[] =  {
1993         "GENERIC_RELOC_VANILLA",
1994         "GENERIC_RELOC_PAIR",
1995         "GENERIC_RELOC_SECTDIFF",
1996         "GENERIC_RELOC_PB_LA_PTR",
1997         "GENERIC_RELOC_LOCAL_SECTDIFF",
1998         "GENERIC_RELOC_TLV" };
1999 
2000       if (RType > 5)
2001         res = "Unknown";
2002       else
2003         res = Table[RType];
2004       break;
2005     }
2006     case Triple::x86_64: {
2007       static const char *const Table[] =  {
2008         "X86_64_RELOC_UNSIGNED",
2009         "X86_64_RELOC_SIGNED",
2010         "X86_64_RELOC_BRANCH",
2011         "X86_64_RELOC_GOT_LOAD",
2012         "X86_64_RELOC_GOT",
2013         "X86_64_RELOC_SUBTRACTOR",
2014         "X86_64_RELOC_SIGNED_1",
2015         "X86_64_RELOC_SIGNED_2",
2016         "X86_64_RELOC_SIGNED_4",
2017         "X86_64_RELOC_TLV" };
2018 
2019       if (RType > 9)
2020         res = "Unknown";
2021       else
2022         res = Table[RType];
2023       break;
2024     }
2025     case Triple::arm: {
2026       static const char *const Table[] =  {
2027         "ARM_RELOC_VANILLA",
2028         "ARM_RELOC_PAIR",
2029         "ARM_RELOC_SECTDIFF",
2030         "ARM_RELOC_LOCAL_SECTDIFF",
2031         "ARM_RELOC_PB_LA_PTR",
2032         "ARM_RELOC_BR24",
2033         "ARM_THUMB_RELOC_BR22",
2034         "ARM_THUMB_32BIT_BRANCH",
2035         "ARM_RELOC_HALF",
2036         "ARM_RELOC_HALF_SECTDIFF" };
2037 
2038       if (RType > 9)
2039         res = "Unknown";
2040       else
2041         res = Table[RType];
2042       break;
2043     }
2044     case Triple::aarch64: {
2045       static const char *const Table[] = {
2046         "ARM64_RELOC_UNSIGNED",           "ARM64_RELOC_SUBTRACTOR",
2047         "ARM64_RELOC_BRANCH26",           "ARM64_RELOC_PAGE21",
2048         "ARM64_RELOC_PAGEOFF12",          "ARM64_RELOC_GOT_LOAD_PAGE21",
2049         "ARM64_RELOC_GOT_LOAD_PAGEOFF12", "ARM64_RELOC_POINTER_TO_GOT",
2050         "ARM64_RELOC_TLVP_LOAD_PAGE21",   "ARM64_RELOC_TLVP_LOAD_PAGEOFF12",
2051         "ARM64_RELOC_ADDEND"
2052       };
2053 
2054       if (RType >= array_lengthof(Table))
2055         res = "Unknown";
2056       else
2057         res = Table[RType];
2058       break;
2059     }
2060     case Triple::ppc: {
2061       static const char *const Table[] =  {
2062         "PPC_RELOC_VANILLA",
2063         "PPC_RELOC_PAIR",
2064         "PPC_RELOC_BR14",
2065         "PPC_RELOC_BR24",
2066         "PPC_RELOC_HI16",
2067         "PPC_RELOC_LO16",
2068         "PPC_RELOC_HA16",
2069         "PPC_RELOC_LO14",
2070         "PPC_RELOC_SECTDIFF",
2071         "PPC_RELOC_PB_LA_PTR",
2072         "PPC_RELOC_HI16_SECTDIFF",
2073         "PPC_RELOC_LO16_SECTDIFF",
2074         "PPC_RELOC_HA16_SECTDIFF",
2075         "PPC_RELOC_JBSR",
2076         "PPC_RELOC_LO14_SECTDIFF",
2077         "PPC_RELOC_LOCAL_SECTDIFF" };
2078 
2079       if (RType > 15)
2080         res = "Unknown";
2081       else
2082         res = Table[RType];
2083       break;
2084     }
2085     case Triple::UnknownArch:
2086       res = "Unknown";
2087       break;
2088   }
2089   Result.append(res.begin(), res.end());
2090 }
2091 
2092 uint8_t MachOObjectFile::getRelocationLength(DataRefImpl Rel) const {
2093   MachO::any_relocation_info RE = getRelocation(Rel);
2094   return getAnyRelocationLength(RE);
2095 }
2096 
2097 //
2098 // guessLibraryShortName() is passed a name of a dynamic library and returns a
2099 // guess on what the short name is.  Then name is returned as a substring of the
2100 // StringRef Name passed in.  The name of the dynamic library is recognized as
2101 // a framework if it has one of the two following forms:
2102 //      Foo.framework/Versions/A/Foo
2103 //      Foo.framework/Foo
2104 // Where A and Foo can be any string.  And may contain a trailing suffix
2105 // starting with an underbar.  If the Name is recognized as a framework then
2106 // isFramework is set to true else it is set to false.  If the Name has a
2107 // suffix then Suffix is set to the substring in Name that contains the suffix
2108 // else it is set to a NULL StringRef.
2109 //
2110 // The Name of the dynamic library is recognized as a library name if it has
2111 // one of the two following forms:
2112 //      libFoo.A.dylib
2113 //      libFoo.dylib
2114 // The library may have a suffix trailing the name Foo of the form:
2115 //      libFoo_profile.A.dylib
2116 //      libFoo_profile.dylib
2117 //
2118 // The Name of the dynamic library is also recognized as a library name if it
2119 // has the following form:
2120 //      Foo.qtx
2121 //
2122 // If the Name of the dynamic library is none of the forms above then a NULL
2123 // StringRef is returned.
2124 //
2125 StringRef MachOObjectFile::guessLibraryShortName(StringRef Name,
2126                                                  bool &isFramework,
2127                                                  StringRef &Suffix) {
2128   StringRef Foo, F, DotFramework, V, Dylib, Lib, Dot, Qtx;
2129   size_t a, b, c, d, Idx;
2130 
2131   isFramework = false;
2132   Suffix = StringRef();
2133 
2134   // Pull off the last component and make Foo point to it
2135   a = Name.rfind('/');
2136   if (a == Name.npos || a == 0)
2137     goto guess_library;
2138   Foo = Name.slice(a+1, Name.npos);
2139 
2140   // Look for a suffix starting with a '_'
2141   Idx = Foo.rfind('_');
2142   if (Idx != Foo.npos && Foo.size() >= 2) {
2143     Suffix = Foo.slice(Idx, Foo.npos);
2144     Foo = Foo.slice(0, Idx);
2145   }
2146 
2147   // First look for the form Foo.framework/Foo
2148   b = Name.rfind('/', a);
2149   if (b == Name.npos)
2150     Idx = 0;
2151   else
2152     Idx = b+1;
2153   F = Name.slice(Idx, Idx + Foo.size());
2154   DotFramework = Name.slice(Idx + Foo.size(),
2155                             Idx + Foo.size() + sizeof(".framework/")-1);
2156   if (F == Foo && DotFramework == ".framework/") {
2157     isFramework = true;
2158     return Foo;
2159   }
2160 
2161   // Next look for the form Foo.framework/Versions/A/Foo
2162   if (b == Name.npos)
2163     goto guess_library;
2164   c =  Name.rfind('/', b);
2165   if (c == Name.npos || c == 0)
2166     goto guess_library;
2167   V = Name.slice(c+1, Name.npos);
2168   if (!V.startswith("Versions/"))
2169     goto guess_library;
2170   d =  Name.rfind('/', c);
2171   if (d == Name.npos)
2172     Idx = 0;
2173   else
2174     Idx = d+1;
2175   F = Name.slice(Idx, Idx + Foo.size());
2176   DotFramework = Name.slice(Idx + Foo.size(),
2177                             Idx + Foo.size() + sizeof(".framework/")-1);
2178   if (F == Foo && DotFramework == ".framework/") {
2179     isFramework = true;
2180     return Foo;
2181   }
2182 
2183 guess_library:
2184   // pull off the suffix after the "." and make a point to it
2185   a = Name.rfind('.');
2186   if (a == Name.npos || a == 0)
2187     return StringRef();
2188   Dylib = Name.slice(a, Name.npos);
2189   if (Dylib != ".dylib")
2190     goto guess_qtx;
2191 
2192   // First pull off the version letter for the form Foo.A.dylib if any.
2193   if (a >= 3) {
2194     Dot = Name.slice(a-2, a-1);
2195     if (Dot == ".")
2196       a = a - 2;
2197   }
2198 
2199   b = Name.rfind('/', a);
2200   if (b == Name.npos)
2201     b = 0;
2202   else
2203     b = b+1;
2204   // ignore any suffix after an underbar like Foo_profile.A.dylib
2205   Idx = Name.find('_', b);
2206   if (Idx != Name.npos && Idx != b) {
2207     Lib = Name.slice(b, Idx);
2208     Suffix = Name.slice(Idx, a);
2209   }
2210   else
2211     Lib = Name.slice(b, a);
2212   // There are incorrect library names of the form:
2213   // libATS.A_profile.dylib so check for these.
2214   if (Lib.size() >= 3) {
2215     Dot = Lib.slice(Lib.size()-2, Lib.size()-1);
2216     if (Dot == ".")
2217       Lib = Lib.slice(0, Lib.size()-2);
2218   }
2219   return Lib;
2220 
2221 guess_qtx:
2222   Qtx = Name.slice(a, Name.npos);
2223   if (Qtx != ".qtx")
2224     return StringRef();
2225   b = Name.rfind('/', a);
2226   if (b == Name.npos)
2227     Lib = Name.slice(0, a);
2228   else
2229     Lib = Name.slice(b+1, a);
2230   // There are library names of the form: QT.A.qtx so check for these.
2231   if (Lib.size() >= 3) {
2232     Dot = Lib.slice(Lib.size()-2, Lib.size()-1);
2233     if (Dot == ".")
2234       Lib = Lib.slice(0, Lib.size()-2);
2235   }
2236   return Lib;
2237 }
2238 
2239 // getLibraryShortNameByIndex() is used to get the short name of the library
2240 // for an undefined symbol in a linked Mach-O binary that was linked with the
2241 // normal two-level namespace default (that is MH_TWOLEVEL in the header).
2242 // It is passed the index (0 - based) of the library as translated from
2243 // GET_LIBRARY_ORDINAL (1 - based).
2244 std::error_code MachOObjectFile::getLibraryShortNameByIndex(unsigned Index,
2245                                                          StringRef &Res) const {
2246   if (Index >= Libraries.size())
2247     return object_error::parse_failed;
2248 
2249   // If the cache of LibrariesShortNames is not built up do that first for
2250   // all the Libraries.
2251   if (LibrariesShortNames.size() == 0) {
2252     for (unsigned i = 0; i < Libraries.size(); i++) {
2253       MachO::dylib_command D =
2254         getStruct<MachO::dylib_command>(*this, Libraries[i]);
2255       if (D.dylib.name >= D.cmdsize)
2256         return object_error::parse_failed;
2257       const char *P = (const char *)(Libraries[i]) + D.dylib.name;
2258       StringRef Name = StringRef(P);
2259       if (D.dylib.name+Name.size() >= D.cmdsize)
2260         return object_error::parse_failed;
2261       StringRef Suffix;
2262       bool isFramework;
2263       StringRef shortName = guessLibraryShortName(Name, isFramework, Suffix);
2264       if (shortName.empty())
2265         LibrariesShortNames.push_back(Name);
2266       else
2267         LibrariesShortNames.push_back(shortName);
2268     }
2269   }
2270 
2271   Res = LibrariesShortNames[Index];
2272   return std::error_code();
2273 }
2274 
2275 section_iterator
2276 MachOObjectFile::getRelocationRelocatedSection(relocation_iterator Rel) const {
2277   DataRefImpl Sec;
2278   Sec.d.a = Rel->getRawDataRefImpl().d.a;
2279   return section_iterator(SectionRef(Sec, this));
2280 }
2281 
2282 basic_symbol_iterator MachOObjectFile::symbol_begin() const {
2283   DataRefImpl DRI;
2284   MachO::symtab_command Symtab = getSymtabLoadCommand();
2285   if (!SymtabLoadCmd || Symtab.nsyms == 0)
2286     return basic_symbol_iterator(SymbolRef(DRI, this));
2287 
2288   return getSymbolByIndex(0);
2289 }
2290 
2291 basic_symbol_iterator MachOObjectFile::symbol_end() const {
2292   DataRefImpl DRI;
2293   MachO::symtab_command Symtab = getSymtabLoadCommand();
2294   if (!SymtabLoadCmd || Symtab.nsyms == 0)
2295     return basic_symbol_iterator(SymbolRef(DRI, this));
2296 
2297   unsigned SymbolTableEntrySize = is64Bit() ?
2298     sizeof(MachO::nlist_64) :
2299     sizeof(MachO::nlist);
2300   unsigned Offset = Symtab.symoff +
2301     Symtab.nsyms * SymbolTableEntrySize;
2302   DRI.p = reinterpret_cast<uintptr_t>(getPtr(*this, Offset));
2303   return basic_symbol_iterator(SymbolRef(DRI, this));
2304 }
2305 
2306 basic_symbol_iterator MachOObjectFile::getSymbolByIndex(unsigned Index) const {
2307   MachO::symtab_command Symtab = getSymtabLoadCommand();
2308   if (!SymtabLoadCmd || Index >= Symtab.nsyms)
2309     report_fatal_error("Requested symbol index is out of range.");
2310   unsigned SymbolTableEntrySize =
2311     is64Bit() ? sizeof(MachO::nlist_64) : sizeof(MachO::nlist);
2312   DataRefImpl DRI;
2313   DRI.p = reinterpret_cast<uintptr_t>(getPtr(*this, Symtab.symoff));
2314   DRI.p += Index * SymbolTableEntrySize;
2315   return basic_symbol_iterator(SymbolRef(DRI, this));
2316 }
2317 
2318 uint64_t MachOObjectFile::getSymbolIndex(DataRefImpl Symb) const {
2319   MachO::symtab_command Symtab = getSymtabLoadCommand();
2320   if (!SymtabLoadCmd)
2321     report_fatal_error("getSymbolIndex() called with no symbol table symbol");
2322   unsigned SymbolTableEntrySize =
2323     is64Bit() ? sizeof(MachO::nlist_64) : sizeof(MachO::nlist);
2324   DataRefImpl DRIstart;
2325   DRIstart.p = reinterpret_cast<uintptr_t>(getPtr(*this, Symtab.symoff));
2326   uint64_t Index = (Symb.p - DRIstart.p) / SymbolTableEntrySize;
2327   return Index;
2328 }
2329 
2330 section_iterator MachOObjectFile::section_begin() const {
2331   DataRefImpl DRI;
2332   return section_iterator(SectionRef(DRI, this));
2333 }
2334 
2335 section_iterator MachOObjectFile::section_end() const {
2336   DataRefImpl DRI;
2337   DRI.d.a = Sections.size();
2338   return section_iterator(SectionRef(DRI, this));
2339 }
2340 
2341 uint8_t MachOObjectFile::getBytesInAddress() const {
2342   return is64Bit() ? 8 : 4;
2343 }
2344 
2345 StringRef MachOObjectFile::getFileFormatName() const {
2346   unsigned CPUType = getCPUType(*this);
2347   if (!is64Bit()) {
2348     switch (CPUType) {
2349     case llvm::MachO::CPU_TYPE_I386:
2350       return "Mach-O 32-bit i386";
2351     case llvm::MachO::CPU_TYPE_ARM:
2352       return "Mach-O arm";
2353     case llvm::MachO::CPU_TYPE_POWERPC:
2354       return "Mach-O 32-bit ppc";
2355     default:
2356       return "Mach-O 32-bit unknown";
2357     }
2358   }
2359 
2360   switch (CPUType) {
2361   case llvm::MachO::CPU_TYPE_X86_64:
2362     return "Mach-O 64-bit x86-64";
2363   case llvm::MachO::CPU_TYPE_ARM64:
2364     return "Mach-O arm64";
2365   case llvm::MachO::CPU_TYPE_POWERPC64:
2366     return "Mach-O 64-bit ppc64";
2367   default:
2368     return "Mach-O 64-bit unknown";
2369   }
2370 }
2371 
2372 Triple::ArchType MachOObjectFile::getArch(uint32_t CPUType) {
2373   switch (CPUType) {
2374   case llvm::MachO::CPU_TYPE_I386:
2375     return Triple::x86;
2376   case llvm::MachO::CPU_TYPE_X86_64:
2377     return Triple::x86_64;
2378   case llvm::MachO::CPU_TYPE_ARM:
2379     return Triple::arm;
2380   case llvm::MachO::CPU_TYPE_ARM64:
2381     return Triple::aarch64;
2382   case llvm::MachO::CPU_TYPE_POWERPC:
2383     return Triple::ppc;
2384   case llvm::MachO::CPU_TYPE_POWERPC64:
2385     return Triple::ppc64;
2386   default:
2387     return Triple::UnknownArch;
2388   }
2389 }
2390 
2391 Triple MachOObjectFile::getArchTriple(uint32_t CPUType, uint32_t CPUSubType,
2392                                       const char **McpuDefault,
2393                                       const char **ArchFlag) {
2394   if (McpuDefault)
2395     *McpuDefault = nullptr;
2396   if (ArchFlag)
2397     *ArchFlag = nullptr;
2398 
2399   switch (CPUType) {
2400   case MachO::CPU_TYPE_I386:
2401     switch (CPUSubType & ~MachO::CPU_SUBTYPE_MASK) {
2402     case MachO::CPU_SUBTYPE_I386_ALL:
2403       if (ArchFlag)
2404         *ArchFlag = "i386";
2405       return Triple("i386-apple-darwin");
2406     default:
2407       return Triple();
2408     }
2409   case MachO::CPU_TYPE_X86_64:
2410     switch (CPUSubType & ~MachO::CPU_SUBTYPE_MASK) {
2411     case MachO::CPU_SUBTYPE_X86_64_ALL:
2412       if (ArchFlag)
2413         *ArchFlag = "x86_64";
2414       return Triple("x86_64-apple-darwin");
2415     case MachO::CPU_SUBTYPE_X86_64_H:
2416       if (ArchFlag)
2417         *ArchFlag = "x86_64h";
2418       return Triple("x86_64h-apple-darwin");
2419     default:
2420       return Triple();
2421     }
2422   case MachO::CPU_TYPE_ARM:
2423     switch (CPUSubType & ~MachO::CPU_SUBTYPE_MASK) {
2424     case MachO::CPU_SUBTYPE_ARM_V4T:
2425       if (ArchFlag)
2426         *ArchFlag = "armv4t";
2427       return Triple("armv4t-apple-darwin");
2428     case MachO::CPU_SUBTYPE_ARM_V5TEJ:
2429       if (ArchFlag)
2430         *ArchFlag = "armv5e";
2431       return Triple("armv5e-apple-darwin");
2432     case MachO::CPU_SUBTYPE_ARM_XSCALE:
2433       if (ArchFlag)
2434         *ArchFlag = "xscale";
2435       return Triple("xscale-apple-darwin");
2436     case MachO::CPU_SUBTYPE_ARM_V6:
2437       if (ArchFlag)
2438         *ArchFlag = "armv6";
2439       return Triple("armv6-apple-darwin");
2440     case MachO::CPU_SUBTYPE_ARM_V6M:
2441       if (McpuDefault)
2442         *McpuDefault = "cortex-m0";
2443       if (ArchFlag)
2444         *ArchFlag = "armv6m";
2445       return Triple("armv6m-apple-darwin");
2446     case MachO::CPU_SUBTYPE_ARM_V7:
2447       if (ArchFlag)
2448         *ArchFlag = "armv7";
2449       return Triple("armv7-apple-darwin");
2450     case MachO::CPU_SUBTYPE_ARM_V7EM:
2451       if (McpuDefault)
2452         *McpuDefault = "cortex-m4";
2453       if (ArchFlag)
2454         *ArchFlag = "armv7em";
2455       return Triple("thumbv7em-apple-darwin");
2456     case MachO::CPU_SUBTYPE_ARM_V7K:
2457       if (McpuDefault)
2458         *McpuDefault = "cortex-a7";
2459       if (ArchFlag)
2460         *ArchFlag = "armv7k";
2461       return Triple("armv7k-apple-darwin");
2462     case MachO::CPU_SUBTYPE_ARM_V7M:
2463       if (McpuDefault)
2464         *McpuDefault = "cortex-m3";
2465       if (ArchFlag)
2466         *ArchFlag = "armv7m";
2467       return Triple("thumbv7m-apple-darwin");
2468     case MachO::CPU_SUBTYPE_ARM_V7S:
2469       if (McpuDefault)
2470         *McpuDefault = "cortex-a7";
2471       if (ArchFlag)
2472         *ArchFlag = "armv7s";
2473       return Triple("armv7s-apple-darwin");
2474     default:
2475       return Triple();
2476     }
2477   case MachO::CPU_TYPE_ARM64:
2478     switch (CPUSubType & ~MachO::CPU_SUBTYPE_MASK) {
2479     case MachO::CPU_SUBTYPE_ARM64_ALL:
2480       if (ArchFlag)
2481         *ArchFlag = "arm64";
2482       return Triple("arm64-apple-darwin");
2483     default:
2484       return Triple();
2485     }
2486   case MachO::CPU_TYPE_POWERPC:
2487     switch (CPUSubType & ~MachO::CPU_SUBTYPE_MASK) {
2488     case MachO::CPU_SUBTYPE_POWERPC_ALL:
2489       if (ArchFlag)
2490         *ArchFlag = "ppc";
2491       return Triple("ppc-apple-darwin");
2492     default:
2493       return Triple();
2494     }
2495   case MachO::CPU_TYPE_POWERPC64:
2496     switch (CPUSubType & ~MachO::CPU_SUBTYPE_MASK) {
2497     case MachO::CPU_SUBTYPE_POWERPC_ALL:
2498       if (ArchFlag)
2499         *ArchFlag = "ppc64";
2500       return Triple("ppc64-apple-darwin");
2501     default:
2502       return Triple();
2503     }
2504   default:
2505     return Triple();
2506   }
2507 }
2508 
2509 Triple MachOObjectFile::getHostArch() {
2510   return Triple(sys::getDefaultTargetTriple());
2511 }
2512 
2513 bool MachOObjectFile::isValidArch(StringRef ArchFlag) {
2514   return StringSwitch<bool>(ArchFlag)
2515       .Case("i386", true)
2516       .Case("x86_64", true)
2517       .Case("x86_64h", true)
2518       .Case("armv4t", true)
2519       .Case("arm", true)
2520       .Case("armv5e", true)
2521       .Case("armv6", true)
2522       .Case("armv6m", true)
2523       .Case("armv7", true)
2524       .Case("armv7em", true)
2525       .Case("armv7k", true)
2526       .Case("armv7m", true)
2527       .Case("armv7s", true)
2528       .Case("arm64", true)
2529       .Case("ppc", true)
2530       .Case("ppc64", true)
2531       .Default(false);
2532 }
2533 
2534 unsigned MachOObjectFile::getArch() const {
2535   return getArch(getCPUType(*this));
2536 }
2537 
2538 Triple MachOObjectFile::getArchTriple(const char **McpuDefault) const {
2539   return getArchTriple(Header.cputype, Header.cpusubtype, McpuDefault);
2540 }
2541 
2542 relocation_iterator MachOObjectFile::section_rel_begin(unsigned Index) const {
2543   DataRefImpl DRI;
2544   DRI.d.a = Index;
2545   return section_rel_begin(DRI);
2546 }
2547 
2548 relocation_iterator MachOObjectFile::section_rel_end(unsigned Index) const {
2549   DataRefImpl DRI;
2550   DRI.d.a = Index;
2551   return section_rel_end(DRI);
2552 }
2553 
2554 dice_iterator MachOObjectFile::begin_dices() const {
2555   DataRefImpl DRI;
2556   if (!DataInCodeLoadCmd)
2557     return dice_iterator(DiceRef(DRI, this));
2558 
2559   MachO::linkedit_data_command DicLC = getDataInCodeLoadCommand();
2560   DRI.p = reinterpret_cast<uintptr_t>(getPtr(*this, DicLC.dataoff));
2561   return dice_iterator(DiceRef(DRI, this));
2562 }
2563 
2564 dice_iterator MachOObjectFile::end_dices() const {
2565   DataRefImpl DRI;
2566   if (!DataInCodeLoadCmd)
2567     return dice_iterator(DiceRef(DRI, this));
2568 
2569   MachO::linkedit_data_command DicLC = getDataInCodeLoadCommand();
2570   unsigned Offset = DicLC.dataoff + DicLC.datasize;
2571   DRI.p = reinterpret_cast<uintptr_t>(getPtr(*this, Offset));
2572   return dice_iterator(DiceRef(DRI, this));
2573 }
2574 
2575 ExportEntry::ExportEntry(ArrayRef<uint8_t> T)
2576     : Trie(T), Malformed(false), Done(false) {}
2577 
2578 void ExportEntry::moveToFirst() {
2579   pushNode(0);
2580   pushDownUntilBottom();
2581 }
2582 
2583 void ExportEntry::moveToEnd() {
2584   Stack.clear();
2585   Done = true;
2586 }
2587 
2588 bool ExportEntry::operator==(const ExportEntry &Other) const {
2589   // Common case, one at end, other iterating from begin.
2590   if (Done || Other.Done)
2591     return (Done == Other.Done);
2592   // Not equal if different stack sizes.
2593   if (Stack.size() != Other.Stack.size())
2594     return false;
2595   // Not equal if different cumulative strings.
2596   if (!CumulativeString.equals(Other.CumulativeString))
2597     return false;
2598   // Equal if all nodes in both stacks match.
2599   for (unsigned i=0; i < Stack.size(); ++i) {
2600     if (Stack[i].Start != Other.Stack[i].Start)
2601       return false;
2602   }
2603   return true;
2604 }
2605 
2606 uint64_t ExportEntry::readULEB128(const uint8_t *&Ptr) {
2607   unsigned Count;
2608   uint64_t Result = decodeULEB128(Ptr, &Count);
2609   Ptr += Count;
2610   if (Ptr > Trie.end()) {
2611     Ptr = Trie.end();
2612     Malformed = true;
2613   }
2614   return Result;
2615 }
2616 
2617 StringRef ExportEntry::name() const {
2618   return CumulativeString;
2619 }
2620 
2621 uint64_t ExportEntry::flags() const {
2622   return Stack.back().Flags;
2623 }
2624 
2625 uint64_t ExportEntry::address() const {
2626   return Stack.back().Address;
2627 }
2628 
2629 uint64_t ExportEntry::other() const {
2630   return Stack.back().Other;
2631 }
2632 
2633 StringRef ExportEntry::otherName() const {
2634   const char* ImportName = Stack.back().ImportName;
2635   if (ImportName)
2636     return StringRef(ImportName);
2637   return StringRef();
2638 }
2639 
2640 uint32_t ExportEntry::nodeOffset() const {
2641   return Stack.back().Start - Trie.begin();
2642 }
2643 
2644 ExportEntry::NodeState::NodeState(const uint8_t *Ptr)
2645     : Start(Ptr), Current(Ptr), Flags(0), Address(0), Other(0),
2646       ImportName(nullptr), ChildCount(0), NextChildIndex(0),
2647       ParentStringLength(0), IsExportNode(false) {}
2648 
2649 void ExportEntry::pushNode(uint64_t offset) {
2650   const uint8_t *Ptr = Trie.begin() + offset;
2651   NodeState State(Ptr);
2652   uint64_t ExportInfoSize = readULEB128(State.Current);
2653   State.IsExportNode = (ExportInfoSize != 0);
2654   const uint8_t* Children = State.Current + ExportInfoSize;
2655   if (State.IsExportNode) {
2656     State.Flags = readULEB128(State.Current);
2657     if (State.Flags & MachO::EXPORT_SYMBOL_FLAGS_REEXPORT) {
2658       State.Address = 0;
2659       State.Other = readULEB128(State.Current); // dylib ordinal
2660       State.ImportName = reinterpret_cast<const char*>(State.Current);
2661     } else {
2662       State.Address = readULEB128(State.Current);
2663       if (State.Flags & MachO::EXPORT_SYMBOL_FLAGS_STUB_AND_RESOLVER)
2664         State.Other = readULEB128(State.Current);
2665     }
2666   }
2667   State.ChildCount = *Children;
2668   State.Current = Children + 1;
2669   State.NextChildIndex = 0;
2670   State.ParentStringLength = CumulativeString.size();
2671   Stack.push_back(State);
2672 }
2673 
2674 void ExportEntry::pushDownUntilBottom() {
2675   while (Stack.back().NextChildIndex < Stack.back().ChildCount) {
2676     NodeState &Top = Stack.back();
2677     CumulativeString.resize(Top.ParentStringLength);
2678     for (;*Top.Current != 0; Top.Current++) {
2679       char C = *Top.Current;
2680       CumulativeString.push_back(C);
2681     }
2682     Top.Current += 1;
2683     uint64_t childNodeIndex = readULEB128(Top.Current);
2684     Top.NextChildIndex += 1;
2685     pushNode(childNodeIndex);
2686   }
2687   if (!Stack.back().IsExportNode) {
2688     Malformed = true;
2689     moveToEnd();
2690   }
2691 }
2692 
2693 // We have a trie data structure and need a way to walk it that is compatible
2694 // with the C++ iterator model. The solution is a non-recursive depth first
2695 // traversal where the iterator contains a stack of parent nodes along with a
2696 // string that is the accumulation of all edge strings along the parent chain
2697 // to this point.
2698 //
2699 // There is one "export" node for each exported symbol.  But because some
2700 // symbols may be a prefix of another symbol (e.g. _dup and _dup2), an export
2701 // node may have child nodes too.
2702 //
2703 // The algorithm for moveNext() is to keep moving down the leftmost unvisited
2704 // child until hitting a node with no children (which is an export node or
2705 // else the trie is malformed). On the way down, each node is pushed on the
2706 // stack ivar.  If there is no more ways down, it pops up one and tries to go
2707 // down a sibling path until a childless node is reached.
2708 void ExportEntry::moveNext() {
2709   if (Stack.empty() || !Stack.back().IsExportNode) {
2710     Malformed = true;
2711     moveToEnd();
2712     return;
2713   }
2714 
2715   Stack.pop_back();
2716   while (!Stack.empty()) {
2717     NodeState &Top = Stack.back();
2718     if (Top.NextChildIndex < Top.ChildCount) {
2719       pushDownUntilBottom();
2720       // Now at the next export node.
2721       return;
2722     } else {
2723       if (Top.IsExportNode) {
2724         // This node has no children but is itself an export node.
2725         CumulativeString.resize(Top.ParentStringLength);
2726         return;
2727       }
2728       Stack.pop_back();
2729     }
2730   }
2731   Done = true;
2732 }
2733 
2734 iterator_range<export_iterator>
2735 MachOObjectFile::exports(ArrayRef<uint8_t> Trie) {
2736   ExportEntry Start(Trie);
2737   if (Trie.size() == 0)
2738     Start.moveToEnd();
2739   else
2740     Start.moveToFirst();
2741 
2742   ExportEntry Finish(Trie);
2743   Finish.moveToEnd();
2744 
2745   return make_range(export_iterator(Start), export_iterator(Finish));
2746 }
2747 
2748 iterator_range<export_iterator> MachOObjectFile::exports() const {
2749   return exports(getDyldInfoExportsTrie());
2750 }
2751 
2752 MachORebaseEntry::MachORebaseEntry(ArrayRef<uint8_t> Bytes, bool is64Bit)
2753     : Opcodes(Bytes), Ptr(Bytes.begin()), SegmentOffset(0), SegmentIndex(0),
2754       RemainingLoopCount(0), AdvanceAmount(0), RebaseType(0),
2755       PointerSize(is64Bit ? 8 : 4), Malformed(false), Done(false) {}
2756 
2757 void MachORebaseEntry::moveToFirst() {
2758   Ptr = Opcodes.begin();
2759   moveNext();
2760 }
2761 
2762 void MachORebaseEntry::moveToEnd() {
2763   Ptr = Opcodes.end();
2764   RemainingLoopCount = 0;
2765   Done = true;
2766 }
2767 
2768 void MachORebaseEntry::moveNext() {
2769   // If in the middle of some loop, move to next rebasing in loop.
2770   SegmentOffset += AdvanceAmount;
2771   if (RemainingLoopCount) {
2772     --RemainingLoopCount;
2773     return;
2774   }
2775   if (Ptr == Opcodes.end()) {
2776     Done = true;
2777     return;
2778   }
2779   bool More = true;
2780   while (More && !Malformed) {
2781     // Parse next opcode and set up next loop.
2782     uint8_t Byte = *Ptr++;
2783     uint8_t ImmValue = Byte & MachO::REBASE_IMMEDIATE_MASK;
2784     uint8_t Opcode = Byte & MachO::REBASE_OPCODE_MASK;
2785     switch (Opcode) {
2786     case MachO::REBASE_OPCODE_DONE:
2787       More = false;
2788       Done = true;
2789       moveToEnd();
2790       DEBUG_WITH_TYPE("mach-o-rebase", llvm::dbgs() << "REBASE_OPCODE_DONE\n");
2791       break;
2792     case MachO::REBASE_OPCODE_SET_TYPE_IMM:
2793       RebaseType = ImmValue;
2794       DEBUG_WITH_TYPE(
2795           "mach-o-rebase",
2796           llvm::dbgs() << "REBASE_OPCODE_SET_TYPE_IMM: "
2797                        << "RebaseType=" << (int) RebaseType << "\n");
2798       break;
2799     case MachO::REBASE_OPCODE_SET_SEGMENT_AND_OFFSET_ULEB:
2800       SegmentIndex = ImmValue;
2801       SegmentOffset = readULEB128();
2802       DEBUG_WITH_TYPE(
2803           "mach-o-rebase",
2804           llvm::dbgs() << "REBASE_OPCODE_SET_SEGMENT_AND_OFFSET_ULEB: "
2805                        << "SegmentIndex=" << SegmentIndex << ", "
2806                        << format("SegmentOffset=0x%06X", SegmentOffset)
2807                        << "\n");
2808       break;
2809     case MachO::REBASE_OPCODE_ADD_ADDR_ULEB:
2810       SegmentOffset += readULEB128();
2811       DEBUG_WITH_TYPE("mach-o-rebase",
2812                       llvm::dbgs() << "REBASE_OPCODE_ADD_ADDR_ULEB: "
2813                                    << format("SegmentOffset=0x%06X",
2814                                              SegmentOffset) << "\n");
2815       break;
2816     case MachO::REBASE_OPCODE_ADD_ADDR_IMM_SCALED:
2817       SegmentOffset += ImmValue * PointerSize;
2818       DEBUG_WITH_TYPE("mach-o-rebase",
2819                       llvm::dbgs() << "REBASE_OPCODE_ADD_ADDR_IMM_SCALED: "
2820                                    << format("SegmentOffset=0x%06X",
2821                                              SegmentOffset) << "\n");
2822       break;
2823     case MachO::REBASE_OPCODE_DO_REBASE_IMM_TIMES:
2824       AdvanceAmount = PointerSize;
2825       RemainingLoopCount = ImmValue - 1;
2826       DEBUG_WITH_TYPE(
2827           "mach-o-rebase",
2828           llvm::dbgs() << "REBASE_OPCODE_DO_REBASE_IMM_TIMES: "
2829                        << format("SegmentOffset=0x%06X", SegmentOffset)
2830                        << ", AdvanceAmount=" << AdvanceAmount
2831                        << ", RemainingLoopCount=" << RemainingLoopCount
2832                        << "\n");
2833       return;
2834     case MachO::REBASE_OPCODE_DO_REBASE_ULEB_TIMES:
2835       AdvanceAmount = PointerSize;
2836       RemainingLoopCount = readULEB128() - 1;
2837       DEBUG_WITH_TYPE(
2838           "mach-o-rebase",
2839           llvm::dbgs() << "REBASE_OPCODE_DO_REBASE_ULEB_TIMES: "
2840                        << format("SegmentOffset=0x%06X", SegmentOffset)
2841                        << ", AdvanceAmount=" << AdvanceAmount
2842                        << ", RemainingLoopCount=" << RemainingLoopCount
2843                        << "\n");
2844       return;
2845     case MachO::REBASE_OPCODE_DO_REBASE_ADD_ADDR_ULEB:
2846       AdvanceAmount = readULEB128() + PointerSize;
2847       RemainingLoopCount = 0;
2848       DEBUG_WITH_TYPE(
2849           "mach-o-rebase",
2850           llvm::dbgs() << "REBASE_OPCODE_DO_REBASE_ADD_ADDR_ULEB: "
2851                        << format("SegmentOffset=0x%06X", SegmentOffset)
2852                        << ", AdvanceAmount=" << AdvanceAmount
2853                        << ", RemainingLoopCount=" << RemainingLoopCount
2854                        << "\n");
2855       return;
2856     case MachO::REBASE_OPCODE_DO_REBASE_ULEB_TIMES_SKIPPING_ULEB:
2857       RemainingLoopCount = readULEB128() - 1;
2858       AdvanceAmount = readULEB128() + PointerSize;
2859       DEBUG_WITH_TYPE(
2860           "mach-o-rebase",
2861           llvm::dbgs() << "REBASE_OPCODE_DO_REBASE_ULEB_TIMES_SKIPPING_ULEB: "
2862                        << format("SegmentOffset=0x%06X", SegmentOffset)
2863                        << ", AdvanceAmount=" << AdvanceAmount
2864                        << ", RemainingLoopCount=" << RemainingLoopCount
2865                        << "\n");
2866       return;
2867     default:
2868       Malformed = true;
2869     }
2870   }
2871 }
2872 
2873 uint64_t MachORebaseEntry::readULEB128() {
2874   unsigned Count;
2875   uint64_t Result = decodeULEB128(Ptr, &Count);
2876   Ptr += Count;
2877   if (Ptr > Opcodes.end()) {
2878     Ptr = Opcodes.end();
2879     Malformed = true;
2880   }
2881   return Result;
2882 }
2883 
2884 uint32_t MachORebaseEntry::segmentIndex() const { return SegmentIndex; }
2885 
2886 uint64_t MachORebaseEntry::segmentOffset() const { return SegmentOffset; }
2887 
2888 StringRef MachORebaseEntry::typeName() const {
2889   switch (RebaseType) {
2890   case MachO::REBASE_TYPE_POINTER:
2891     return "pointer";
2892   case MachO::REBASE_TYPE_TEXT_ABSOLUTE32:
2893     return "text abs32";
2894   case MachO::REBASE_TYPE_TEXT_PCREL32:
2895     return "text rel32";
2896   }
2897   return "unknown";
2898 }
2899 
2900 bool MachORebaseEntry::operator==(const MachORebaseEntry &Other) const {
2901 #ifdef EXPENSIVE_CHECKS
2902   assert(Opcodes == Other.Opcodes && "compare iterators of different files");
2903 #else
2904   assert(Opcodes.data() == Other.Opcodes.data() && "compare iterators of different files");
2905 #endif
2906   return (Ptr == Other.Ptr) &&
2907          (RemainingLoopCount == Other.RemainingLoopCount) &&
2908          (Done == Other.Done);
2909 }
2910 
2911 iterator_range<rebase_iterator>
2912 MachOObjectFile::rebaseTable(ArrayRef<uint8_t> Opcodes, bool is64) {
2913   MachORebaseEntry Start(Opcodes, is64);
2914   Start.moveToFirst();
2915 
2916   MachORebaseEntry Finish(Opcodes, is64);
2917   Finish.moveToEnd();
2918 
2919   return make_range(rebase_iterator(Start), rebase_iterator(Finish));
2920 }
2921 
2922 iterator_range<rebase_iterator> MachOObjectFile::rebaseTable() const {
2923   return rebaseTable(getDyldInfoRebaseOpcodes(), is64Bit());
2924 }
2925 
2926 MachOBindEntry::MachOBindEntry(ArrayRef<uint8_t> Bytes, bool is64Bit, Kind BK)
2927     : Opcodes(Bytes), Ptr(Bytes.begin()), SegmentOffset(0), SegmentIndex(0),
2928       Ordinal(0), Flags(0), Addend(0), RemainingLoopCount(0), AdvanceAmount(0),
2929       BindType(0), PointerSize(is64Bit ? 8 : 4),
2930       TableKind(BK), Malformed(false), Done(false) {}
2931 
2932 void MachOBindEntry::moveToFirst() {
2933   Ptr = Opcodes.begin();
2934   moveNext();
2935 }
2936 
2937 void MachOBindEntry::moveToEnd() {
2938   Ptr = Opcodes.end();
2939   RemainingLoopCount = 0;
2940   Done = true;
2941 }
2942 
2943 void MachOBindEntry::moveNext() {
2944   // If in the middle of some loop, move to next binding in loop.
2945   SegmentOffset += AdvanceAmount;
2946   if (RemainingLoopCount) {
2947     --RemainingLoopCount;
2948     return;
2949   }
2950   if (Ptr == Opcodes.end()) {
2951     Done = true;
2952     return;
2953   }
2954   bool More = true;
2955   while (More && !Malformed) {
2956     // Parse next opcode and set up next loop.
2957     uint8_t Byte = *Ptr++;
2958     uint8_t ImmValue = Byte & MachO::BIND_IMMEDIATE_MASK;
2959     uint8_t Opcode = Byte & MachO::BIND_OPCODE_MASK;
2960     int8_t SignExtended;
2961     const uint8_t *SymStart;
2962     switch (Opcode) {
2963     case MachO::BIND_OPCODE_DONE:
2964       if (TableKind == Kind::Lazy) {
2965         // Lazying bindings have a DONE opcode between entries.  Need to ignore
2966         // it to advance to next entry.  But need not if this is last entry.
2967         bool NotLastEntry = false;
2968         for (const uint8_t *P = Ptr; P < Opcodes.end(); ++P) {
2969           if (*P) {
2970             NotLastEntry = true;
2971           }
2972         }
2973         if (NotLastEntry)
2974           break;
2975       }
2976       More = false;
2977       Done = true;
2978       moveToEnd();
2979       DEBUG_WITH_TYPE("mach-o-bind", llvm::dbgs() << "BIND_OPCODE_DONE\n");
2980       break;
2981     case MachO::BIND_OPCODE_SET_DYLIB_ORDINAL_IMM:
2982       Ordinal = ImmValue;
2983       DEBUG_WITH_TYPE(
2984           "mach-o-bind",
2985           llvm::dbgs() << "BIND_OPCODE_SET_DYLIB_ORDINAL_IMM: "
2986                        << "Ordinal=" << Ordinal << "\n");
2987       break;
2988     case MachO::BIND_OPCODE_SET_DYLIB_ORDINAL_ULEB:
2989       Ordinal = readULEB128();
2990       DEBUG_WITH_TYPE(
2991           "mach-o-bind",
2992           llvm::dbgs() << "BIND_OPCODE_SET_DYLIB_ORDINAL_ULEB: "
2993                        << "Ordinal=" << Ordinal << "\n");
2994       break;
2995     case MachO::BIND_OPCODE_SET_DYLIB_SPECIAL_IMM:
2996       if (ImmValue) {
2997         SignExtended = MachO::BIND_OPCODE_MASK | ImmValue;
2998         Ordinal = SignExtended;
2999       } else
3000         Ordinal = 0;
3001       DEBUG_WITH_TYPE(
3002           "mach-o-bind",
3003           llvm::dbgs() << "BIND_OPCODE_SET_DYLIB_SPECIAL_IMM: "
3004                        << "Ordinal=" << Ordinal << "\n");
3005       break;
3006     case MachO::BIND_OPCODE_SET_SYMBOL_TRAILING_FLAGS_IMM:
3007       Flags = ImmValue;
3008       SymStart = Ptr;
3009       while (*Ptr) {
3010         ++Ptr;
3011       }
3012       SymbolName = StringRef(reinterpret_cast<const char*>(SymStart),
3013                              Ptr-SymStart);
3014       ++Ptr;
3015       DEBUG_WITH_TYPE(
3016           "mach-o-bind",
3017           llvm::dbgs() << "BIND_OPCODE_SET_SYMBOL_TRAILING_FLAGS_IMM: "
3018                        << "SymbolName=" << SymbolName << "\n");
3019       if (TableKind == Kind::Weak) {
3020         if (ImmValue & MachO::BIND_SYMBOL_FLAGS_NON_WEAK_DEFINITION)
3021           return;
3022       }
3023       break;
3024     case MachO::BIND_OPCODE_SET_TYPE_IMM:
3025       BindType = ImmValue;
3026       DEBUG_WITH_TYPE(
3027           "mach-o-bind",
3028           llvm::dbgs() << "BIND_OPCODE_SET_TYPE_IMM: "
3029                        << "BindType=" << (int)BindType << "\n");
3030       break;
3031     case MachO::BIND_OPCODE_SET_ADDEND_SLEB:
3032       Addend = readSLEB128();
3033       if (TableKind == Kind::Lazy)
3034         Malformed = true;
3035       DEBUG_WITH_TYPE(
3036           "mach-o-bind",
3037           llvm::dbgs() << "BIND_OPCODE_SET_ADDEND_SLEB: "
3038                        << "Addend=" << Addend << "\n");
3039       break;
3040     case MachO::BIND_OPCODE_SET_SEGMENT_AND_OFFSET_ULEB:
3041       SegmentIndex = ImmValue;
3042       SegmentOffset = readULEB128();
3043       DEBUG_WITH_TYPE(
3044           "mach-o-bind",
3045           llvm::dbgs() << "BIND_OPCODE_SET_SEGMENT_AND_OFFSET_ULEB: "
3046                        << "SegmentIndex=" << SegmentIndex << ", "
3047                        << format("SegmentOffset=0x%06X", SegmentOffset)
3048                        << "\n");
3049       break;
3050     case MachO::BIND_OPCODE_ADD_ADDR_ULEB:
3051       SegmentOffset += readULEB128();
3052       DEBUG_WITH_TYPE("mach-o-bind",
3053                       llvm::dbgs() << "BIND_OPCODE_ADD_ADDR_ULEB: "
3054                                    << format("SegmentOffset=0x%06X",
3055                                              SegmentOffset) << "\n");
3056       break;
3057     case MachO::BIND_OPCODE_DO_BIND:
3058       AdvanceAmount = PointerSize;
3059       RemainingLoopCount = 0;
3060       DEBUG_WITH_TYPE("mach-o-bind",
3061                       llvm::dbgs() << "BIND_OPCODE_DO_BIND: "
3062                                    << format("SegmentOffset=0x%06X",
3063                                              SegmentOffset) << "\n");
3064       return;
3065      case MachO::BIND_OPCODE_DO_BIND_ADD_ADDR_ULEB:
3066       AdvanceAmount = readULEB128() + PointerSize;
3067       RemainingLoopCount = 0;
3068       if (TableKind == Kind::Lazy)
3069         Malformed = true;
3070       DEBUG_WITH_TYPE(
3071           "mach-o-bind",
3072           llvm::dbgs() << "BIND_OPCODE_DO_BIND_ADD_ADDR_ULEB: "
3073                        << format("SegmentOffset=0x%06X", SegmentOffset)
3074                        << ", AdvanceAmount=" << AdvanceAmount
3075                        << ", RemainingLoopCount=" << RemainingLoopCount
3076                        << "\n");
3077       return;
3078     case MachO::BIND_OPCODE_DO_BIND_ADD_ADDR_IMM_SCALED:
3079       AdvanceAmount = ImmValue * PointerSize + PointerSize;
3080       RemainingLoopCount = 0;
3081       if (TableKind == Kind::Lazy)
3082         Malformed = true;
3083       DEBUG_WITH_TYPE("mach-o-bind",
3084                       llvm::dbgs()
3085                       << "BIND_OPCODE_DO_BIND_ADD_ADDR_IMM_SCALED: "
3086                       << format("SegmentOffset=0x%06X",
3087                                              SegmentOffset) << "\n");
3088       return;
3089     case MachO::BIND_OPCODE_DO_BIND_ULEB_TIMES_SKIPPING_ULEB:
3090       RemainingLoopCount = readULEB128() - 1;
3091       AdvanceAmount = readULEB128() + PointerSize;
3092       if (TableKind == Kind::Lazy)
3093         Malformed = true;
3094       DEBUG_WITH_TYPE(
3095           "mach-o-bind",
3096           llvm::dbgs() << "BIND_OPCODE_DO_BIND_ULEB_TIMES_SKIPPING_ULEB: "
3097                        << format("SegmentOffset=0x%06X", SegmentOffset)
3098                        << ", AdvanceAmount=" << AdvanceAmount
3099                        << ", RemainingLoopCount=" << RemainingLoopCount
3100                        << "\n");
3101       return;
3102     default:
3103       Malformed = true;
3104     }
3105   }
3106 }
3107 
3108 uint64_t MachOBindEntry::readULEB128() {
3109   unsigned Count;
3110   uint64_t Result = decodeULEB128(Ptr, &Count);
3111   Ptr += Count;
3112   if (Ptr > Opcodes.end()) {
3113     Ptr = Opcodes.end();
3114     Malformed = true;
3115   }
3116   return Result;
3117 }
3118 
3119 int64_t MachOBindEntry::readSLEB128() {
3120   unsigned Count;
3121   int64_t Result = decodeSLEB128(Ptr, &Count);
3122   Ptr += Count;
3123   if (Ptr > Opcodes.end()) {
3124     Ptr = Opcodes.end();
3125     Malformed = true;
3126   }
3127   return Result;
3128 }
3129 
3130 uint32_t MachOBindEntry::segmentIndex() const { return SegmentIndex; }
3131 
3132 uint64_t MachOBindEntry::segmentOffset() const { return SegmentOffset; }
3133 
3134 StringRef MachOBindEntry::typeName() const {
3135   switch (BindType) {
3136   case MachO::BIND_TYPE_POINTER:
3137     return "pointer";
3138   case MachO::BIND_TYPE_TEXT_ABSOLUTE32:
3139     return "text abs32";
3140   case MachO::BIND_TYPE_TEXT_PCREL32:
3141     return "text rel32";
3142   }
3143   return "unknown";
3144 }
3145 
3146 StringRef MachOBindEntry::symbolName() const { return SymbolName; }
3147 
3148 int64_t MachOBindEntry::addend() const { return Addend; }
3149 
3150 uint32_t MachOBindEntry::flags() const { return Flags; }
3151 
3152 int MachOBindEntry::ordinal() const { return Ordinal; }
3153 
3154 bool MachOBindEntry::operator==(const MachOBindEntry &Other) const {
3155 #ifdef EXPENSIVE_CHECKS
3156   assert(Opcodes == Other.Opcodes && "compare iterators of different files");
3157 #else
3158   assert(Opcodes.data() == Other.Opcodes.data() && "compare iterators of different files");
3159 #endif
3160   return (Ptr == Other.Ptr) &&
3161          (RemainingLoopCount == Other.RemainingLoopCount) &&
3162          (Done == Other.Done);
3163 }
3164 
3165 iterator_range<bind_iterator>
3166 MachOObjectFile::bindTable(ArrayRef<uint8_t> Opcodes, bool is64,
3167                            MachOBindEntry::Kind BKind) {
3168   MachOBindEntry Start(Opcodes, is64, BKind);
3169   Start.moveToFirst();
3170 
3171   MachOBindEntry Finish(Opcodes, is64, BKind);
3172   Finish.moveToEnd();
3173 
3174   return make_range(bind_iterator(Start), bind_iterator(Finish));
3175 }
3176 
3177 iterator_range<bind_iterator> MachOObjectFile::bindTable() const {
3178   return bindTable(getDyldInfoBindOpcodes(), is64Bit(),
3179                    MachOBindEntry::Kind::Regular);
3180 }
3181 
3182 iterator_range<bind_iterator> MachOObjectFile::lazyBindTable() const {
3183   return bindTable(getDyldInfoLazyBindOpcodes(), is64Bit(),
3184                    MachOBindEntry::Kind::Lazy);
3185 }
3186 
3187 iterator_range<bind_iterator> MachOObjectFile::weakBindTable() const {
3188   return bindTable(getDyldInfoWeakBindOpcodes(), is64Bit(),
3189                    MachOBindEntry::Kind::Weak);
3190 }
3191 
3192 MachOObjectFile::load_command_iterator
3193 MachOObjectFile::begin_load_commands() const {
3194   return LoadCommands.begin();
3195 }
3196 
3197 MachOObjectFile::load_command_iterator
3198 MachOObjectFile::end_load_commands() const {
3199   return LoadCommands.end();
3200 }
3201 
3202 iterator_range<MachOObjectFile::load_command_iterator>
3203 MachOObjectFile::load_commands() const {
3204   return make_range(begin_load_commands(), end_load_commands());
3205 }
3206 
3207 StringRef
3208 MachOObjectFile::getSectionFinalSegmentName(DataRefImpl Sec) const {
3209   ArrayRef<char> Raw = getSectionRawFinalSegmentName(Sec);
3210   return parseSegmentOrSectionName(Raw.data());
3211 }
3212 
3213 ArrayRef<char>
3214 MachOObjectFile::getSectionRawName(DataRefImpl Sec) const {
3215   assert(Sec.d.a < Sections.size() && "Should have detected this earlier");
3216   const section_base *Base =
3217     reinterpret_cast<const section_base *>(Sections[Sec.d.a]);
3218   return makeArrayRef(Base->sectname);
3219 }
3220 
3221 ArrayRef<char>
3222 MachOObjectFile::getSectionRawFinalSegmentName(DataRefImpl Sec) const {
3223   assert(Sec.d.a < Sections.size() && "Should have detected this earlier");
3224   const section_base *Base =
3225     reinterpret_cast<const section_base *>(Sections[Sec.d.a]);
3226   return makeArrayRef(Base->segname);
3227 }
3228 
3229 bool
3230 MachOObjectFile::isRelocationScattered(const MachO::any_relocation_info &RE)
3231   const {
3232   if (getCPUType(*this) == MachO::CPU_TYPE_X86_64)
3233     return false;
3234   return getPlainRelocationAddress(RE) & MachO::R_SCATTERED;
3235 }
3236 
3237 unsigned MachOObjectFile::getPlainRelocationSymbolNum(
3238     const MachO::any_relocation_info &RE) const {
3239   if (isLittleEndian())
3240     return RE.r_word1 & 0xffffff;
3241   return RE.r_word1 >> 8;
3242 }
3243 
3244 bool MachOObjectFile::getPlainRelocationExternal(
3245     const MachO::any_relocation_info &RE) const {
3246   if (isLittleEndian())
3247     return (RE.r_word1 >> 27) & 1;
3248   return (RE.r_word1 >> 4) & 1;
3249 }
3250 
3251 bool MachOObjectFile::getScatteredRelocationScattered(
3252     const MachO::any_relocation_info &RE) const {
3253   return RE.r_word0 >> 31;
3254 }
3255 
3256 uint32_t MachOObjectFile::getScatteredRelocationValue(
3257     const MachO::any_relocation_info &RE) const {
3258   return RE.r_word1;
3259 }
3260 
3261 uint32_t MachOObjectFile::getScatteredRelocationType(
3262     const MachO::any_relocation_info &RE) const {
3263   return (RE.r_word0 >> 24) & 0xf;
3264 }
3265 
3266 unsigned MachOObjectFile::getAnyRelocationAddress(
3267     const MachO::any_relocation_info &RE) const {
3268   if (isRelocationScattered(RE))
3269     return getScatteredRelocationAddress(RE);
3270   return getPlainRelocationAddress(RE);
3271 }
3272 
3273 unsigned MachOObjectFile::getAnyRelocationPCRel(
3274     const MachO::any_relocation_info &RE) const {
3275   if (isRelocationScattered(RE))
3276     return getScatteredRelocationPCRel(RE);
3277   return getPlainRelocationPCRel(*this, RE);
3278 }
3279 
3280 unsigned MachOObjectFile::getAnyRelocationLength(
3281     const MachO::any_relocation_info &RE) const {
3282   if (isRelocationScattered(RE))
3283     return getScatteredRelocationLength(RE);
3284   return getPlainRelocationLength(*this, RE);
3285 }
3286 
3287 unsigned
3288 MachOObjectFile::getAnyRelocationType(
3289                                    const MachO::any_relocation_info &RE) const {
3290   if (isRelocationScattered(RE))
3291     return getScatteredRelocationType(RE);
3292   return getPlainRelocationType(*this, RE);
3293 }
3294 
3295 SectionRef
3296 MachOObjectFile::getAnyRelocationSection(
3297                                    const MachO::any_relocation_info &RE) const {
3298   if (isRelocationScattered(RE) || getPlainRelocationExternal(RE))
3299     return *section_end();
3300   unsigned SecNum = getPlainRelocationSymbolNum(RE);
3301   if (SecNum == MachO::R_ABS || SecNum > Sections.size())
3302     return *section_end();
3303   DataRefImpl DRI;
3304   DRI.d.a = SecNum - 1;
3305   return SectionRef(DRI, this);
3306 }
3307 
3308 MachO::section MachOObjectFile::getSection(DataRefImpl DRI) const {
3309   assert(DRI.d.a < Sections.size() && "Should have detected this earlier");
3310   return getStruct<MachO::section>(*this, Sections[DRI.d.a]);
3311 }
3312 
3313 MachO::section_64 MachOObjectFile::getSection64(DataRefImpl DRI) const {
3314   assert(DRI.d.a < Sections.size() && "Should have detected this earlier");
3315   return getStruct<MachO::section_64>(*this, Sections[DRI.d.a]);
3316 }
3317 
3318 MachO::section MachOObjectFile::getSection(const LoadCommandInfo &L,
3319                                            unsigned Index) const {
3320   const char *Sec = getSectionPtr(*this, L, Index);
3321   return getStruct<MachO::section>(*this, Sec);
3322 }
3323 
3324 MachO::section_64 MachOObjectFile::getSection64(const LoadCommandInfo &L,
3325                                                 unsigned Index) const {
3326   const char *Sec = getSectionPtr(*this, L, Index);
3327   return getStruct<MachO::section_64>(*this, Sec);
3328 }
3329 
3330 MachO::nlist
3331 MachOObjectFile::getSymbolTableEntry(DataRefImpl DRI) const {
3332   const char *P = reinterpret_cast<const char *>(DRI.p);
3333   return getStruct<MachO::nlist>(*this, P);
3334 }
3335 
3336 MachO::nlist_64
3337 MachOObjectFile::getSymbol64TableEntry(DataRefImpl DRI) const {
3338   const char *P = reinterpret_cast<const char *>(DRI.p);
3339   return getStruct<MachO::nlist_64>(*this, P);
3340 }
3341 
3342 MachO::linkedit_data_command
3343 MachOObjectFile::getLinkeditDataLoadCommand(const LoadCommandInfo &L) const {
3344   return getStruct<MachO::linkedit_data_command>(*this, L.Ptr);
3345 }
3346 
3347 MachO::segment_command
3348 MachOObjectFile::getSegmentLoadCommand(const LoadCommandInfo &L) const {
3349   return getStruct<MachO::segment_command>(*this, L.Ptr);
3350 }
3351 
3352 MachO::segment_command_64
3353 MachOObjectFile::getSegment64LoadCommand(const LoadCommandInfo &L) const {
3354   return getStruct<MachO::segment_command_64>(*this, L.Ptr);
3355 }
3356 
3357 MachO::linker_option_command
3358 MachOObjectFile::getLinkerOptionLoadCommand(const LoadCommandInfo &L) const {
3359   return getStruct<MachO::linker_option_command>(*this, L.Ptr);
3360 }
3361 
3362 MachO::version_min_command
3363 MachOObjectFile::getVersionMinLoadCommand(const LoadCommandInfo &L) const {
3364   return getStruct<MachO::version_min_command>(*this, L.Ptr);
3365 }
3366 
3367 MachO::note_command
3368 MachOObjectFile::getNoteLoadCommand(const LoadCommandInfo &L) const {
3369   return getStruct<MachO::note_command>(*this, L.Ptr);
3370 }
3371 
3372 MachO::build_version_command
3373 MachOObjectFile::getBuildVersionLoadCommand(const LoadCommandInfo &L) const {
3374   return getStruct<MachO::build_version_command>(*this, L.Ptr);
3375 }
3376 
3377 MachO::build_tool_version
3378 MachOObjectFile::getBuildToolVersion(unsigned index) const {
3379   return getStruct<MachO::build_tool_version>(*this, BuildTools[index]);
3380 }
3381 
3382 MachO::dylib_command
3383 MachOObjectFile::getDylibIDLoadCommand(const LoadCommandInfo &L) const {
3384   return getStruct<MachO::dylib_command>(*this, L.Ptr);
3385 }
3386 
3387 MachO::dyld_info_command
3388 MachOObjectFile::getDyldInfoLoadCommand(const LoadCommandInfo &L) const {
3389   return getStruct<MachO::dyld_info_command>(*this, L.Ptr);
3390 }
3391 
3392 MachO::dylinker_command
3393 MachOObjectFile::getDylinkerCommand(const LoadCommandInfo &L) const {
3394   return getStruct<MachO::dylinker_command>(*this, L.Ptr);
3395 }
3396 
3397 MachO::uuid_command
3398 MachOObjectFile::getUuidCommand(const LoadCommandInfo &L) const {
3399   return getStruct<MachO::uuid_command>(*this, L.Ptr);
3400 }
3401 
3402 MachO::rpath_command
3403 MachOObjectFile::getRpathCommand(const LoadCommandInfo &L) const {
3404   return getStruct<MachO::rpath_command>(*this, L.Ptr);
3405 }
3406 
3407 MachO::source_version_command
3408 MachOObjectFile::getSourceVersionCommand(const LoadCommandInfo &L) const {
3409   return getStruct<MachO::source_version_command>(*this, L.Ptr);
3410 }
3411 
3412 MachO::entry_point_command
3413 MachOObjectFile::getEntryPointCommand(const LoadCommandInfo &L) const {
3414   return getStruct<MachO::entry_point_command>(*this, L.Ptr);
3415 }
3416 
3417 MachO::encryption_info_command
3418 MachOObjectFile::getEncryptionInfoCommand(const LoadCommandInfo &L) const {
3419   return getStruct<MachO::encryption_info_command>(*this, L.Ptr);
3420 }
3421 
3422 MachO::encryption_info_command_64
3423 MachOObjectFile::getEncryptionInfoCommand64(const LoadCommandInfo &L) const {
3424   return getStruct<MachO::encryption_info_command_64>(*this, L.Ptr);
3425 }
3426 
3427 MachO::sub_framework_command
3428 MachOObjectFile::getSubFrameworkCommand(const LoadCommandInfo &L) const {
3429   return getStruct<MachO::sub_framework_command>(*this, L.Ptr);
3430 }
3431 
3432 MachO::sub_umbrella_command
3433 MachOObjectFile::getSubUmbrellaCommand(const LoadCommandInfo &L) const {
3434   return getStruct<MachO::sub_umbrella_command>(*this, L.Ptr);
3435 }
3436 
3437 MachO::sub_library_command
3438 MachOObjectFile::getSubLibraryCommand(const LoadCommandInfo &L) const {
3439   return getStruct<MachO::sub_library_command>(*this, L.Ptr);
3440 }
3441 
3442 MachO::sub_client_command
3443 MachOObjectFile::getSubClientCommand(const LoadCommandInfo &L) const {
3444   return getStruct<MachO::sub_client_command>(*this, L.Ptr);
3445 }
3446 
3447 MachO::routines_command
3448 MachOObjectFile::getRoutinesCommand(const LoadCommandInfo &L) const {
3449   return getStruct<MachO::routines_command>(*this, L.Ptr);
3450 }
3451 
3452 MachO::routines_command_64
3453 MachOObjectFile::getRoutinesCommand64(const LoadCommandInfo &L) const {
3454   return getStruct<MachO::routines_command_64>(*this, L.Ptr);
3455 }
3456 
3457 MachO::thread_command
3458 MachOObjectFile::getThreadCommand(const LoadCommandInfo &L) const {
3459   return getStruct<MachO::thread_command>(*this, L.Ptr);
3460 }
3461 
3462 MachO::any_relocation_info
3463 MachOObjectFile::getRelocation(DataRefImpl Rel) const {
3464   DataRefImpl Sec;
3465   Sec.d.a = Rel.d.a;
3466   uint32_t Offset;
3467   if (is64Bit()) {
3468     MachO::section_64 Sect = getSection64(Sec);
3469     Offset = Sect.reloff;
3470   } else {
3471     MachO::section Sect = getSection(Sec);
3472     Offset = Sect.reloff;
3473   }
3474 
3475   auto P = reinterpret_cast<const MachO::any_relocation_info *>(
3476       getPtr(*this, Offset)) + Rel.d.b;
3477   return getStruct<MachO::any_relocation_info>(
3478       *this, reinterpret_cast<const char *>(P));
3479 }
3480 
3481 MachO::data_in_code_entry
3482 MachOObjectFile::getDice(DataRefImpl Rel) const {
3483   const char *P = reinterpret_cast<const char *>(Rel.p);
3484   return getStruct<MachO::data_in_code_entry>(*this, P);
3485 }
3486 
3487 const MachO::mach_header &MachOObjectFile::getHeader() const {
3488   return Header;
3489 }
3490 
3491 const MachO::mach_header_64 &MachOObjectFile::getHeader64() const {
3492   assert(is64Bit());
3493   return Header64;
3494 }
3495 
3496 uint32_t MachOObjectFile::getIndirectSymbolTableEntry(
3497                                              const MachO::dysymtab_command &DLC,
3498                                              unsigned Index) const {
3499   uint64_t Offset = DLC.indirectsymoff + Index * sizeof(uint32_t);
3500   return getStruct<uint32_t>(*this, getPtr(*this, Offset));
3501 }
3502 
3503 MachO::data_in_code_entry
3504 MachOObjectFile::getDataInCodeTableEntry(uint32_t DataOffset,
3505                                          unsigned Index) const {
3506   uint64_t Offset = DataOffset + Index * sizeof(MachO::data_in_code_entry);
3507   return getStruct<MachO::data_in_code_entry>(*this, getPtr(*this, Offset));
3508 }
3509 
3510 MachO::symtab_command MachOObjectFile::getSymtabLoadCommand() const {
3511   if (SymtabLoadCmd)
3512     return getStruct<MachO::symtab_command>(*this, SymtabLoadCmd);
3513 
3514   // If there is no SymtabLoadCmd return a load command with zero'ed fields.
3515   MachO::symtab_command Cmd;
3516   Cmd.cmd = MachO::LC_SYMTAB;
3517   Cmd.cmdsize = sizeof(MachO::symtab_command);
3518   Cmd.symoff = 0;
3519   Cmd.nsyms = 0;
3520   Cmd.stroff = 0;
3521   Cmd.strsize = 0;
3522   return Cmd;
3523 }
3524 
3525 MachO::dysymtab_command MachOObjectFile::getDysymtabLoadCommand() const {
3526   if (DysymtabLoadCmd)
3527     return getStruct<MachO::dysymtab_command>(*this, DysymtabLoadCmd);
3528 
3529   // If there is no DysymtabLoadCmd return a load command with zero'ed fields.
3530   MachO::dysymtab_command Cmd;
3531   Cmd.cmd = MachO::LC_DYSYMTAB;
3532   Cmd.cmdsize = sizeof(MachO::dysymtab_command);
3533   Cmd.ilocalsym = 0;
3534   Cmd.nlocalsym = 0;
3535   Cmd.iextdefsym = 0;
3536   Cmd.nextdefsym = 0;
3537   Cmd.iundefsym = 0;
3538   Cmd.nundefsym = 0;
3539   Cmd.tocoff = 0;
3540   Cmd.ntoc = 0;
3541   Cmd.modtaboff = 0;
3542   Cmd.nmodtab = 0;
3543   Cmd.extrefsymoff = 0;
3544   Cmd.nextrefsyms = 0;
3545   Cmd.indirectsymoff = 0;
3546   Cmd.nindirectsyms = 0;
3547   Cmd.extreloff = 0;
3548   Cmd.nextrel = 0;
3549   Cmd.locreloff = 0;
3550   Cmd.nlocrel = 0;
3551   return Cmd;
3552 }
3553 
3554 MachO::linkedit_data_command
3555 MachOObjectFile::getDataInCodeLoadCommand() const {
3556   if (DataInCodeLoadCmd)
3557     return getStruct<MachO::linkedit_data_command>(*this, DataInCodeLoadCmd);
3558 
3559   // If there is no DataInCodeLoadCmd return a load command with zero'ed fields.
3560   MachO::linkedit_data_command Cmd;
3561   Cmd.cmd = MachO::LC_DATA_IN_CODE;
3562   Cmd.cmdsize = sizeof(MachO::linkedit_data_command);
3563   Cmd.dataoff = 0;
3564   Cmd.datasize = 0;
3565   return Cmd;
3566 }
3567 
3568 MachO::linkedit_data_command
3569 MachOObjectFile::getLinkOptHintsLoadCommand() const {
3570   if (LinkOptHintsLoadCmd)
3571     return getStruct<MachO::linkedit_data_command>(*this, LinkOptHintsLoadCmd);
3572 
3573   // If there is no LinkOptHintsLoadCmd return a load command with zero'ed
3574   // fields.
3575   MachO::linkedit_data_command Cmd;
3576   Cmd.cmd = MachO::LC_LINKER_OPTIMIZATION_HINT;
3577   Cmd.cmdsize = sizeof(MachO::linkedit_data_command);
3578   Cmd.dataoff = 0;
3579   Cmd.datasize = 0;
3580   return Cmd;
3581 }
3582 
3583 ArrayRef<uint8_t> MachOObjectFile::getDyldInfoRebaseOpcodes() const {
3584   if (!DyldInfoLoadCmd)
3585     return None;
3586 
3587   MachO::dyld_info_command DyldInfo =
3588       getStruct<MachO::dyld_info_command>(*this, DyldInfoLoadCmd);
3589   const uint8_t *Ptr =
3590       reinterpret_cast<const uint8_t *>(getPtr(*this, DyldInfo.rebase_off));
3591   return makeArrayRef(Ptr, DyldInfo.rebase_size);
3592 }
3593 
3594 ArrayRef<uint8_t> MachOObjectFile::getDyldInfoBindOpcodes() const {
3595   if (!DyldInfoLoadCmd)
3596     return None;
3597 
3598   MachO::dyld_info_command DyldInfo =
3599       getStruct<MachO::dyld_info_command>(*this, DyldInfoLoadCmd);
3600   const uint8_t *Ptr =
3601       reinterpret_cast<const uint8_t *>(getPtr(*this, DyldInfo.bind_off));
3602   return makeArrayRef(Ptr, DyldInfo.bind_size);
3603 }
3604 
3605 ArrayRef<uint8_t> MachOObjectFile::getDyldInfoWeakBindOpcodes() const {
3606   if (!DyldInfoLoadCmd)
3607     return None;
3608 
3609   MachO::dyld_info_command DyldInfo =
3610       getStruct<MachO::dyld_info_command>(*this, DyldInfoLoadCmd);
3611   const uint8_t *Ptr =
3612       reinterpret_cast<const uint8_t *>(getPtr(*this, DyldInfo.weak_bind_off));
3613   return makeArrayRef(Ptr, DyldInfo.weak_bind_size);
3614 }
3615 
3616 ArrayRef<uint8_t> MachOObjectFile::getDyldInfoLazyBindOpcodes() const {
3617   if (!DyldInfoLoadCmd)
3618     return None;
3619 
3620   MachO::dyld_info_command DyldInfo =
3621       getStruct<MachO::dyld_info_command>(*this, DyldInfoLoadCmd);
3622   const uint8_t *Ptr =
3623       reinterpret_cast<const uint8_t *>(getPtr(*this, DyldInfo.lazy_bind_off));
3624   return makeArrayRef(Ptr, DyldInfo.lazy_bind_size);
3625 }
3626 
3627 ArrayRef<uint8_t> MachOObjectFile::getDyldInfoExportsTrie() const {
3628   if (!DyldInfoLoadCmd)
3629     return None;
3630 
3631   MachO::dyld_info_command DyldInfo =
3632       getStruct<MachO::dyld_info_command>(*this, DyldInfoLoadCmd);
3633   const uint8_t *Ptr =
3634       reinterpret_cast<const uint8_t *>(getPtr(*this, DyldInfo.export_off));
3635   return makeArrayRef(Ptr, DyldInfo.export_size);
3636 }
3637 
3638 ArrayRef<uint8_t> MachOObjectFile::getUuid() const {
3639   if (!UuidLoadCmd)
3640     return None;
3641   // Returning a pointer is fine as uuid doesn't need endian swapping.
3642   const char *Ptr = UuidLoadCmd + offsetof(MachO::uuid_command, uuid);
3643   return makeArrayRef(reinterpret_cast<const uint8_t *>(Ptr), 16);
3644 }
3645 
3646 StringRef MachOObjectFile::getStringTableData() const {
3647   MachO::symtab_command S = getSymtabLoadCommand();
3648   return getData().substr(S.stroff, S.strsize);
3649 }
3650 
3651 bool MachOObjectFile::is64Bit() const {
3652   return getType() == getMachOType(false, true) ||
3653     getType() == getMachOType(true, true);
3654 }
3655 
3656 void MachOObjectFile::ReadULEB128s(uint64_t Index,
3657                                    SmallVectorImpl<uint64_t> &Out) const {
3658   DataExtractor extractor(ObjectFile::getData(), true, 0);
3659 
3660   uint32_t offset = Index;
3661   uint64_t data = 0;
3662   while (uint64_t delta = extractor.getULEB128(&offset)) {
3663     data += delta;
3664     Out.push_back(data);
3665   }
3666 }
3667 
3668 bool MachOObjectFile::isRelocatableObject() const {
3669   return getHeader().filetype == MachO::MH_OBJECT;
3670 }
3671 
3672 Expected<std::unique_ptr<MachOObjectFile>>
3673 ObjectFile::createMachOObjectFile(MemoryBufferRef Buffer,
3674                                   uint32_t UniversalCputype,
3675                                   uint32_t UniversalIndex) {
3676   StringRef Magic = Buffer.getBuffer().slice(0, 4);
3677   if (Magic == "\xFE\xED\xFA\xCE")
3678     return MachOObjectFile::create(Buffer, false, false,
3679                                    UniversalCputype, UniversalIndex);
3680   if (Magic == "\xCE\xFA\xED\xFE")
3681     return MachOObjectFile::create(Buffer, true, false,
3682                                    UniversalCputype, UniversalIndex);
3683   if (Magic == "\xFE\xED\xFA\xCF")
3684     return MachOObjectFile::create(Buffer, false, true,
3685                                    UniversalCputype, UniversalIndex);
3686   if (Magic == "\xCF\xFA\xED\xFE")
3687     return MachOObjectFile::create(Buffer, true, true,
3688                                    UniversalCputype, UniversalIndex);
3689   return make_error<GenericBinaryError>("Unrecognized MachO magic number",
3690                                         object_error::invalid_file_type);
3691 }
3692