From 3383ccc4003a685476be4eb5786539648c33ba90 Mon Sep 17 00:00:00 2001 From: Mehdi Amini Date: Mon, 9 Nov 2015 02:46:41 +0000 Subject: Add a method to the BitcodeReader to parse only the identification block Summary: Mimic parseTriple(); and exposes it to LTOModule.cpp Reviewers: dexonsmith, rafael Subscribers: llvm-commits From: Mehdi Amini llvm-svn: 252442 --- llvm/lib/Bitcode/Reader/BitcodeReader.cpp | 49 +++++++++++++++++++++++++++++++ 1 file changed, 49 insertions(+) (limited to 'llvm/lib/Bitcode/Reader/BitcodeReader.cpp') diff --git a/llvm/lib/Bitcode/Reader/BitcodeReader.cpp b/llvm/lib/Bitcode/Reader/BitcodeReader.cpp index 8920b6e..7e760e2 100644 --- a/llvm/lib/Bitcode/Reader/BitcodeReader.cpp +++ b/llvm/lib/Bitcode/Reader/BitcodeReader.cpp @@ -271,6 +271,9 @@ public: /// \returns true if an error occurred. ErrorOr parseTriple(); + /// Cheap mechanism to just extract the identification block out of bitcode. + ErrorOr parseIdentificationBlock(); + static uint64_t decodeSignRotatedValue(uint64_t V); /// Materialize any deferred Metadata block. @@ -3729,6 +3732,41 @@ ErrorOr BitcodeReader::parseTriple() { } } +ErrorOr BitcodeReader::parseIdentificationBlock() { + if (std::error_code EC = initStream(nullptr)) + return EC; + + // Sniff for the signature. + if (!hasValidBitcodeHeader(Stream)) + return error("Invalid bitcode signature"); + + // We expect a number of well-defined blocks, though we don't necessarily + // need to understand them all. + while (1) { + BitstreamEntry Entry = Stream.advance(); + switch (Entry.Kind) { + case BitstreamEntry::Error: + return error("Malformed block"); + case BitstreamEntry::EndBlock: + return std::error_code(); + + case BitstreamEntry::SubBlock: + if (Entry.ID == bitc::IDENTIFICATION_BLOCK_ID) { + if (std::error_code EC = parseBitcodeVersion()) + return EC; + return ProducerIdentification; + } + // Ignore other sub-blocks. + if (Stream.SkipBlock()) + return error("Malformed block"); + continue; + case BitstreamEntry::Record: + Stream.skipRecord(Entry.ID); + continue; + } + } +} + /// Parse metadata attachments. std::error_code BitcodeReader::parseMetadataAttachment(Function &F) { if (Stream.EnterSubBlock(bitc::METADATA_ATTACHMENT_ID)) @@ -5835,6 +5873,17 @@ llvm::getBitcodeTargetTriple(MemoryBufferRef Buffer, LLVMContext &Context, return Triple.get(); } +std::string +llvm::getBitcodeProducerString(MemoryBufferRef Buffer, LLVMContext &Context, + DiagnosticHandlerFunction DiagnosticHandler) { + std::unique_ptr Buf = MemoryBuffer::getMemBuffer(Buffer, false); + BitcodeReader R(Buf.release(), Context, DiagnosticHandler); + ErrorOr ProducerString = R.parseIdentificationBlock(); + if (ProducerString.getError()) + return ""; + return ProducerString.get(); +} + // Parse the specified bitcode buffer, returning the function info index. // If IsLazy is false, parse the entire function summary into // the index. Otherwise skip the function summary section, and only create -- cgit v1.1