From 91ac04aa86129b1017f04bd0a361b293f0562614 Mon Sep 17 00:00:00 2001 From: Reid Spencer Date: Mon, 9 Apr 2007 06:14:31 +0000 Subject: [PATCH] For PR1146: Use ParamAttrsList for writing parameter attributes. Since they are sparse now, we also write them sparsely (saves a few bytes). Unfortunately, this is a bytecode file format change. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@35811 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Bytecode/Reader/Reader.cpp | 30 +++++++++++++------ lib/Bytecode/Reader/Reader.h | 4 +++ lib/Bytecode/Writer/SlotCalculator.cpp | 9 ++++-- lib/Bytecode/Writer/SlotCalculator.h | 2 +- lib/Bytecode/Writer/Writer.cpp | 40 +++++++++++++++++--------- lib/Bytecode/Writer/WriterInternals.h | 2 ++ 6 files changed, 62 insertions(+), 25 deletions(-) diff --git a/lib/Bytecode/Reader/Reader.cpp b/lib/Bytecode/Reader/Reader.cpp index 82b1888e6aa..ffb731f3141 100644 --- a/lib/Bytecode/Reader/Reader.cpp +++ b/lib/Bytecode/Reader/Reader.cpp @@ -23,6 +23,7 @@ #include "llvm/Constants.h" #include "llvm/InlineAsm.h" #include "llvm/Instructions.h" +#include "llvm/ParameterAttributes.h" #include "llvm/TypeSymbolTable.h" #include "llvm/Bytecode/Format.h" #include "llvm/Config/alloca.h" @@ -288,6 +289,8 @@ Value * BytecodeReader::getValue(unsigned type, unsigned oNum, bool Create) { if (Num < Locals->size()) return Locals->getOperand(Num); + // We did not find the value. + if (!Create) return 0; // Do not create a placeholder? // Did we already create a place holder? @@ -1005,21 +1008,18 @@ const Type *BytecodeReader::ParseType() { } case Type::FunctionTyID: { const Type *RetType = readType(); - unsigned RetAttr = read_vbr_uint(); - unsigned NumParams = read_vbr_uint(); std::vector Params; - std::vector Attrs; - Attrs.push_back(FunctionType::ParameterAttributes(RetAttr)); while (NumParams--) { Params.push_back(readType()); - if (Params.back() != Type::VoidTy) - Attrs.push_back(FunctionType::ParameterAttributes(read_vbr_uint())); } bool isVarArg = Params.size() && Params.back() == Type::VoidTy; - if (isVarArg) Params.pop_back(); + if (isVarArg) + Params.pop_back(); + + ParamAttrsList *Attrs = ParseParamAttrsList(); Result = FunctionType::get(RetType, Params, isVarArg, Attrs); break; @@ -1076,6 +1076,21 @@ const Type *BytecodeReader::ParseType() { return Result; } +ParamAttrsList *BytecodeReader::ParseParamAttrsList() { + unsigned NumAttrs = read_vbr_uint(); + ParamAttrsList *Attrs = 0; + if (NumAttrs) { + Attrs = new ParamAttrsList(); + while (NumAttrs--) { + uint16_t index = read_vbr_uint(); + uint16_t attrs = read_vbr_uint(); + Attrs->addAttributes(index, attrs); + } + } + return Attrs; +} + + // ParseTypes - We have to use this weird code to handle recursive // types. We know that recursive types will only reference the current slab of // values in the type plane, but they can forward reference types before they @@ -2106,4 +2121,3 @@ bool BytecodeReader::ParseBytecode(volatile BufPtr Buf, unsigned Length, //===----------------------------------------------------------------------===// BytecodeHandler::~BytecodeHandler() {} - diff --git a/lib/Bytecode/Reader/Reader.h b/lib/Bytecode/Reader/Reader.h index 8da286b6ccc..c852cce6bab 100644 --- a/lib/Bytecode/Reader/Reader.h +++ b/lib/Bytecode/Reader/Reader.h @@ -236,6 +236,7 @@ protected: /// @brief Parse global types void ParseGlobalTypes(); + /// @brief Parse a basic block (for LLVM 1.0 basic block blocks) BasicBlock* ParseBasicBlock(unsigned BlockNo); @@ -264,6 +265,9 @@ protected: /// @brief Parse a single type constant const Type *ParseType(); + /// @brief Parse a list of parameter attributes + ParamAttrsList *ParseParamAttrsList(); + /// @brief Parse a string constants block void ParseStringConstants(unsigned NumEntries, ValueTable &Tab); diff --git a/lib/Bytecode/Writer/SlotCalculator.cpp b/lib/Bytecode/Writer/SlotCalculator.cpp index 43ad922e2b7..85ccad58c5b 100644 --- a/lib/Bytecode/Writer/SlotCalculator.cpp +++ b/lib/Bytecode/Writer/SlotCalculator.cpp @@ -332,6 +332,10 @@ void SlotCalculator::purgeFunction() { SC_DEBUG("end purgeFunction!\n"); } +inline static bool hasImplicitNull(const Type* Ty) { + return Ty != Type::LabelTy && Ty != Type::VoidTy && !isa(Ty); +} + void SlotCalculator::CreateFunctionValueSlot(const Value *V) { assert(!NodeMap.count(V) && "Function-local value can't be inserted!"); @@ -353,7 +357,7 @@ void SlotCalculator::CreateFunctionValueSlot(const Value *V) { // to insert the implicit null value. if (Table[TyPlane].empty()) { // Label's and opaque types can't have a null value. - if (Ty != Type::LabelTy && !isa(Ty)) { + if (hasImplicitNull(Ty)) { Value *ZeroInitializer = Constant::getNullValue(Ty); // If we are pushing zeroinit, it will be handled below. @@ -370,5 +374,4 @@ void SlotCalculator::CreateFunctionValueSlot(const Value *V) { SC_DEBUG(" Inserting value [" << TyPlane << "] = " << *V << " slot=" << NodeMap[V] << "\n"); -} - +} diff --git a/lib/Bytecode/Writer/SlotCalculator.h b/lib/Bytecode/Writer/SlotCalculator.h index d457c6c8a79..343800cf6c8 100644 --- a/lib/Bytecode/Writer/SlotCalculator.h +++ b/lib/Bytecode/Writer/SlotCalculator.h @@ -73,7 +73,7 @@ public: SlotCalculator(const Module *M); /// getSlot - Return the slot number of the specified value in it's type - /// plane. This returns < 0 on error! + /// plane. /// unsigned getSlot(const Value *V) const { NodeMapType::const_iterator I = NodeMap.find(V); diff --git a/lib/Bytecode/Writer/Writer.cpp b/lib/Bytecode/Writer/Writer.cpp index 925ae1f4644..dfc84be0378 100644 --- a/lib/Bytecode/Writer/Writer.cpp +++ b/lib/Bytecode/Writer/Writer.cpp @@ -17,12 +17,13 @@ // //===----------------------------------------------------------------------===// -#define DEBUG_TYPE "bytecodewriter" +#define DEBUG_TYPE "bcwriter" #include "WriterInternals.h" #include "llvm/Bytecode/WriteBytecodePass.h" #include "llvm/CallingConv.h" #include "llvm/Constants.h" #include "llvm/DerivedTypes.h" +#include "llvm/ParameterAttributes.h" #include "llvm/InlineAsm.h" #include "llvm/Instructions.h" #include "llvm/Module.h" @@ -197,6 +198,21 @@ inline BytecodeBlock::~BytecodeBlock() { // Do backpatch when block goes out //=== Constant Output ===// //===----------------------------------------------------------------------===// +void BytecodeWriter::outputParamAttrsList(const ParamAttrsList *Attrs) { + if (!Attrs) { + output_vbr(unsigned(0)); + return; + } + unsigned numAttrs = Attrs->size(); + output_vbr(numAttrs); + for (unsigned i = 0; i < numAttrs; ++i) { + uint16_t index = Attrs->getParamIndex(i); + uint16_t attrs = Attrs->getParamAttrs(index); + output_vbr(uint32_t(index)); + output_vbr(uint32_t(attrs)); + } +} + void BytecodeWriter::outputType(const Type *T) { const StructType* STy = dyn_cast(T); if(STy && STy->isPacked()) @@ -213,25 +229,23 @@ void BytecodeWriter::outputType(const Type *T) { output_vbr(cast(T)->getBitWidth()); break; case Type::FunctionTyID: { - const FunctionType *MT = cast(T); - output_typeid(Table.getTypeSlot(MT->getReturnType())); - output_vbr(unsigned(MT->getParamAttrs(0))); + const FunctionType *FT = cast(T); + output_typeid(Table.getTypeSlot(FT->getReturnType())); // Output the number of arguments to function (+1 if varargs): - output_vbr((unsigned)MT->getNumParams()+MT->isVarArg()); + output_vbr((unsigned)FT->getNumParams()+FT->isVarArg()); // Output all of the arguments... - FunctionType::param_iterator I = MT->param_begin(); - unsigned Idx = 1; - for (; I != MT->param_end(); ++I) { + FunctionType::param_iterator I = FT->param_begin(); + for (; I != FT->param_end(); ++I) output_typeid(Table.getTypeSlot(*I)); - output_vbr(unsigned(MT->getParamAttrs(Idx))); - Idx++; - } // Terminate list with VoidTy if we are a varargs function... - if (MT->isVarArg()) + if (FT->isVarArg()) output_typeid((unsigned)Type::VoidTyID); + + // Put out all the parameter attributes + outputParamAttrsList(FT->getParamAttrs()); break; } @@ -1107,7 +1121,7 @@ void BytecodeWriter::outputValueSymbolTable(const ValueSymbolTable &VST) { // Organize the symbol table by type typedef SmallVector PlaneMapVector; - typedef DenseMap PlaneMap; + typedef DenseMap PlaneMap; PlaneMap Planes; for (ValueSymbolTable::const_iterator SI = VST.begin(), SE = VST.end(); SI != SE; ++SI) diff --git a/lib/Bytecode/Writer/WriterInternals.h b/lib/Bytecode/Writer/WriterInternals.h index 747ad8ef069..c4dbf474a0c 100644 --- a/lib/Bytecode/Writer/WriterInternals.h +++ b/lib/Bytecode/Writer/WriterInternals.h @@ -24,6 +24,7 @@ namespace llvm { class InlineAsm; class TypeSymbolTable; class ValueSymbolTable; + class ParamAttrsList; class BytecodeWriter { std::vector &Out; @@ -61,6 +62,7 @@ private: void outputTypeSymbolTable(const TypeSymbolTable &TST); void outputValueSymbolTable(const ValueSymbolTable &ST); void outputTypes(unsigned StartNo); + void outputParamAttrsList(const ParamAttrsList* Attrs); void outputConstantsInPlane(const Value *const*Plane, unsigned PlaneSize, unsigned StartNo); void outputConstant(const Constant *CPV);