Change BitcodeReader to use error_code instead of bool + string.

In order to create an ObjectFile implementation that uses bitcode files, we
need to propagate the bitcode errors to the ObjectFile interface, so we need
to convert it to use the same error handling as ObjectFile: error_code.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@193996 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Rafael Espindola 2013-11-04 16:16:24 +00:00
parent 5c042162be
commit e076b5338a
4 changed files with 494 additions and 380 deletions

File diff suppressed because it is too large Load Diff

View File

@ -21,6 +21,7 @@
#include "llvm/IR/Attributes.h"
#include "llvm/IR/OperandTraits.h"
#include "llvm/IR/Type.h"
#include "llvm/Support/system_error.h"
#include "llvm/Support/ValueHandle.h"
#include <vector>
@ -132,8 +133,6 @@ class BitcodeReader : public GVMaterializer {
uint64_t NextUnreadBit;
bool SeenValueSymbolTable;
const char *ErrorString;
std::vector<Type*> TypeList;
BitcodeReaderValueList ValueList;
BitcodeReaderMDValueList MDValueList;
@ -194,17 +193,46 @@ class BitcodeReader : public GVMaterializer {
/// not need this flag.
bool UseRelativeIDs;
static const error_category &BitcodeErrorCategory();
public:
enum ErrorType {
BitcodeStreamInvalidSize,
ConflictingMETADATA_KINDRecords,
CouldNotFindFunctionInStream,
ExpectedConstant,
InsufficientFunctionProtos,
InvalidBitcodeSignature,
InvalidBitcodeWrapperHeader,
InvalidConstantReference,
InvalidID, // A read identifier is not found in the table it should be in.
InvalidInstructionWithNoBB,
InvalidRecord, // A read record doesn't have the expected size or structure
InvalidTypeForValue, // Type read OK, but is invalid for its use
InvalidTYPETable,
InvalidType, // We were unable to read a type
MalformedBlock, // We are unable to advance in the stream.
MalformedGlobalInitializerSet,
InvalidMultipleBlocks, // We found multiple blocks of a kind that should
// have only one
NeverResolvedValueFoundInFunction,
InvalidValue // Invalid version, inst number, attr number, etc
};
error_code Error(ErrorType E) {
return error_code(E, BitcodeErrorCategory());
}
explicit BitcodeReader(MemoryBuffer *buffer, LLVMContext &C)
: Context(C), TheModule(0), Buffer(buffer), BufferOwned(false),
LazyStreamer(0), NextUnreadBit(0), SeenValueSymbolTable(false),
ErrorString(0), ValueList(C), MDValueList(C),
ValueList(C), MDValueList(C),
SeenFirstFunctionBody(false), UseRelativeIDs(false) {
}
explicit BitcodeReader(DataStreamer *streamer, LLVMContext &C)
: Context(C), TheModule(0), Buffer(0), BufferOwned(false),
LazyStreamer(streamer), NextUnreadBit(0), SeenValueSymbolTable(false),
ErrorString(0), ValueList(C), MDValueList(C),
ValueList(C), MDValueList(C),
SeenFirstFunctionBody(false), UseRelativeIDs(false) {
}
~BitcodeReader() {
@ -225,19 +253,13 @@ public:
virtual bool MaterializeModule(Module *M, std::string *ErrInfo = 0);
virtual void Dematerialize(GlobalValue *GV);
bool Error(const char *Str) {
ErrorString = Str;
return true;
}
const char *getErrorString() const { return ErrorString; }
/// @brief Main interface to parsing a bitcode buffer.
/// @returns true if an error occurred.
bool ParseBitcodeInto(Module *M);
error_code ParseBitcodeInto(Module *M);
/// @brief Cheap mechanism to just extract module triple
/// @returns true if an error occurred.
bool ParseTriple(std::string &Triple);
error_code ParseTriple(std::string &Triple);
static uint64_t decodeSignRotatedValue(uint64_t V);
@ -324,26 +346,26 @@ private:
return getFnValueByID(ValNo, Ty);
}
bool ParseAttrKind(uint64_t Code, Attribute::AttrKind *Kind);
bool ParseModule(bool Resume);
bool ParseAttributeBlock();
bool ParseAttributeGroupBlock();
bool ParseTypeTable();
bool ParseTypeTableBody();
error_code ParseAttrKind(uint64_t Code, Attribute::AttrKind *Kind);
error_code ParseModule(bool Resume);
error_code ParseAttributeBlock();
error_code ParseAttributeGroupBlock();
error_code ParseTypeTable();
error_code ParseTypeTableBody();
bool ParseValueSymbolTable();
bool ParseConstants();
bool RememberAndSkipFunctionBody();
bool ParseFunctionBody(Function *F);
bool GlobalCleanup();
bool ResolveGlobalAndAliasInits();
bool ParseMetadata();
bool ParseMetadataAttachment();
bool ParseModuleTriple(std::string &Triple);
bool ParseUseLists();
bool InitStream();
bool InitStreamFromBuffer();
bool InitLazyStream();
error_code ParseValueSymbolTable();
error_code ParseConstants();
error_code RememberAndSkipFunctionBody();
error_code ParseFunctionBody(Function *F);
error_code GlobalCleanup();
error_code ResolveGlobalAndAliasInits();
error_code ParseMetadata();
error_code ParseMetadataAttachment();
error_code ParseModuleTriple(std::string &Triple);
error_code ParseUseLists();
error_code InitStream();
error_code InitStreamFromBuffer();
error_code InitLazyStream();
bool FindFunctionInStream(Function *F,
DenseMap<Function*, uint64_t>::iterator DeferredFunctionInfoIterator);
};

View File

@ -1,6 +1,6 @@
; RUN: not llvm-dis < %s.bc 2>&1 | FileCheck %s
; CHECK: llvm-dis{{(\.EXE|\.exe)?}}: Unknown attribute kind
; CHECK: llvm-dis{{(\.EXE|\.exe)?}}: Invalid value
; invalid.ll.bc has an invalid attribute number.
; The test checks that LLVM reports the error and doesn't access freed memory

View File

@ -1,4 +1,4 @@
; RUN: not llvm-dis < %s.bc 2>&1 | FileCheck %s
; PR8494
; CHECK: Invalid MODULE_CODE_FUNCTION record
; CHECK: Invalid record