blob: 2f2e7960d602dcc2407fb9682307318899e70727 [file] [log] [blame]
Chris Lattner05950c32001-10-13 06:47:01 +00001//===- ReadInst.cpp - Code to read an instruction from bytecode -----------===//
Chris Lattner00950542001-06-06 20:29:01 +00002//
3// This file defines the mechanism to read an instruction from a bytecode
4// stream.
5//
6// Note that this library should be as fast as possible, reentrant, and
7// threadsafe!!
8//
9// TODO: Change from getValue(Raw.Arg1) etc, to getArg(Raw, 1)
10// Make it check type, so that casts are checked.
11//
Chris Lattner05950c32001-10-13 06:47:01 +000012//===----------------------------------------------------------------------===//
Chris Lattner00950542001-06-06 20:29:01 +000013
Chris Lattner7061dc52001-12-03 18:02:31 +000014#include "ReaderInternals.h"
Chris Lattner00950542001-06-06 20:29:01 +000015#include "llvm/iTerminators.h"
16#include "llvm/iMemory.h"
Chris Lattner7061dc52001-12-03 18:02:31 +000017#include "llvm/iPHINode.h"
18#include "llvm/iOther.h"
Chris Lattner00950542001-06-06 20:29:01 +000019
Misha Brukmand554ebf2003-09-23 16:17:50 +000020std::auto_ptr<RawInst>
21BytecodeParser::ParseRawInst(const unsigned char *&Buf,
22 const unsigned char *EndBuf) {
Chris Lattner00950542001-06-06 20:29:01 +000023 unsigned Op, Typ;
Misha Brukmand554ebf2003-09-23 16:17:50 +000024 std::auto_ptr<RawInst> Result = std::auto_ptr<RawInst>(new RawInst());
25 if (read(Buf, EndBuf, Op))
26 throw std::string("Error reading from buffer.");
Chris Lattner00950542001-06-06 20:29:01 +000027
Chris Lattner2b9f6002001-10-23 03:21:10 +000028 // bits Instruction format: Common to all formats
29 // --------------------------
30 // 01-00: Opcode type, fixed to 1.
31 // 07-02: Opcode
Misha Brukmand554ebf2003-09-23 16:17:50 +000032 Result->NumOperands = (Op >> 0) & 03;
33 Result->Opcode = (Op >> 2) & 63;
Chris Lattner00950542001-06-06 20:29:01 +000034
Misha Brukmand554ebf2003-09-23 16:17:50 +000035 switch (Result->NumOperands) {
Chris Lattner00950542001-06-06 20:29:01 +000036 case 1:
Chris Lattner2b9f6002001-10-23 03:21:10 +000037 // bits Instruction format:
38 // --------------------------
39 // 19-08: Resulting type plane
40 // 31-20: Operand #1 (if set to (2^12-1), then zero operands)
41 //
Misha Brukmand554ebf2003-09-23 16:17:50 +000042 Result->Ty = getType((Op >> 8) & 4095);
43 Result->Arg1 = (Op >> 20) & 4095;
44 if (Result->Arg1 == 4095) // Handle special encoding for 0 operands...
45 Result->NumOperands = 0;
Chris Lattner00950542001-06-06 20:29:01 +000046 break;
47 case 2:
Chris Lattner2b9f6002001-10-23 03:21:10 +000048 // bits Instruction format:
49 // --------------------------
50 // 15-08: Resulting type plane
51 // 23-16: Operand #1
52 // 31-24: Operand #2
53 //
Misha Brukmand554ebf2003-09-23 16:17:50 +000054 Result->Ty = getType((Op >> 8) & 255);
55 Result->Arg1 = (Op >> 16) & 255;
56 Result->Arg2 = (Op >> 24) & 255;
Chris Lattner00950542001-06-06 20:29:01 +000057 break;
58 case 3:
Chris Lattner2b9f6002001-10-23 03:21:10 +000059 // bits Instruction format:
60 // --------------------------
61 // 13-08: Resulting type plane
62 // 19-14: Operand #1
63 // 25-20: Operand #2
64 // 31-26: Operand #3
65 //
Misha Brukmand554ebf2003-09-23 16:17:50 +000066 Result->Ty = getType((Op >> 8) & 63);
67 Result->Arg1 = (Op >> 14) & 63;
68 Result->Arg2 = (Op >> 20) & 63;
69 Result->Arg3 = (Op >> 26) & 63;
Chris Lattner00950542001-06-06 20:29:01 +000070 break;
71 case 0:
72 Buf -= 4; // Hrm, try this again...
Misha Brukmand554ebf2003-09-23 16:17:50 +000073 if (read_vbr(Buf, EndBuf, Result->Opcode))
74 throw std::string("Error reading from buffer.");
75 Result->Opcode >>= 2;
76 if (read_vbr(Buf, EndBuf, Typ))
77 throw std::string("Error reading from buffer.");
78 Result->Ty = getType(Typ);
79 if (Result->Ty == 0)
80 throw std::string("Invalid type read in instruction.");
81 if (read_vbr(Buf, EndBuf, Result->NumOperands))
82 throw std::string("Error reading from buffer.");
Chris Lattner00950542001-06-06 20:29:01 +000083
Misha Brukmand554ebf2003-09-23 16:17:50 +000084 switch (Result->NumOperands) {
Chris Lattner00950542001-06-06 20:29:01 +000085 case 0:
Misha Brukmand554ebf2003-09-23 16:17:50 +000086 throw std::string("Zero-argument instruction found; this is invalid.");
Chris Lattner00950542001-06-06 20:29:01 +000087 case 1:
Misha Brukmand554ebf2003-09-23 16:17:50 +000088 if (read_vbr(Buf, EndBuf, Result->Arg1))
89 throw std::string("Error reading from buffer");
Chris Lattner00950542001-06-06 20:29:01 +000090 break;
91 case 2:
Misha Brukmand554ebf2003-09-23 16:17:50 +000092 if (read_vbr(Buf, EndBuf, Result->Arg1) ||
93 read_vbr(Buf, EndBuf, Result->Arg2))
94 throw std::string("Error reading from buffer");
Chris Lattner00950542001-06-06 20:29:01 +000095 break;
96 case 3:
Misha Brukmand554ebf2003-09-23 16:17:50 +000097 if (read_vbr(Buf, EndBuf, Result->Arg1) ||
98 read_vbr(Buf, EndBuf, Result->Arg2) ||
99 read_vbr(Buf, EndBuf, Result->Arg3))
100 throw std::string("Error reading from buffer");
Chris Lattner00950542001-06-06 20:29:01 +0000101 break;
102 default:
Misha Brukmand554ebf2003-09-23 16:17:50 +0000103 if (read_vbr(Buf, EndBuf, Result->Arg1) ||
104 read_vbr(Buf, EndBuf, Result->Arg2))
105 throw std::string("Error reading from buffer");
Chris Lattner00950542001-06-06 20:29:01 +0000106
107 // Allocate a vector to hold arguments 3, 4, 5, 6 ...
Misha Brukmand554ebf2003-09-23 16:17:50 +0000108 Result->VarArgs = new std::vector<unsigned>(Result->NumOperands-2);
109 for (unsigned a = 0; a < Result->NumOperands-2; a++)
110 if (read_vbr(Buf, EndBuf, (*Result->VarArgs)[a]))
111 throw std::string("Error reading from buffer");
112
Chris Lattner00950542001-06-06 20:29:01 +0000113 break;
114 }
Misha Brukmand554ebf2003-09-23 16:17:50 +0000115 if (align32(Buf, EndBuf))
116 throw std::string("Unaligned bytecode buffer.");
Chris Lattner00950542001-06-06 20:29:01 +0000117 break;
118 }
119
Chris Lattnerc8b25d42001-07-07 08:36:50 +0000120#if 0
Misha Brukmand554ebf2003-09-23 16:17:50 +0000121 std::cerr << "NO: " << Result->NumOperands << " opcode: " << Result->Opcode
122 << " Ty: "<< Result->Ty->getDescription()<< " arg1: "<< Result->Arg1
123 << " arg2: " << Result->Arg2 << " arg3: " << Result->Arg3 << "\n";
Chris Lattnerc8b25d42001-07-07 08:36:50 +0000124#endif
Misha Brukmand554ebf2003-09-23 16:17:50 +0000125 return Result;
Chris Lattner00950542001-06-06 20:29:01 +0000126}
127
128
Chris Lattner12e64652003-05-22 18:08:30 +0000129bool BytecodeParser::ParseInstruction(const unsigned char *&Buf,
130 const unsigned char *EndBuf,
Chris Lattner09bd0252003-09-08 18:04:16 +0000131 Instruction *&Res) {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000132 std::auto_ptr<RawInst> Raw = ParseRawInst(Buf, EndBuf);
Chris Lattner00950542001-06-06 20:29:01 +0000133
Misha Brukmand554ebf2003-09-23 16:17:50 +0000134 if (Raw->Opcode >= Instruction::BinaryOpsBegin &&
135 Raw->Opcode < Instruction::BinaryOpsEnd && Raw->NumOperands == 2) {
136 Res = BinaryOperator::create((Instruction::BinaryOps)Raw->Opcode,
137 getValue(Raw->Ty, Raw->Arg1),
138 getValue(Raw->Ty, Raw->Arg2));
Chris Lattner00950542001-06-06 20:29:01 +0000139 return false;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000140 }
Chris Lattner027dcc52001-07-08 21:10:27 +0000141
142 Value *V;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000143 switch (Raw->Opcode) {
Chris Lattner8f77dae2003-05-08 02:44:12 +0000144 case Instruction::VarArg:
Chris Lattner5ab1f872001-10-21 00:14:44 +0000145 case Instruction::Cast: {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000146 V = getValue(Raw->Ty, Raw->Arg1);
147 const Type *Ty = getType(Raw->Arg2);
Chris Lattner0d75d8d72003-03-06 16:32:25 +0000148 if (V == 0 || Ty == 0) { std::cerr << "Invalid cast!\n"; return true; }
Misha Brukmand554ebf2003-09-23 16:17:50 +0000149 if (Raw->Opcode == Instruction::Cast)
Chris Lattner8f77dae2003-05-08 02:44:12 +0000150 Res = new CastInst(V, Ty);
151 else
152 Res = new VarArgInst(V, Ty);
Chris Lattner09083092001-07-08 04:57:15 +0000153 return false;
Chris Lattner5ab1f872001-10-21 00:14:44 +0000154 }
Chris Lattner027dcc52001-07-08 21:10:27 +0000155 case Instruction::PHINode: {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000156 PHINode *PN = new PHINode(Raw->Ty);
157 switch (Raw->NumOperands) {
Chris Lattneree976f32001-06-11 15:04:40 +0000158 case 0:
159 case 1:
Chris Lattner0d75d8d72003-03-06 16:32:25 +0000160 case 3: std::cerr << "Invalid phi node encountered!\n";
Chris Lattner00950542001-06-06 20:29:01 +0000161 delete PN;
Chris Lattner74734132002-08-17 22:01:27 +0000162 return true;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000163 case 2: PN->addIncoming(getValue(Raw->Ty, Raw->Arg1),
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000164 getBasicBlock(Raw->Arg2));
Chris Lattneree976f32001-06-11 15:04:40 +0000165 break;
Chris Lattner00950542001-06-06 20:29:01 +0000166 default:
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000167 PN->addIncoming(getValue(Raw->Ty, Raw->Arg1),
168 getBasicBlock(Raw->Arg2));
Misha Brukmand554ebf2003-09-23 16:17:50 +0000169 if (Raw->VarArgs->size() & 1) {
Chris Lattner0d75d8d72003-03-06 16:32:25 +0000170 std::cerr << "PHI Node with ODD number of arguments!\n";
Chris Lattneree976f32001-06-11 15:04:40 +0000171 delete PN;
Chris Lattner74734132002-08-17 22:01:27 +0000172 return true;
Chris Lattneree976f32001-06-11 15:04:40 +0000173 } else {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000174 std::vector<unsigned> &args = *Raw->VarArgs;
Chris Lattneree976f32001-06-11 15:04:40 +0000175 for (unsigned i = 0; i < args.size(); i+=2)
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000176 PN->addIncoming(getValue(Raw->Ty, args[i]), getBasicBlock(args[i+1]));
Chris Lattner00950542001-06-06 20:29:01 +0000177 }
Misha Brukmand554ebf2003-09-23 16:17:50 +0000178 delete Raw->VarArgs;
Chris Lattneree976f32001-06-11 15:04:40 +0000179 break;
Chris Lattner00950542001-06-06 20:29:01 +0000180 }
181 Res = PN;
182 return false;
Chris Lattner027dcc52001-07-08 21:10:27 +0000183 }
184
185 case Instruction::Shl:
186 case Instruction::Shr:
Misha Brukmand554ebf2003-09-23 16:17:50 +0000187 Res = new ShiftInst((Instruction::OtherOps)Raw->Opcode,
188 getValue(Raw->Ty, Raw->Arg1),
Chris Lattner36392bc2003-10-08 21:18:57 +0000189 getValue(Type::UByteTyID, Raw->Arg2));
Chris Lattner027dcc52001-07-08 21:10:27 +0000190 return false;
191 case Instruction::Ret:
Misha Brukmand554ebf2003-09-23 16:17:50 +0000192 if (Raw->NumOperands == 0) {
Chris Lattner00950542001-06-06 20:29:01 +0000193 Res = new ReturnInst(); return false;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000194 } else if (Raw->NumOperands == 1) {
195 Res = new ReturnInst(getValue(Raw->Ty, Raw->Arg1)); return false;
Chris Lattner00950542001-06-06 20:29:01 +0000196 }
Chris Lattner027dcc52001-07-08 21:10:27 +0000197 break;
198
199 case Instruction::Br:
Misha Brukmand554ebf2003-09-23 16:17:50 +0000200 if (Raw->NumOperands == 1) {
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000201 Res = new BranchInst(getBasicBlock(Raw->Arg1));
Chris Lattner00950542001-06-06 20:29:01 +0000202 return false;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000203 } else if (Raw->NumOperands == 3) {
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000204 Res = new BranchInst(getBasicBlock(Raw->Arg1), getBasicBlock(Raw->Arg2),
205 getValue(Type::BoolTyID , Raw->Arg3));
Chris Lattner00950542001-06-06 20:29:01 +0000206 return false;
207 }
Chris Lattner027dcc52001-07-08 21:10:27 +0000208 break;
209
210 case Instruction::Switch: {
Chris Lattner00950542001-06-06 20:29:01 +0000211 SwitchInst *I =
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000212 new SwitchInst(getValue(Raw->Ty, Raw->Arg1), getBasicBlock(Raw->Arg2));
Chris Lattner00950542001-06-06 20:29:01 +0000213 Res = I;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000214 if (Raw->NumOperands < 3) return false; // No destinations? Weird.
Chris Lattner00950542001-06-06 20:29:01 +0000215
Misha Brukmand554ebf2003-09-23 16:17:50 +0000216 if (Raw->NumOperands == 3 || Raw->VarArgs->size() & 1) {
Chris Lattner0d75d8d72003-03-06 16:32:25 +0000217 std::cerr << "Switch statement with odd number of arguments!\n";
Chris Lattner00950542001-06-06 20:29:01 +0000218 delete I;
Chris Lattner74734132002-08-17 22:01:27 +0000219 return true;
Chris Lattner00950542001-06-06 20:29:01 +0000220 }
221
Misha Brukmand554ebf2003-09-23 16:17:50 +0000222 std::vector<unsigned> &args = *Raw->VarArgs;
Chris Lattner00950542001-06-06 20:29:01 +0000223 for (unsigned i = 0; i < args.size(); i += 2)
Misha Brukmand554ebf2003-09-23 16:17:50 +0000224 I->addCase(cast<Constant>(getValue(Raw->Ty, args[i])),
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000225 getBasicBlock(args[i+1]));
Chris Lattner00950542001-06-06 20:29:01 +0000226
Misha Brukmand554ebf2003-09-23 16:17:50 +0000227 delete Raw->VarArgs;
Chris Lattner00950542001-06-06 20:29:01 +0000228 return false;
Chris Lattner027dcc52001-07-08 21:10:27 +0000229 }
230
231 case Instruction::Call: {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000232 Value *F = getValue(Raw->Ty, Raw->Arg1);
Chris Lattner5bea4112003-09-05 18:25:29 +0000233 if (F == 0) return true;
Chris Lattner00950542001-06-06 20:29:01 +0000234
Chris Lattner05950c32001-10-13 06:47:01 +0000235 // Check to make sure we have a pointer to method type
Chris Lattner5bea4112003-09-05 18:25:29 +0000236 const PointerType *PTy = dyn_cast<PointerType>(F->getType());
Chris Lattner74734132002-08-17 22:01:27 +0000237 if (PTy == 0) return true;
Chris Lattner5bea4112003-09-05 18:25:29 +0000238 const FunctionType *FTy = dyn_cast<FunctionType>(PTy->getElementType());
239 if (FTy == 0) return true;
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000240
Chris Lattner0d75d8d72003-03-06 16:32:25 +0000241 std::vector<Value *> Params;
Chris Lattner5bea4112003-09-05 18:25:29 +0000242 const FunctionType::ParamTypes &PL = FTy->getParamTypes();
Chris Lattner05950c32001-10-13 06:47:01 +0000243
Chris Lattner5bea4112003-09-05 18:25:29 +0000244 if (!FTy->isVarArg()) {
Chris Lattner2aac6bf2002-04-04 22:19:18 +0000245 FunctionType::ParamTypes::const_iterator It = PL.begin();
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000246
Misha Brukmand554ebf2003-09-23 16:17:50 +0000247 switch (Raw->NumOperands) {
Chris Lattner0d75d8d72003-03-06 16:32:25 +0000248 case 0: std::cerr << "Invalid call instruction encountered!\n";
Chris Lattner74734132002-08-17 22:01:27 +0000249 return true;
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000250 case 1: break;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000251 case 2: Params.push_back(getValue(*It++, Raw->Arg2)); break;
252 case 3: Params.push_back(getValue(*It++, Raw->Arg2));
Chris Lattner74734132002-08-17 22:01:27 +0000253 if (It == PL.end()) return true;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000254 Params.push_back(getValue(*It++, Raw->Arg3)); break;
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000255 default:
Misha Brukmand554ebf2003-09-23 16:17:50 +0000256 Params.push_back(getValue(*It++, Raw->Arg2));
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000257 {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000258 std::vector<unsigned> &args = *Raw->VarArgs;
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000259 for (unsigned i = 0; i < args.size(); i++) {
Chris Lattner74734132002-08-17 22:01:27 +0000260 if (It == PL.end()) return true;
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000261 Params.push_back(getValue(*It++, args[i]));
Chris Lattner5bea4112003-09-05 18:25:29 +0000262 if (Params.back() == 0) return true;
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000263 }
Chris Lattner00950542001-06-06 20:29:01 +0000264 }
Misha Brukmand554ebf2003-09-23 16:17:50 +0000265 delete Raw->VarArgs;
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000266 }
Chris Lattner74734132002-08-17 22:01:27 +0000267 if (It != PL.end()) return true;
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000268 } else {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000269 if (Raw->NumOperands > 2) {
270 std::vector<unsigned> &args = *Raw->VarArgs;
Chris Lattner74734132002-08-17 22:01:27 +0000271 if (args.size() < 1) return true;
Chris Lattnere5a57ee2001-07-25 22:47:55 +0000272
Chris Lattner05950c32001-10-13 06:47:01 +0000273 if ((args.size() & 1) != 0)
Chris Lattner74734132002-08-17 22:01:27 +0000274 return true; // Must be pairs of type/value
Chris Lattner05950c32001-10-13 06:47:01 +0000275 for (unsigned i = 0; i < args.size(); i+=2) {
276 const Type *Ty = getType(args[i]);
277 if (Ty == 0)
Chris Lattner74734132002-08-17 22:01:27 +0000278 return true;
Chris Lattner05950c32001-10-13 06:47:01 +0000279
280 Value *V = getValue(Ty, args[i+1]);
Chris Lattner74734132002-08-17 22:01:27 +0000281 if (V == 0) return true;
Chris Lattner05950c32001-10-13 06:47:01 +0000282 Params.push_back(V);
283 }
Misha Brukmand554ebf2003-09-23 16:17:50 +0000284 delete Raw->VarArgs;
Chris Lattner00950542001-06-06 20:29:01 +0000285 }
Chris Lattner00950542001-06-06 20:29:01 +0000286 }
Chris Lattner00950542001-06-06 20:29:01 +0000287
Chris Lattner5bea4112003-09-05 18:25:29 +0000288 Res = new CallInst(F, Params);
Chris Lattner00950542001-06-06 20:29:01 +0000289 return false;
Chris Lattner027dcc52001-07-08 21:10:27 +0000290 }
Chris Lattner05950c32001-10-13 06:47:01 +0000291 case Instruction::Invoke: {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000292 Value *F = getValue(Raw->Ty, Raw->Arg1);
Chris Lattner5bea4112003-09-05 18:25:29 +0000293 if (F == 0) return true;
Chris Lattner05950c32001-10-13 06:47:01 +0000294
295 // Check to make sure we have a pointer to method type
Chris Lattner5bea4112003-09-05 18:25:29 +0000296 const PointerType *PTy = dyn_cast<PointerType>(F->getType());
Chris Lattner74734132002-08-17 22:01:27 +0000297 if (PTy == 0) return true;
Chris Lattner5bea4112003-09-05 18:25:29 +0000298 const FunctionType *FTy = dyn_cast<FunctionType>(PTy->getElementType());
299 if (FTy == 0) return true;
Chris Lattner05950c32001-10-13 06:47:01 +0000300
Chris Lattner0d75d8d72003-03-06 16:32:25 +0000301 std::vector<Value *> Params;
Chris Lattner5bea4112003-09-05 18:25:29 +0000302 const FunctionType::ParamTypes &PL = FTy->getParamTypes();
Misha Brukmand554ebf2003-09-23 16:17:50 +0000303 std::vector<unsigned> &args = *Raw->VarArgs;
Chris Lattner05950c32001-10-13 06:47:01 +0000304
305 BasicBlock *Normal, *Except;
306
Chris Lattner5bea4112003-09-05 18:25:29 +0000307 if (!FTy->isVarArg()) {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000308 if (Raw->NumOperands < 3) return true;
Chris Lattner05950c32001-10-13 06:47:01 +0000309
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000310 Normal = getBasicBlock(Raw->Arg2);
Misha Brukmand554ebf2003-09-23 16:17:50 +0000311 if (Raw->NumOperands == 3)
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000312 Except = getBasicBlock(Raw->Arg3);
Chris Lattnereaeaad62003-06-17 13:31:10 +0000313 else {
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000314 Except = getBasicBlock(args[0]);
Chris Lattner05950c32001-10-13 06:47:01 +0000315
Chris Lattnereaeaad62003-06-17 13:31:10 +0000316 FunctionType::ParamTypes::const_iterator It = PL.begin();
317 for (unsigned i = 1; i < args.size(); i++) {
318 if (It == PL.end()) return true;
Chris Lattnereaeaad62003-06-17 13:31:10 +0000319 Params.push_back(getValue(*It++, args[i]));
Chris Lattner5bea4112003-09-05 18:25:29 +0000320 if (Params.back() == 0) return true;
Chris Lattnereaeaad62003-06-17 13:31:10 +0000321 }
322 if (It != PL.end()) return true;
Chris Lattner05950c32001-10-13 06:47:01 +0000323 }
Chris Lattner05950c32001-10-13 06:47:01 +0000324 } else {
Chris Lattner74734132002-08-17 22:01:27 +0000325 if (args.size() < 4) return true;
Chris Lattner4ee8ef22003-10-08 22:52:54 +0000326 if (args[0] != Type::LabelTyID || args[2] != Type::LabelTyID)
327 return true;
328
329 Normal = getBasicBlock(args[1]);
330 Except = getBasicBlock(args[3]);
Chris Lattner05950c32001-10-13 06:47:01 +0000331
332 if ((args.size() & 1) != 0)
Chris Lattner74734132002-08-17 22:01:27 +0000333 return true; // Must be pairs of type/value
Chris Lattner05950c32001-10-13 06:47:01 +0000334 for (unsigned i = 4; i < args.size(); i+=2) {
Chris Lattner36392bc2003-10-08 21:18:57 +0000335 Params.push_back(getValue(args[i], args[i+1]));
Chris Lattner5bea4112003-09-05 18:25:29 +0000336 if (Params.back() == 0) return true;
Chris Lattner05950c32001-10-13 06:47:01 +0000337 }
338 }
339
Misha Brukmand554ebf2003-09-23 16:17:50 +0000340 if (Raw->NumOperands > 3)
341 delete Raw->VarArgs;
Chris Lattner5bea4112003-09-05 18:25:29 +0000342 Res = new InvokeInst(F, Normal, Except, Params);
Chris Lattner05950c32001-10-13 06:47:01 +0000343 return false;
344 }
Chris Lattner027dcc52001-07-08 21:10:27 +0000345 case Instruction::Malloc:
Misha Brukmand554ebf2003-09-23 16:17:50 +0000346 if (Raw->NumOperands > 2) return true;
Chris Lattner36392bc2003-10-08 21:18:57 +0000347 V = Raw->NumOperands ? getValue(Type::UIntTyID, Raw->Arg1) : 0;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000348 if (const PointerType *PTy = dyn_cast<PointerType>(Raw->Ty))
Chris Lattnere87e1c92002-09-13 22:28:50 +0000349 Res = new MallocInst(PTy->getElementType(), V);
350 else
351 return true;
Chris Lattner00950542001-06-06 20:29:01 +0000352 return false;
Chris Lattner027dcc52001-07-08 21:10:27 +0000353
354 case Instruction::Alloca:
Misha Brukmand554ebf2003-09-23 16:17:50 +0000355 if (Raw->NumOperands > 2) return true;
Chris Lattner36392bc2003-10-08 21:18:57 +0000356 V = Raw->NumOperands ? getValue(Type::UIntTyID, Raw->Arg1) : 0;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000357 if (const PointerType *PTy = dyn_cast<PointerType>(Raw->Ty))
Chris Lattnere87e1c92002-09-13 22:28:50 +0000358 Res = new AllocaInst(PTy->getElementType(), V);
359 else
360 return true;
Chris Lattner00950542001-06-06 20:29:01 +0000361 return false;
Chris Lattner027dcc52001-07-08 21:10:27 +0000362
363 case Instruction::Free:
Misha Brukmand554ebf2003-09-23 16:17:50 +0000364 V = getValue(Raw->Ty, Raw->Arg1);
Chris Lattner74734132002-08-17 22:01:27 +0000365 if (!isa<PointerType>(V->getType())) return true;
Chris Lattner027dcc52001-07-08 21:10:27 +0000366 Res = new FreeInst(V);
367 return false;
368
Chris Lattnerab5ac6b2001-07-08 23:22:50 +0000369 case Instruction::GetElementPtr: {
Chris Lattner0d75d8d72003-03-06 16:32:25 +0000370 std::vector<Value*> Idx;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000371 if (!isa<PointerType>(Raw->Ty)) return true;
372 const CompositeType *TopTy = dyn_cast<CompositeType>(Raw->Ty);
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000373
Misha Brukmand554ebf2003-09-23 16:17:50 +0000374 switch (Raw->NumOperands) {
Chris Lattner09bd0252003-09-08 18:04:16 +0000375 case 0: std::cerr << "Invalid getelementptr encountered!\n"; return true;
Chris Lattner027dcc52001-07-08 21:10:27 +0000376 case 1: break;
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000377 case 2:
Chris Lattner74734132002-08-17 22:01:27 +0000378 if (!TopTy) return true;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000379 Idx.push_back(V = getValue(TopTy->getIndexType(), Raw->Arg2));
Chris Lattner74734132002-08-17 22:01:27 +0000380 if (!V) return true;
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000381 break;
382 case 3: {
Chris Lattner74734132002-08-17 22:01:27 +0000383 if (!TopTy) return true;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000384 Idx.push_back(V = getValue(TopTy->getIndexType(), Raw->Arg2));
Chris Lattner74734132002-08-17 22:01:27 +0000385 if (!V) return true;
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000386
Chris Lattnercc63f1c2002-08-22 23:37:20 +0000387 const Type *ETy = GetElementPtrInst::getIndexedType(TopTy, Idx, true);
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000388 const CompositeType *ElTy = dyn_cast_or_null<CompositeType>(ETy);
Chris Lattner74734132002-08-17 22:01:27 +0000389 if (!ElTy) return true;
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000390
Misha Brukmand554ebf2003-09-23 16:17:50 +0000391 Idx.push_back(V = getValue(ElTy->getIndexType(), Raw->Arg3));
Chris Lattner74734132002-08-17 22:01:27 +0000392 if (!V) return true;
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000393 break;
394 }
Chris Lattner027dcc52001-07-08 21:10:27 +0000395 default:
Chris Lattner74734132002-08-17 22:01:27 +0000396 if (!TopTy) return true;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000397 Idx.push_back(V = getValue(TopTy->getIndexType(), Raw->Arg2));
Chris Lattner74734132002-08-17 22:01:27 +0000398 if (!V) return true;
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000399
Misha Brukmand554ebf2003-09-23 16:17:50 +0000400 std::vector<unsigned> &args = *Raw->VarArgs;
Chris Lattner027dcc52001-07-08 21:10:27 +0000401 for (unsigned i = 0, E = args.size(); i != E; ++i) {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000402 const Type *ETy = GetElementPtrInst::getIndexedType(Raw->Ty, Idx, true);
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000403 const CompositeType *ElTy = dyn_cast_or_null<CompositeType>(ETy);
Chris Lattner74734132002-08-17 22:01:27 +0000404 if (!ElTy) return true;
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000405 Idx.push_back(V = getValue(ElTy->getIndexType(), args[i]));
Chris Lattner74734132002-08-17 22:01:27 +0000406 if (!V) return true;
Chris Lattner027dcc52001-07-08 21:10:27 +0000407 }
Misha Brukmand554ebf2003-09-23 16:17:50 +0000408 delete Raw->VarArgs;
Chris Lattner027dcc52001-07-08 21:10:27 +0000409 break;
410 }
Chris Lattner77a316a2001-11-12 21:48:38 +0000411
Misha Brukmand554ebf2003-09-23 16:17:50 +0000412 Res = new GetElementPtrInst(getValue(Raw->Ty, Raw->Arg1), Idx);
Chris Lattnerab5ac6b2001-07-08 23:22:50 +0000413 return false;
414 }
Chris Lattner09bd0252003-09-08 18:04:16 +0000415
Chris Lattnerdba2b222003-09-08 18:20:14 +0000416 case 62: // volatile load
Chris Lattner09bd0252003-09-08 18:04:16 +0000417 case Instruction::Load:
Misha Brukmand554ebf2003-09-23 16:17:50 +0000418 if (Raw->NumOperands != 1) return true;
419 if (!isa<PointerType>(Raw->Ty)) return true;
420 Res = new LoadInst(getValue(Raw->Ty, Raw->Arg1), "", Raw->Opcode == 62);
Chris Lattner09bd0252003-09-08 18:04:16 +0000421 return false;
Chris Lattnerb2b12b42001-11-26 16:54:55 +0000422
Chris Lattnerdba2b222003-09-08 18:20:14 +0000423 case 63: // volatile store
Chris Lattner09bd0252003-09-08 18:04:16 +0000424 case Instruction::Store: {
Misha Brukmand554ebf2003-09-23 16:17:50 +0000425 if (!isa<PointerType>(Raw->Ty) || Raw->NumOperands != 2) return true;
Chris Lattnerab5ac6b2001-07-08 23:22:50 +0000426
Misha Brukmand554ebf2003-09-23 16:17:50 +0000427 Value *Ptr = getValue(Raw->Ty, Raw->Arg2);
Chris Lattner352eef72002-08-21 22:55:27 +0000428 const Type *ValTy = cast<PointerType>(Ptr->getType())->getElementType();
Misha Brukmand554ebf2003-09-23 16:17:50 +0000429 Res = new StoreInst(getValue(ValTy, Raw->Arg1), Ptr, Raw->Opcode == 63);
Chris Lattner00950542001-06-06 20:29:01 +0000430 return false;
431 }
Chris Lattner36143fc2003-09-08 18:54:55 +0000432 case Instruction::Unwind:
Misha Brukmand554ebf2003-09-23 16:17:50 +0000433 if (Raw->NumOperands != 0) return true;
Chris Lattnerda73bea2003-09-08 19:43:46 +0000434 Res = new UnwindInst();
435 return false;
Misha Brukmand554ebf2003-09-23 16:17:50 +0000436 } // end switch(Raw->Opcode)
Chris Lattner00950542001-06-06 20:29:01 +0000437
Misha Brukmand554ebf2003-09-23 16:17:50 +0000438 std::cerr << "Unrecognized instruction! " << Raw->Opcode
Chris Lattner0d75d8d72003-03-06 16:32:25 +0000439 << " ADDR = 0x" << (void*)Buf << "\n";
Chris Lattner74734132002-08-17 22:01:27 +0000440 return true;
Chris Lattner00950542001-06-06 20:29:01 +0000441}