llvm.org GIT mirror llvm / 1f65932
Make ObjectFile and BitcodeReader always own the MemoryBuffer. This allows us to just use a std::unique_ptr to store the pointer to the buffer. The flip side is that they have to support releasing the buffer back to the caller. Overall this looks like a more efficient and less brittle api. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@211542 91177308-0d34-0410-b5e6-96231b3b80d8 Rafael Espindola 5 years ago
23 changed file(s) with 117 addition(s) and 154 deletion(s). Raw diff Collapse all Expand all
2929 /// deserialization of function bodies. If successful, this takes ownership
3030 /// of 'buffer. On error, this *does not* take ownership of Buffer.
3131 ErrorOr getLazyBitcodeModule(MemoryBuffer *Buffer,
32 LLVMContext &Context,
33 bool BufferOwned = true);
32 LLVMContext &Context);
3433
3534 /// getStreamedBitcodeModule - Read the header of the specified stream
3635 /// and prepare for lazy deserialization and streaming of function bodies.
5353 /// Make sure the entire Module has been completely read.
5454 ///
5555 virtual std::error_code MaterializeModule(Module *M) = 0;
56
57 virtual void releaseBuffer() = 0;
5658 };
5759
5860 } // End llvm namespace
457457 /// Make sure all GlobalValues in this Module are fully read and clear the
458458 /// Materializer. If the module is corrupt, this DOES NOT clear the old
459459 /// Materializer.
460 std::error_code materializeAllPermanently();
460 std::error_code materializeAllPermanently(bool ReleaseBuffer = false);
461461
462462 /// @}
463463 /// @name Direct access to the globals list, functions list, and symbol table
3131 Binary(const Binary &other) LLVM_DELETED_FUNCTION;
3232
3333 unsigned int TypeID;
34 bool BufferOwned;
3534
3635 protected:
37 MemoryBuffer *Data;
36 std::unique_ptr Data;
3837
39 Binary(unsigned int Type, MemoryBuffer *Source, bool BufferOwned = true);
38 Binary(unsigned int Type, MemoryBuffer *Source);
4039
4140 enum {
4241 ID_Archive,
7877 virtual ~Binary();
7978
8079 StringRef getData() const;
80 MemoryBuffer *releaseBuffer() { return Data.release(); }
8181 StringRef getFileName() const;
8282
8383 // Cast methods.
419419 StringRef &Result) const override;
420420
421421 public:
422 COFFObjectFile(MemoryBuffer *Object, std::error_code &EC,
423 bool BufferOwned = true);
422 COFFObjectFile(MemoryBuffer *Object, std::error_code &EC);
424423 basic_symbol_iterator symbol_begin_impl() const override;
425424 basic_symbol_iterator symbol_end_impl() const override;
426425 library_iterator needed_library_begin() const override;
176176 bool isDyldELFObject;
177177
178178 public:
179 ELFObjectFile(MemoryBuffer *Object, std::error_code &EC,
180 bool BufferOwned = true);
179 ELFObjectFile(MemoryBuffer *Object, std::error_code &EC);
181180
182181 const Elf_Sym *getSymbol(DataRefImpl Symb) const;
183182
773772 }
774773
775774 template
776 ELFObjectFile::ELFObjectFile(MemoryBuffer *Object, std::error_code &ec,
777 bool BufferOwned)
775 ELFObjectFile::ELFObjectFile(MemoryBuffer *Object, std::error_code &ec)
778776 : ObjectFile(getELFType(static_cast(ELFT::TargetEndianness) ==
779777 support::little,
780778 ELFT::Is64Bits),
781 Object, BufferOwned),
779 Object),
782780 EF(Object, ec) {}
783781
784782 template
2626 std::unique_ptr Mang;
2727
2828 public:
29 IRObjectFile(MemoryBuffer *Object, std::error_code &EC, LLVMContext &Context,
30 bool BufferOwned);
29 IRObjectFile(MemoryBuffer *Object, std::error_code &EC, LLVMContext &Context);
30 ~IRObjectFile();
3131 void moveSymbolNext(DataRefImpl &Symb) const override;
3232 std::error_code printSymbolName(raw_ostream &OS,
3333 DataRefImpl Symb) const override;
5656 };
5757
5858 MachOObjectFile(MemoryBuffer *Object, bool IsLittleEndian, bool Is64Bits,
59 std::error_code &EC, bool BufferOwned = true);
59 std::error_code &EC);
6060
6161 void moveSymbolNext(DataRefImpl &Symb) const override;
6262 std::error_code getSymbolName(DataRefImpl Symb,
207207 ObjectFile(const ObjectFile &other) LLVM_DELETED_FUNCTION;
208208
209209 protected:
210 ObjectFile(unsigned int Type, MemoryBuffer *Source, bool BufferOwned = true);
210 ObjectFile(unsigned int Type, MemoryBuffer *Source);
211211
212212 const uint8_t *base() const {
213213 return reinterpret_cast(Data->getBufferStart());
333333 /// @brief Create ObjectFile from path.
334334 static ErrorOr createObjectFile(StringRef ObjectPath);
335335 static ErrorOr createObjectFile(MemoryBuffer *Object,
336 bool BufferOwned,
337336 sys::fs::file_magic Type);
338337 static ErrorOr createObjectFile(MemoryBuffer *Object) {
339 return createObjectFile(Object, true, sys::fs::file_magic::unknown);
338 return createObjectFile(Object, sys::fs::file_magic::unknown);
340339 }
341340
342341
345344 }
346345
347346 public:
348 static ErrorOr createCOFFObjectFile(MemoryBuffer *Object,
349 bool BufferOwned = true);
350 static ErrorOr createELFObjectFile(MemoryBuffer *Object,
351 bool BufferOwned = true);
352 static ErrorOr createMachOObjectFile(MemoryBuffer *Object,
353 bool BufferOwned = true);
347 static ErrorOr createCOFFObjectFile(MemoryBuffer *Object);
348 static ErrorOr createELFObjectFile(MemoryBuffer *Object);
349 static ErrorOr createMachOObjectFile(MemoryBuffer *Object);
354350 };
355351
356352 // Inline function definitions.
114114 class SymbolicFile : public Binary {
115115 public:
116116 virtual ~SymbolicFile();
117 SymbolicFile(unsigned int Type, MemoryBuffer *Source, bool BufferOwned);
117 SymbolicFile(unsigned int Type, MemoryBuffer *Source);
118118
119119 // virtual interface.
120120 virtual void moveSymbolNext(DataRefImpl &Symb) const = 0;
142142
143143 // construction aux.
144144 static ErrorOr createIRObjectFile(MemoryBuffer *Object,
145 LLVMContext &Context,
146 bool BufferOwned = true);
145 LLVMContext &Context);
147146
148147 static ErrorOr createSymbolicFile(MemoryBuffer *Object,
149 bool BufferOwned,
150148 sys::fs::file_magic Type,
151149 LLVMContext *Context);
152150
153151 static ErrorOr createSymbolicFile(MemoryBuffer *Object) {
154 return createSymbolicFile(Object, true, sys::fs::file_magic::unknown,
155 nullptr);
152 return createSymbolicFile(Object, sys::fs::file_magic::unknown, nullptr);
156153 }
157154 static ErrorOr createSymbolicFile(StringRef ObjectPath);
158155
3838 }
3939
4040 void BitcodeReader::FreeState() {
41 if (BufferOwned)
42 delete Buffer;
4341 Buffer = nullptr;
4442 std::vector().swap(TypeList);
4543 ValueList.clear();
31493147 // GVMaterializer implementation
31503148 //===----------------------------------------------------------------------===//
31513149
3150 void BitcodeReader::releaseBuffer() { Buffer.release(); }
31523151
31533152 bool BitcodeReader::isMaterializable(const GlobalValue *GV) const {
31543153 if (const Function *F = dyn_cast(GV)) {
33733372 /// getLazyBitcodeModule - lazy function-at-a-time loading from a file.
33743373 ///
33753374 ErrorOr llvm::getLazyBitcodeModule(MemoryBuffer *Buffer,
3376 LLVMContext &Context,
3377 bool BufferOwned) {
3375 LLVMContext &Context) {
33783376 Module *M = new Module(Buffer->getBufferIdentifier(), Context);
3379 BitcodeReader *R = new BitcodeReader(Buffer, Context, BufferOwned);
3377 BitcodeReader *R = new BitcodeReader(Buffer, Context);
33803378 M->setMaterializer(R);
33813379 if (std::error_code EC = R->ParseBitcodeInto(M)) {
33823380 R->releaseBuffer(); // Never take ownership on error.
34083406
34093407 ErrorOr llvm::parseBitcodeFile(MemoryBuffer *Buffer,
34103408 LLVMContext &Context) {
3411 ErrorOr ModuleOrErr = getLazyBitcodeModule(Buffer, Context, false);
3409 ErrorOr ModuleOrErr = getLazyBitcodeModule(Buffer, Context);
34123410 if (!ModuleOrErr)
34133411 return ModuleOrErr;
34143412 Module *M = ModuleOrErr.get();
3415
34163413 // Read in the entire module, and destroy the BitcodeReader.
3417 if (std::error_code EC = M->materializeAllPermanently()) {
3414 if (std::error_code EC = M->materializeAllPermanently(true)) {
34183415 delete M;
34193416 return EC;
34203417 }
34283425 std::string llvm::getBitcodeTargetTriple(MemoryBuffer *Buffer,
34293426 LLVMContext& Context,
34303427 std::string *ErrMsg) {
3431 BitcodeReader *R = new BitcodeReader(Buffer, Context, /*BufferOwned*/ false);
3428 BitcodeReader *R = new BitcodeReader(Buffer, Context);
34323429
34333430 std::string Triple("");
34343431 if (std::error_code EC = R->ParseTriple(Triple))
34353432 if (ErrMsg)
34363433 *ErrMsg = EC.message();
34373434
3435 R->releaseBuffer();
34383436 delete R;
34393437 return Triple;
34403438 }
124124 class BitcodeReader : public GVMaterializer {
125125 LLVMContext &Context;
126126 Module *TheModule;
127 MemoryBuffer *Buffer;
128 bool BufferOwned;
127 std::unique_ptr Buffer;
129128 std::unique_ptr StreamFile;
130129 BitstreamCursor Stream;
131130 DataStreamer *LazyStreamer;
222221 return std::error_code(E, BitcodeErrorCategory());
223222 }
224223
225 explicit BitcodeReader(MemoryBuffer *buffer, LLVMContext &C, bool BufferOwned)
226 : Context(C), TheModule(nullptr), Buffer(buffer),
227 BufferOwned(BufferOwned), LazyStreamer(nullptr), NextUnreadBit(0),
228 SeenValueSymbolTable(false), ValueList(C), MDValueList(C),
229 SeenFirstFunctionBody(false), UseRelativeIDs(false) {}
224 explicit BitcodeReader(MemoryBuffer *buffer, LLVMContext &C)
225 : Context(C), TheModule(nullptr), Buffer(buffer), LazyStreamer(nullptr),
226 NextUnreadBit(0), SeenValueSymbolTable(false), ValueList(C),
227 MDValueList(C), SeenFirstFunctionBody(false), UseRelativeIDs(false) {}
230228 explicit BitcodeReader(DataStreamer *streamer, LLVMContext &C)
231 : Context(C), TheModule(nullptr), Buffer(nullptr), BufferOwned(false),
232 LazyStreamer(streamer), NextUnreadBit(0), SeenValueSymbolTable(false),
233 ValueList(C), MDValueList(C), SeenFirstFunctionBody(false),
234 UseRelativeIDs(false) {}
229 : Context(C), TheModule(nullptr), Buffer(nullptr), LazyStreamer(streamer),
230 NextUnreadBit(0), SeenValueSymbolTable(false), ValueList(C),
231 MDValueList(C), SeenFirstFunctionBody(false), UseRelativeIDs(false) {}
235232 ~BitcodeReader() { FreeState(); }
236233
237234 void materializeForwardReferencedFunctions();
238235
239236 void FreeState();
240237
241 void releaseBuffer() {
242 Buffer = nullptr;
243 }
238 void releaseBuffer() override;
244239
245240 bool isMaterializable(const GlobalValue *GV) const override;
246241 bool isDematerializable(const GlobalValue *GV) const override;
399399 return Materializer->MaterializeModule(this);
400400 }
401401
402 std::error_code Module::materializeAllPermanently() {
402 std::error_code Module::materializeAllPermanently(bool ReleaseBuffer) {
403403 if (std::error_code EC = materializeAll())
404404 return EC;
405
406 if (ReleaseBuffer)
407 Materializer->releaseBuffer();
405408
406409 Materializer.reset();
407410 return std::error_code();
180180 ErrorOr> BuffOrErr = getMemoryBuffer();
181181 if (std::error_code EC = BuffOrErr.getError())
182182 return EC;
183 return createBinary(BuffOrErr.get().release(), Context);
183
184 std::unique_ptr Buff(BuffOrErr.get().release());
185 ErrorOr> Ret = createBinary(Buff.get(), Context);
186 if (!Ret.getError())
187 Buff.release();
188 return Ret;
184189 }
185190
186191 ErrorOr Archive::create(MemoryBuffer *Source) {
2424 using namespace llvm;
2525 using namespace object;
2626
27 Binary::~Binary() {
28 if (BufferOwned)
29 delete Data;
30 }
27 Binary::~Binary() {}
3128
32 Binary::Binary(unsigned int Type, MemoryBuffer *Source, bool BufferOwned)
33 : TypeID(Type), BufferOwned(BufferOwned), Data(Source) {}
29 Binary::Binary(unsigned int Type, MemoryBuffer *Source)
30 : TypeID(Type), Data(Source) {}
3431
3532 StringRef Binary::getData() const {
3633 return Data->getBuffer();
4037 return Data->getBufferIdentifier();
4138 }
4239
43 ErrorOr object::createBinary(MemoryBuffer *Source,
40 ErrorOr object::createBinary(MemoryBuffer *Buffer,
4441 LLVMContext *Context) {
45 std::unique_ptr scopedSource(Source);
46 sys::fs::file_magic Type = sys::fs::identify_magic(Source->getBuffer());
42 sys::fs::file_magic Type = sys::fs::identify_magic(Buffer->getBuffer());
4743
4844 switch (Type) {
4945 case sys::fs::file_magic::archive:
50 return Archive::create(scopedSource.release());
46 return Archive::create(Buffer);
5147 case sys::fs::file_magic::elf_relocatable:
5248 case sys::fs::file_magic::elf_executable:
5349 case sys::fs::file_magic::elf_shared_object:
6662 case sys::fs::file_magic::coff_import_library:
6763 case sys::fs::file_magic::pecoff_executable:
6864 case sys::fs::file_magic::bitcode:
69 return ObjectFile::createSymbolicFile(scopedSource.release(), true, Type,
70 Context);
65 return ObjectFile::createSymbolicFile(Buffer, Type, Context);
7166 case sys::fs::file_magic::macho_universal_binary:
72 return MachOUniversalBinary::create(scopedSource.release());
67 return MachOUniversalBinary::create(Buffer);
7368 case sys::fs::file_magic::unknown:
7469 case sys::fs::file_magic::windows_resource:
7570 // Unrecognized object file format.
3030 using support::little16_t;
3131
3232 // Returns false if size is greater than the buffer size. And sets ec.
33 static bool checkSize(const MemoryBuffer *M, std::error_code &EC,
33 static bool checkSize(const MemoryBuffer &M, std::error_code &EC,
3434 uint64_t Size) {
35 if (M->getBufferSize() < Size) {
35 if (M.getBufferSize() < Size) {
3636 EC = object_error::unexpected_eof;
3737 return false;
3838 }
4242 // Sets Obj unless any bytes in [addr, addr + size) fall outsize of m.
4343 // Returns unexpected_eof if error.
4444 template
45 static std::error_code getObject(const T *&Obj, const MemoryBuffer *M,
45 static std::error_code getObject(const T *&Obj, const MemoryBuffer &M,
4646 const uint8_t *Ptr,
4747 const size_t Size = sizeof(T)) {
4848 uintptr_t Addr = uintptr_t(Ptr);
49 if (Addr + Size < Addr ||
50 Addr + Size < Size ||
51 Addr + Size > uintptr_t(M->getBufferEnd())) {
49 if (Addr + Size < Addr || Addr + Size < Size ||
50 Addr + Size > uintptr_t(M.getBufferEnd())) {
5251 return object_error::unexpected_eof;
5352 }
5453 Obj = reinterpret_cast(Addr);
397396 // Initialize the pointer to the symbol table.
398397 std::error_code COFFObjectFile::initSymbolTablePtr() {
399398 if (std::error_code EC = getObject(
400 SymbolTable, Data, base() + COFFHeader->PointerToSymbolTable,
399 SymbolTable, *Data, base() + COFFHeader->PointerToSymbolTable,
401400 COFFHeader->NumberOfSymbols * sizeof(coff_symbol)))
402401 return EC;
403402
408407 base() + COFFHeader->PointerToSymbolTable +
409408 COFFHeader->NumberOfSymbols * sizeof(coff_symbol);
410409 const ulittle32_t *StringTableSizePtr;
411 if (std::error_code EC = getObject(StringTableSizePtr, Data, StringTableAddr))
410 if (std::error_code EC =
411 getObject(StringTableSizePtr, *Data, StringTableAddr))
412412 return EC;
413413 StringTableSize = *StringTableSizePtr;
414414 if (std::error_code EC =
415 getObject(StringTable, Data, StringTableAddr, StringTableSize))
415 getObject(StringTable, *Data, StringTableAddr, StringTableSize))
416416 return EC;
417417
418418 // Treat table sizes < 4 as empty because contrary to the PECOFF spec, some
510510 return object_error::success;
511511 }
512512
513 COFFObjectFile::COFFObjectFile(MemoryBuffer *Object, std::error_code &EC,
514 bool BufferOwned)
515 : ObjectFile(Binary::ID_COFF, Object, BufferOwned), COFFHeader(nullptr),
513 COFFObjectFile::COFFObjectFile(MemoryBuffer *Object, std::error_code &EC)
514 : ObjectFile(Binary::ID_COFF, Object), COFFHeader(nullptr),
516515 PE32Header(nullptr), PE32PlusHeader(nullptr), DataDirectory(nullptr),
517516 SectionTable(nullptr), SymbolTable(nullptr), StringTable(nullptr),
518517 StringTableSize(0), ImportDirectory(nullptr), NumberOfImportDirectory(0),
519518 ExportDirectory(nullptr) {
520519 // Check that we at least have enough room for a header.
521 if (!checkSize(Data, EC, sizeof(coff_file_header))) return;
520 if (!checkSize(*Data, EC, sizeof(coff_file_header)))
521 return;
522522
523523 // The current location in the file where we are looking at.
524524 uint64_t CurPtr = 0;
531531 if (base()[0] == 0x4d && base()[1] == 0x5a) {
532532 // PE/COFF, seek through MS-DOS compatibility stub and 4-byte
533533 // PE signature to find 'normal' COFF header.
534 if (!checkSize(Data, EC, 0x3c + 8)) return;
534 if (!checkSize(*Data, EC, 0x3c + 8))
535 return;
535536 CurPtr = *reinterpret_cast(base() + 0x3c);
536537 // Check the PE magic bytes. ("PE\0\0")
537538 if (std::memcmp(base() + CurPtr, "PE\0\0", 4) != 0) {
542543 HasPEHeader = true;
543544 }
544545
545 if ((EC = getObject(COFFHeader, Data, base() + CurPtr)))
546 if ((EC = getObject(COFFHeader, *Data, base() + CurPtr)))
546547 return;
547548 CurPtr += sizeof(coff_file_header);
548549
549550 if (HasPEHeader) {
550551 const pe32_header *Header;
551 if ((EC = getObject(Header, Data, base() + CurPtr)))
552 if ((EC = getObject(Header, *Data, base() + CurPtr)))
552553 return;
553554
554555 const uint8_t *DataDirAddr;
566567 EC = object_error::parse_failed;
567568 return;
568569 }
569 if ((EC = getObject(DataDirectory, Data, DataDirAddr, DataDirSize)))
570 if ((EC = getObject(DataDirectory, *Data, DataDirAddr, DataDirSize)))
570571 return;
571572 CurPtr += COFFHeader->SizeOfOptionalHeader;
572573 }
574575 if (COFFHeader->isImportLibrary())
575576 return;
576577
577 if ((EC = getObject(SectionTable, Data, base() + CurPtr,
578 if ((EC = getObject(SectionTable, *Data, base() + CurPtr,
578579 COFFHeader->NumberOfSections * sizeof(coff_section))))
579580 return;
580581
11091110 return object_error::success;
11101111 }
11111112
1112 ErrorOr ObjectFile::createCOFFObjectFile(MemoryBuffer *Object,
1113 bool BufferOwned) {
1113 ErrorOr ObjectFile::createCOFFObjectFile(MemoryBuffer *Object) {
11141114 std::error_code EC;
1115 std::unique_ptr Ret(
1116 new COFFObjectFile(Object, EC, BufferOwned));
1115 std::unique_ptr Ret(new COFFObjectFile(Object, EC));
11171116 if (EC)
11181117 return EC;
11191118 return Ret.release();
1616 namespace llvm {
1717 using namespace object;
1818
19 static ErrorOr createELFObjectFileAux(MemoryBuffer *Obj,
20 bool BufferOwned) {
19 ErrorOr ObjectFile::createELFObjectFile(MemoryBuffer *Obj) {
2120 std::pair Ident = getElfArchType(Obj);
2221 std::size_t MaxAlignment =
2322 1ULL << countTrailingZeros(uintptr_t(Obj->getBufferStart()));
2726 if (Ident.first == ELF::ELFCLASS32 && Ident.second == ELF::ELFDATA2LSB)
2827 #if !LLVM_IS_UNALIGNED_ACCESS_FAST
2928 if (MaxAlignment >= 4)
30 R.reset(new ELFObjectFile >(
31 Obj, EC, BufferOwned));
29 R.reset(new ELFObjectFile>(Obj, EC));
3230 else
3331 #endif
3432 if (MaxAlignment >= 2)
35 R.reset(new ELFObjectFile >(
36 Obj, EC, BufferOwned));
33 R.reset(new ELFObjectFile>(Obj, EC));
3734 else
3835 return object_error::parse_failed;
3936 else if (Ident.first == ELF::ELFCLASS32 && Ident.second == ELF::ELFDATA2MSB)
4037 #if !LLVM_IS_UNALIGNED_ACCESS_FAST
4138 if (MaxAlignment >= 4)
42 R.reset(new ELFObjectFile >(Obj, EC,
43 BufferOwned));
39 R.reset(new ELFObjectFile>(Obj, EC));
4440 else
4541 #endif
4642 if (MaxAlignment >= 2)
47 R.reset(new ELFObjectFile >(Obj, EC,
48 BufferOwned));
43 R.reset(new ELFObjectFile>(Obj, EC));
4944 else
5045 return object_error::parse_failed;
5146 else if (Ident.first == ELF::ELFCLASS64 && Ident.second == ELF::ELFDATA2MSB)
5247 #if !LLVM_IS_UNALIGNED_ACCESS_FAST
5348 if (MaxAlignment >= 8)
54 R.reset(new ELFObjectFile >(Obj, EC,
55 BufferOwned));
49 R.reset(new ELFObjectFile>(Obj, EC));
5650 else
5751 #endif
5852 if (MaxAlignment >= 2)
59 R.reset(new ELFObjectFile >(Obj, EC,
60 BufferOwned));
53 R.reset(new ELFObjectFile>(Obj, EC));
6154 else
6255 return object_error::parse_failed;
6356 else if (Ident.first == ELF::ELFCLASS64 && Ident.second == ELF::ELFDATA2LSB) {
6457 #if !LLVM_IS_UNALIGNED_ACCESS_FAST
6558 if (MaxAlignment >= 8)
66 R.reset(new ELFObjectFile >(
67 Obj, EC, BufferOwned));
59 R.reset(new ELFObjectFile>(Obj, EC));
6860 else
6961 #endif
7062 if (MaxAlignment >= 2)
71 R.reset(new ELFObjectFile >(
72 Obj, EC, BufferOwned));
63 R.reset(new ELFObjectFile>(Obj, EC));
7364 else
7465 return object_error::parse_failed;
7566 }
8172 return R.release();
8273 }
8374
84 ErrorOr ObjectFile::createELFObjectFile(MemoryBuffer *Obj,
85 bool BufferOwned) {
86 ErrorOr Ret = createELFObjectFileAux(Obj, BufferOwned);
87 if (BufferOwned && Ret.getError())
88 delete Obj;
89 return Ret;
90 }
91
9275 } // end namespace llvm
1212
1313 #include "llvm/Bitcode/ReaderWriter.h"
1414 #include "llvm/IR/LLVMContext.h"
15 #include "llvm/IR/GVMaterializer.h"
1516 #include "llvm/IR/Mangler.h"
1617 #include "llvm/IR/Module.h"
1718 #include "llvm/Object/IRObjectFile.h"
2021 using namespace object;
2122
2223 IRObjectFile::IRObjectFile(MemoryBuffer *Object, std::error_code &EC,
23 LLVMContext &Context, bool BufferOwned)
24 : SymbolicFile(Binary::ID_IR, Object, BufferOwned) {
25 ErrorOr MOrErr =
26 getLazyBitcodeModule(Object, Context, /*BufferOwned*/ false);
24 LLVMContext &Context)
25 : SymbolicFile(Binary::ID_IR, Object) {
26 ErrorOr MOrErr = getLazyBitcodeModule(Object, Context);
2727 if ((EC = MOrErr.getError()))
2828 return;
2929
3636
3737 Mang.reset(new Mangler(DL));
3838 }
39
40 IRObjectFile::~IRObjectFile() { M->getMaterializer()->releaseBuffer(); }
3941
4042 static const GlobalValue &getGV(DataRefImpl &Symb) {
4143 return *reinterpret_cast(Symb.p & ~uintptr_t(3));
150152 return basic_symbol_iterator(BasicSymbolRef(Ret, this));
151153 }
152154
153 ErrorOr llvm::object::SymbolicFile::createIRObjectFile(
154 MemoryBuffer *Object, LLVMContext &Context, bool BufferOwned) {
155 ErrorOr
156 llvm::object::SymbolicFile::createIRObjectFile(MemoryBuffer *Object,
157 LLVMContext &Context) {
155158 std::error_code EC;
156 std::unique_ptr Ret(
157 new IRObjectFile(Object, EC, Context, BufferOwned));
159 std::unique_ptr Ret(new IRObjectFile(Object, EC, Context));
158160 if (EC)
159161 return EC;
160162 return Ret.release();
422422 }
423423
424424 MachOObjectFile::MachOObjectFile(MemoryBuffer *Object, bool IsLittleEndian,
425 bool Is64bits, std::error_code &EC,
426 bool BufferOwned)
427 : ObjectFile(getMachOType(IsLittleEndian, Is64bits), Object, BufferOwned),
425 bool Is64bits, std::error_code &EC)
426 : ObjectFile(getMachOType(IsLittleEndian, Is64bits), Object),
428427 SymtabLoadCmd(nullptr), DysymtabLoadCmd(nullptr),
429428 DataInCodeLoadCmd(nullptr) {
430429 uint32_t LoadCommandCount = this->getHeader().ncmds;
18111810 }
18121811 }
18131812
1814 ErrorOr ObjectFile::createMachOObjectFile(MemoryBuffer *Buffer,
1815 bool BufferOwned) {
1813 ErrorOr ObjectFile::createMachOObjectFile(MemoryBuffer *Buffer) {
18161814 StringRef Magic = Buffer->getBuffer().slice(0, 4);
18171815 std::error_code EC;
18181816 std::unique_ptr Ret;
18191817 if (Magic == "\xFE\xED\xFA\xCE")
1820 Ret.reset(new MachOObjectFile(Buffer, false, false, EC, BufferOwned));
1818 Ret.reset(new MachOObjectFile(Buffer, false, false, EC));
18211819 else if (Magic == "\xCE\xFA\xED\xFE")
1822 Ret.reset(new MachOObjectFile(Buffer, true, false, EC, BufferOwned));
1820 Ret.reset(new MachOObjectFile(Buffer, true, false, EC));
18231821 else if (Magic == "\xFE\xED\xFA\xCF")
1824 Ret.reset(new MachOObjectFile(Buffer, false, true, EC, BufferOwned));
1822 Ret.reset(new MachOObjectFile(Buffer, false, true, EC));
18251823 else if (Magic == "\xCF\xFA\xED\xFE")
1826 Ret.reset(new MachOObjectFile(Buffer, true, true, EC, BufferOwned));
1824 Ret.reset(new MachOObjectFile(Buffer, true, true, EC));
18271825 else {
18281826 delete Buffer;
18291827 return object_error::parse_failed;
2222
2323 void ObjectFile::anchor() { }
2424
25 ObjectFile::ObjectFile(unsigned int Type, MemoryBuffer *Source,
26 bool BufferOwned)
27 : SymbolicFile(Type, Source, BufferOwned) {}
25 ObjectFile::ObjectFile(unsigned int Type, MemoryBuffer *Source)
26 : SymbolicFile(Type, Source) {}
2827
2928 std::error_code ObjectFile::printSymbolName(raw_ostream &OS,
3029 DataRefImpl Symb) const {
4645 }
4746
4847 ErrorOr ObjectFile::createObjectFile(MemoryBuffer *Object,
49 bool BufferOwned,
5048 sys::fs::file_magic Type) {
5149 if (Type == sys::fs::file_magic::unknown)
5250 Type = sys::fs::identify_magic(Object->getBuffer());
5755 case sys::fs::file_magic::archive:
5856 case sys::fs::file_magic::macho_universal_binary:
5957 case sys::fs::file_magic::windows_resource:
60 if (BufferOwned)
61 delete Object;
6258 return object_error::invalid_file_type;
6359 case sys::fs::file_magic::elf_relocatable:
6460 case sys::fs::file_magic::elf_executable:
6561 case sys::fs::file_magic::elf_shared_object:
6662 case sys::fs::file_magic::elf_core:
67 return createELFObjectFile(Object, BufferOwned);
63 return createELFObjectFile(Object);
6864 case sys::fs::file_magic::macho_object:
6965 case sys::fs::file_magic::macho_executable:
7066 case sys::fs::file_magic::macho_fixed_virtual_memory_shared_lib:
7571 case sys::fs::file_magic::macho_bundle:
7672 case sys::fs::file_magic::macho_dynamically_linked_shared_lib_stub:
7773 case sys::fs::file_magic::macho_dsym_companion:
78 return createMachOObjectFile(Object, BufferOwned);
74 return createMachOObjectFile(Object);
7975 case sys::fs::file_magic::coff_object:
8076 case sys::fs::file_magic::coff_import_library:
8177 case sys::fs::file_magic::pecoff_executable:
82 return createCOFFObjectFile(Object, BufferOwned);
78 return createCOFFObjectFile(Object);
8379 }
8480 llvm_unreachable("Unexpected Object File Type");
8581 }
1818 using namespace llvm;
1919 using namespace object;
2020
21 SymbolicFile::SymbolicFile(unsigned int Type, MemoryBuffer *Source,
22 bool BufferOwned)
23 : Binary(Type, Source, BufferOwned) {}
21 SymbolicFile::SymbolicFile(unsigned int Type, MemoryBuffer *Source)
22 : Binary(Type, Source) {}
2423
2524 SymbolicFile::~SymbolicFile() {}
2625
2726 ErrorOr
28 SymbolicFile::createSymbolicFile(MemoryBuffer *Object, bool BufferOwned,
29 sys::fs::file_magic Type,
27 SymbolicFile::createSymbolicFile(MemoryBuffer *Object, sys::fs::file_magic Type,
3028 LLVMContext *Context) {
3129 if (Type == sys::fs::file_magic::unknown)
3230 Type = sys::fs::identify_magic(Object->getBuffer());
3432 switch (Type) {
3533 case sys::fs::file_magic::bitcode:
3634 if (Context)
37 return IRObjectFile::createIRObjectFile(Object, *Context, BufferOwned);
35 return IRObjectFile::createIRObjectFile(Object, *Context);
3836 // Fallthrough
3937 case sys::fs::file_magic::unknown:
4038 case sys::fs::file_magic::archive:
4139 case sys::fs::file_magic::macho_universal_binary:
4240 case sys::fs::file_magic::windows_resource:
43 if (BufferOwned)
44 delete Object;
4541 return object_error::invalid_file_type;
4642 case sys::fs::file_magic::elf_relocatable:
4743 case sys::fs::file_magic::elf_executable:
6056 case sys::fs::file_magic::coff_object:
6157 case sys::fs::file_magic::coff_import_library:
6258 case sys::fs::file_magic::pecoff_executable:
63 return ObjectFile::createObjectFile(Object, BufferOwned, Type);
59 return ObjectFile::createObjectFile(Object, Type);
6460 }
6561 llvm_unreachable("Unexpected Binary File Type");
6662 }
698698 MemoryBuffer *MemberBuffer = Buffers[MemberNum].get();
699699 ErrorOr ObjOrErr =
700700 object::SymbolicFile::createSymbolicFile(
701 MemberBuffer, false, sys::fs::file_magic::unknown, &Context);
701 MemberBuffer, sys::fs::file_magic::unknown, &Context);
702702 if (!ObjOrErr)
703703 continue; // FIXME: check only for "not an object file" errors.
704704 std::unique_ptr Obj(ObjOrErr.get());
723723 MemberOffsetRefs.push_back(std::make_pair(Out.tell(), MemberNum));
724724 print32BE(Out, 0);
725725 }
726 Obj->releaseBuffer();
726727 }
727728 Out << NameOS.str();
728729
725725 return;
726726
727727 LLVMContext &Context = getGlobalContext();
728 ErrorOr BinaryOrErr = createBinary(Buffer.release(), &Context);
728 ErrorOr BinaryOrErr = createBinary(Buffer.get(), &Context);
729729 if (error(BinaryOrErr.getError(), Filename))
730730 return;
731 Buffer.release();
731732 std::unique_ptr Bin(BinaryOrErr.get());
732733
733734 if (Archive *A = dyn_cast(Bin.get())) {