Preserve module source information in the ModuleID
[oota-llvm.git] / lib / Bytecode / Reader / ReaderInternals.h
1 //===-- ReaderInternals.h - Definitions internal to the reader ---*- C++ -*--=//
2 //
3 //  This header file defines various stuff that is used by the bytecode reader.
4 //
5 //===----------------------------------------------------------------------===//
6
7 #ifndef READER_INTERNALS_H
8 #define READER_INTERNALS_H
9
10 #include "llvm/Bytecode/Primitives.h"
11 #include "llvm/DerivedTypes.h"
12 #include "llvm/Function.h"
13 #include "llvm/Constant.h"
14 #include <utility>
15 #include <map>
16
17 // Enable to trace to figure out what the heck is going on when parsing fails
18 #define TRACE_LEVEL 0
19
20 #if TRACE_LEVEL    // ByteCodeReading_TRACEer
21 #define BCR_TRACE(n, X) \
22     if (n < TRACE_LEVEL) std::cerr << std::string(n*2, ' ') << X
23 #else
24 #define BCR_TRACE(n, X)
25 #endif
26
27 typedef unsigned char uchar;
28
29 struct RawInst {       // The raw fields out of the bytecode stream...
30   unsigned NumOperands;
31   unsigned Opcode;
32   const Type *Ty;
33   unsigned Arg1, Arg2;
34   union {
35     unsigned Arg3;
36     std::vector<unsigned> *VarArgs; // Contains arg #3,4,5... if NumOperands > 3
37   };
38 };
39
40 class BytecodeParser : public AbstractTypeUser {
41   std::string Error;     // Error message string goes here...
42   BytecodeParser(const BytecodeParser &);  // DO NOT IMPLEMENT
43   void operator=(const BytecodeParser &);  // DO NOT IMPLEMENT
44 public:
45   BytecodeParser() {
46     // Define this in case we don't see a ModuleGlobalInfo block.
47     FirstDerivedTyID = Type::FirstDerivedTyID;
48   }
49   ~BytecodeParser() {
50     freeTable(Values);
51     freeTable(LateResolveValues);
52     freeTable(ModuleValues);
53   }
54
55   Module *ParseBytecode(const uchar *Buf, const uchar *EndBuf,
56                         const std::string &ModuleID);
57
58   std::string getError() const { return Error; }
59
60   void dump() const {
61     std::cerr << "BytecodeParser instance!\n";
62   }
63
64 private:          // All of this data is transient across calls to ParseBytecode
65   struct ValueList : public User {
66     ValueList() : User(Type::TypeTy, Value::TypeVal) {
67     }
68     ~ValueList() {}
69
70     // vector compatibility methods
71     unsigned size() const { return getNumOperands(); }
72     void push_back(Value *V) { Operands.push_back(Use(V, this)); }
73     Value *back() const { return Operands.back(); }
74     void pop_back() { Operands.pop_back(); }
75     bool empty() const { return Operands.empty(); }
76
77     virtual void print(std::ostream& OS) const {
78       OS << "Bytecode Reader UseHandle!";
79     }
80   };
81
82   Module *TheModule;   // Current Module being read into...
83   
84   // Information about the module, extracted from the bytecode revision number.
85   unsigned char RevisionNum;        // The rev # itself
86   unsigned char FirstDerivedTyID;   // First variable index to use for type
87   bool HasImplicitZeroInitializer;  // Is entry 0 of every slot implicity zeros?
88   bool isBigEndian, hasLongPointers;// Information about the target compiled for
89   bool hasInternalMarkerOnly;       // Only types of linkage are intern/external
90
91   typedef std::vector<ValueList*> ValueTable;
92   ValueTable Values, LateResolveValues;
93   ValueTable ModuleValues;
94
95   // GlobalRefs - This maintains a mapping between <Type, Slot #>'s and forward
96   // references to global values or constants.  Such values may be referenced
97   // before they are defined, and if so, the temporary object that they
98   // represent is held here.
99   //
100   typedef std::map<std::pair<const Type *, unsigned>, Value*>  GlobalRefsType;
101   GlobalRefsType GlobalRefs;
102
103   // TypesLoaded - This vector mirrors the Values[TypeTyID] plane.  It is used
104   // to deal with forward references to types.
105   //
106   typedef std::vector<PATypeHandle<Type> > TypeValuesListTy;
107   TypeValuesListTy ModuleTypeValues;
108   TypeValuesListTy FunctionTypeValues;
109
110   // When the ModuleGlobalInfo section is read, we create a function object for
111   // each function in the module.  When the function is loaded, this function is
112   // filled in.
113   //
114   std::vector<std::pair<Function*, unsigned> > FunctionSignatureList;
115
116   // Constant values are read in after global variables.  Because of this, we
117   // must defer setting the initializers on global variables until after module
118   // level constants have been read.  In the mean time, this list keeps track of
119   // what we must do.
120   //
121   std::vector<std::pair<GlobalVariable*, unsigned> > GlobalInits;
122
123 private:
124   void freeTable(ValueTable &Tab) {
125     while (!Tab.empty()) {
126       delete Tab.back();
127       Tab.pop_back();
128     }
129   }
130
131   bool ParseModule          (const uchar * Buf, const uchar *End);
132   bool ParseVersionInfo     (const uchar *&Buf, const uchar *End);
133   bool ParseModuleGlobalInfo(const uchar *&Buf, const uchar *End);
134   bool ParseSymbolTable   (const uchar *&Buf, const uchar *End, SymbolTable *);
135   bool ParseFunction      (const uchar *&Buf, const uchar *End);
136   bool ParseBasicBlock    (const uchar *&Buf, const uchar *End, BasicBlock *&);
137   bool ParseInstruction   (const uchar *&Buf, const uchar *End, Instruction *&,
138                            BasicBlock *BB /*HACK*/);
139   bool ParseRawInst       (const uchar *&Buf, const uchar *End, RawInst &);
140
141   bool ParseGlobalTypes(const uchar *&Buf, const uchar *EndBuf);
142   bool ParseConstantPool(const uchar *&Buf, const uchar *EndBuf,
143                          ValueTable &Tab, TypeValuesListTy &TypeTab);
144   bool parseConstantValue(const uchar *&Buf, const uchar *End,
145                           const Type *Ty, Constant *&V);
146   bool parseTypeConstants(const uchar *&Buf, const uchar *EndBuf,
147                           TypeValuesListTy &Tab, unsigned NumEntries);
148   const Type *parseTypeConstant(const uchar *&Buf, const uchar *EndBuf);
149
150   Value      *getValue(const Type *Ty, unsigned num, bool Create = true);
151   const Type *getType(unsigned ID);
152   Constant   *getConstantValue(const Type *Ty, unsigned num);
153
154   int insertValue(Value *V, ValueTable &Table);  // -1 = Failure
155   void setValueTo(ValueTable &D, unsigned Slot, Value *V);
156   bool postResolveValues(ValueTable &ValTab);
157
158   bool getTypeSlot(const Type *Ty, unsigned &Slot);
159
160   // resolve all references to the placeholder (if any) for the given value
161   void ResolveReferencesToValue(Value *Val, unsigned Slot);
162
163   
164   // refineAbstractType - The callback method is invoked when one of the
165   // elements of TypeValues becomes more concrete...
166   //
167   virtual void refineAbstractType(const DerivedType *OldTy, const Type *NewTy);
168 };
169
170 template<class SuperType>
171 class PlaceholderDef : public SuperType {
172   unsigned ID;
173   PlaceholderDef();                       // DO NOT IMPLEMENT
174   void operator=(const PlaceholderDef &); // DO NOT IMPLEMENT
175 public:
176   PlaceholderDef(const Type *Ty, unsigned id) : SuperType(Ty), ID(id) {}
177   unsigned getID() { return ID; }
178 };
179
180 struct InstPlaceHolderHelper : public Instruction {
181   InstPlaceHolderHelper(const Type *Ty) : Instruction(Ty, UserOp1, "") {}
182   virtual const char *getOpcodeName() const { return "placeholder"; }
183
184   virtual Instruction *clone() const { abort(); return 0; }
185 };
186
187 struct BBPlaceHolderHelper : public BasicBlock {
188   BBPlaceHolderHelper(const Type *Ty) : BasicBlock() {
189     assert(Ty == Type::LabelTy);
190   }
191 };
192
193 struct ConstantPlaceHolderHelper : public Constant {
194   ConstantPlaceHolderHelper(const Type *Ty)
195     : Constant(Ty) {}
196   virtual bool isNullValue() const { return false; }
197 };
198
199 typedef PlaceholderDef<InstPlaceHolderHelper>  ValPHolder;
200 typedef PlaceholderDef<BBPlaceHolderHelper>    BBPHolder;
201 typedef PlaceholderDef<ConstantPlaceHolderHelper>  ConstPHolder;
202
203
204 static inline unsigned getValueIDNumberFromPlaceHolder(Value *Val) {
205   if (isa<Constant>(Val))
206     return ((ConstPHolder*)Val)->getID();
207   
208   // else discriminate by type
209   switch (Val->getType()->getPrimitiveID()) {
210   case Type::LabelTyID:    return ((BBPHolder*)Val)->getID();
211   default:                 return ((ValPHolder*)Val)->getID();
212   }
213 }
214
215 static inline bool readBlock(const uchar *&Buf, const uchar *EndBuf, 
216                              unsigned &Type, unsigned &Size) {
217 #if DEBUG_OUTPUT
218   bool Result = read(Buf, EndBuf, Type) || read(Buf, EndBuf, Size);
219   std::cerr << "StartLoc = " << ((unsigned)Buf & 4095)
220        << " Type = " << Type << " Size = " << Size << endl;
221   return Result;
222 #else
223   return read(Buf, EndBuf, Type) || read(Buf, EndBuf, Size);
224 #endif
225 }
226
227 #endif