summaryrefslogtreecommitdiff
path: root/lib/VMCore
diff options
context:
space:
mode:
authorChris Lattner <sabre@nondot.org>2001-07-07 08:36:50 +0000
committerChris Lattner <sabre@nondot.org>2001-07-07 08:36:50 +0000
commitc8b25d40cbec063b1ca99cc1adf794399c6d05c0 (patch)
tree8ad1468cb632eb9770206b1bd4bdd45d4e037898 /lib/VMCore
parentf0d0e9c262b668cf362fbaa8111bb6cc15268909 (diff)
downloadllvm-c8b25d40cbec063b1ca99cc1adf794399c6d05c0.tar.gz
llvm-c8b25d40cbec063b1ca99cc1adf794399c6d05c0.tar.bz2
llvm-c8b25d40cbec063b1ca99cc1adf794399c6d05c0.tar.xz
Changed the fundemental architecture of Operands for Instructions. Now
Operands are maintained as a vector<Use> in the User class, and operator iterators are provided as before. Getting an operand no longer requires a virtual function call. WARNING: getOperand(x) where x >= getNumOperands() will now assert instead of returning null! git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@149 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/VMCore')
-rw-r--r--lib/VMCore/AsmWriter.cpp40
-rw-r--r--lib/VMCore/ConstantPool.cpp52
-rw-r--r--lib/VMCore/InstrTypes.cpp48
-rw-r--r--lib/VMCore/Value.cpp7
-rw-r--r--lib/VMCore/iBranch.cpp61
-rw-r--r--lib/VMCore/iCall.cpp37
-rw-r--r--lib/VMCore/iReturn.cpp22
-rw-r--r--lib/VMCore/iSwitch.cpp74
8 files changed, 107 insertions, 234 deletions
diff --git a/lib/VMCore/AsmWriter.cpp b/lib/VMCore/AsmWriter.cpp
index c68cd796f1..e2b2495605 100644
--- a/lib/VMCore/AsmWriter.cpp
+++ b/lib/VMCore/AsmWriter.cpp
@@ -157,10 +157,10 @@ bool AssemblyWriter::processInstruction(const Instruction *I) {
Out << I->getOpcode();
// Print out the type of the operands...
- const Value *Operand = I->getOperand(0);
+ const Value *Operand = I->getNumOperands() ? I->getOperand(0) : 0;
// Special case conditional branches to swizzle the condition out to the front
- if (I->getInstType() == Instruction::Br && I->getOperand(1)) {
+ if (I->getInstType() == Instruction::Br && I->getNumOperands() > 1) {
writeOperand(I->getOperand(2), true);
Out << ",";
writeOperand(Operand, true);
@@ -172,9 +172,9 @@ bool AssemblyWriter::processInstruction(const Instruction *I) {
writeOperand(Operand , true); Out << ",";
writeOperand(I->getOperand(1), true); Out << " [";
- for (unsigned op = 2; (Operand = I->getOperand(op)); op += 2) {
+ for (unsigned op = 2, Eop = I->getNumOperands(); op < Eop; op += 2) {
Out << "\n\t\t";
- writeOperand(Operand, true); Out << ",";
+ writeOperand(I->getOperand(op ), true); Out << ",";
writeOperand(I->getOperand(op+1), true);
}
Out << "\n\t]";
@@ -183,8 +183,9 @@ bool AssemblyWriter::processInstruction(const Instruction *I) {
Out << " ["; writeOperand(Operand, false); Out << ",";
writeOperand(I->getOperand(1), false); Out << " ]";
- for (unsigned op = 2; (Operand = I->getOperand(op)); op += 2) {
- Out << ", ["; writeOperand(Operand, false); Out << ",";
+ for (unsigned op = 2, Eop = I->getNumOperands(); op < Eop; op += 2) {
+ Out << ", [";
+ writeOperand(I->getOperand(op ), false); Out << ",";
writeOperand(I->getOperand(op+1), false); Out << " ]";
}
} else if (I->getInstType() == Instruction::Ret && !Operand) {
@@ -192,20 +193,19 @@ bool AssemblyWriter::processInstruction(const Instruction *I) {
} else if (I->getInstType() == Instruction::Call) {
writeOperand(Operand, true);
Out << "(";
- Operand = I->getOperand(1);
- if (Operand) writeOperand(Operand, true);
- for (unsigned op = 2; (Operand = I->getOperand(op)); ++op) {
+ if (I->getNumOperands() > 1) writeOperand(I->getOperand(1), true);
+ for (unsigned op = 2, Eop = I->getNumOperands(); op < Eop; ++op) {
Out << ",";
- writeOperand(Operand, true);
+ writeOperand(I->getOperand(op), true);
}
Out << " )";
} else if (I->getInstType() == Instruction::Malloc ||
I->getInstType() == Instruction::Alloca) {
- Out << " " << ((const PointerType*)((ConstPoolType*)Operand)
- ->getValue())->getValueType();
- if ((Operand = I->getOperand(1))) {
- Out << ","; writeOperand(Operand, true);
+ Out << " " << ((const PointerType*)I->getType())->getValueType();
+ if (I->getNumOperands()) {
+ Out << ",";
+ writeOperand(I->getOperand(0), true);
}
} else if (Operand) { // Print the normal way...
@@ -215,9 +215,9 @@ bool AssemblyWriter::processInstruction(const Instruction *I) {
// different type operands (for example br), then they are all printed.
bool PrintAllTypes = false;
const Type *TheType = Operand->getType();
- unsigned i;
- for (i = 1; (Operand = I->getOperand(i)); i++) {
+ for (unsigned i = 1, E = I->getNumOperands(); i != E; ++i) {
+ Operand = I->getOperand(i);
if (Operand->getType() != TheType) {
PrintAllTypes = true; // We have differing types! Print them all!
break;
@@ -227,9 +227,9 @@ bool AssemblyWriter::processInstruction(const Instruction *I) {
if (!PrintAllTypes)
Out << " " << I->getOperand(0)->getType();
- for (unsigned i = 0; (Operand = I->getOperand(i)); i++) {
+ for (unsigned i = 0, E = I->getNumOperands(); i != E; ++i) {
if (i) Out << ",";
- writeOperand(Operand, PrintAllTypes);
+ writeOperand(I->getOperand(i), PrintAllTypes);
}
}
@@ -262,8 +262,8 @@ void AssemblyWriter::writeOperand(const Value *Operand, bool PrintType,
} else {
int Slot = Table.getValSlot(Operand);
- if (Operand->isConstant()) {
- Out << " " << ((ConstPoolVal*)Operand)->getStrValue();
+ if (const ConstPoolVal *CPV = Operand->castConstant()) {
+ Out << " " << CPV->getStrValue();
} else {
if (Slot >= 0) Out << " %" << Slot;
else if (PrintName)
diff --git a/lib/VMCore/ConstantPool.cpp b/lib/VMCore/ConstantPool.cpp
index 77ed50ae26..13463a1734 100644
--- a/lib/VMCore/ConstantPool.cpp
+++ b/lib/VMCore/ConstantPool.cpp
@@ -219,7 +219,7 @@ ConstPoolArray::ConstPoolArray(const ArrayType *T,
: ConstPoolVal(T, Name) {
for (unsigned i = 0; i < V.size(); i++) {
assert(V[i]->getType() == T->getElementType());
- Val.push_back(ConstPoolUse(V[i], this));
+ Operands.push_back(Use(V[i], this));
}
}
@@ -231,7 +231,7 @@ ConstPoolStruct::ConstPoolStruct(const StructType *T,
for (unsigned i = 0; i < V.size(); i++) {
assert(V[i]->getType() == ETypes[i]);
- Val.push_back(ConstPoolUse(V[i], this));
+ Operands.push_back(Use(V[i], this));
}
}
@@ -265,14 +265,14 @@ ConstPoolType::ConstPoolType(const ConstPoolType &CPT)
ConstPoolArray::ConstPoolArray(const ConstPoolArray &CPA)
: ConstPoolVal(CPA.getType()) {
- for (unsigned i = 0; i < CPA.Val.size(); i++)
- Val.push_back(ConstPoolUse((ConstPoolVal*)CPA.Val[i], this));
+ for (unsigned i = 0; i < CPA.Operands.size(); i++)
+ Operands.push_back(Use(CPA.Operands[i], this));
}
ConstPoolStruct::ConstPoolStruct(const ConstPoolStruct &CPS)
: ConstPoolVal(CPS.getType()) {
- for (unsigned i = 0; i < CPS.Val.size(); i++)
- Val.push_back(ConstPoolUse((ConstPoolVal*)CPS.Val[i], this));
+ for (unsigned i = 0; i < CPS.Operands.size(); i++)
+ Operands.push_back(Use(CPS.Operands[i], this));
}
//===----------------------------------------------------------------------===//
@@ -301,12 +301,12 @@ string ConstPoolType::getStrValue() const {
string ConstPoolArray::getStrValue() const {
string Result = "[";
- if (Val.size()) {
- Result += " " + Val[0]->getType()->getName() +
- " " + Val[0]->getStrValue();
- for (unsigned i = 1; i < Val.size(); i++)
- Result += ", " + Val[i]->getType()->getName() +
- " " + Val[i]->getStrValue();
+ if (Operands.size()) {
+ Result += " " + Operands[0]->getType()->getName() +
+ " " + Operands[0]->castConstantAsserting()->getStrValue();
+ for (unsigned i = 1; i < Operands.size(); i++)
+ Result += ", " + Operands[i]->getType()->getName() +
+ " " + Operands[i]->castConstantAsserting()->getStrValue();
}
return Result + " ]";
@@ -314,12 +314,12 @@ string ConstPoolArray::getStrValue() const {
string ConstPoolStruct::getStrValue() const {
string Result = "{";
- if (Val.size()) {
- Result += " " + Val[0]->getType()->getName() +
- " " + Val[0]->getStrValue();
- for (unsigned i = 1; i < Val.size(); i++)
- Result += ", " + Val[i]->getType()->getName() +
- " " + Val[i]->getStrValue();
+ if (Operands.size()) {
+ Result += " " + Operands[0]->getType()->getName() +
+ " " + Operands[0]->castConstantAsserting()->getStrValue();
+ for (unsigned i = 1; i < Operands.size(); i++)
+ Result += ", " + Operands[i]->getType()->getName() +
+ " " + Operands[i]->castConstantAsserting()->getStrValue();
}
return Result + " }";
@@ -356,9 +356,11 @@ bool ConstPoolType::equals(const ConstPoolVal *V) const {
bool ConstPoolArray::equals(const ConstPoolVal *V) const {
assert(getType() == V->getType());
ConstPoolArray *AV = (ConstPoolArray*)V;
- if (Val.size() != AV->Val.size()) return false;
- for (unsigned i = 0; i < Val.size(); i++)
- if (!Val[i]->equals(AV->Val[i])) return false;
+ if (Operands.size() != AV->Operands.size()) return false;
+ for (unsigned i = 0; i < Operands.size(); i++)
+ if (!Operands[i]->castConstantAsserting()->equals(
+ AV->Operands[i]->castConstantAsserting()))
+ return false;
return true;
}
@@ -366,9 +368,11 @@ bool ConstPoolArray::equals(const ConstPoolVal *V) const {
bool ConstPoolStruct::equals(const ConstPoolVal *V) const {
assert(getType() == V->getType());
ConstPoolStruct *SV = (ConstPoolStruct*)V;
- if (Val.size() != SV->Val.size()) return false;
- for (unsigned i = 0; i < Val.size(); i++)
- if (!Val[i]->equals(SV->Val[i])) return false;
+ if (Operands.size() != SV->Operands.size()) return false;
+ for (unsigned i = 0; i < Operands.size(); i++)
+ if (!Operands[i]->castConstantAsserting()->equals(
+ SV->Operands[i]->castConstantAsserting()))
+ return false;
return true;
}
diff --git a/lib/VMCore/InstrTypes.cpp b/lib/VMCore/InstrTypes.cpp
index baafe0bc13..cda99a9446 100644
--- a/lib/VMCore/InstrTypes.cpp
+++ b/lib/VMCore/InstrTypes.cpp
@@ -9,7 +9,7 @@
#include "llvm/Method.h"
#include "llvm/SymbolTable.h"
#include "llvm/Type.h"
-#include <algorithm>
+#include <algorithm> // find
// TODO: Move to getUnaryOperator iUnary.cpp when and if it exists!
UnaryOperator *UnaryOperator::create(unsigned Op, Value *Source) {
@@ -52,49 +52,25 @@ PHINode::PHINode(const Type *Ty, const string &name)
PHINode::PHINode(const PHINode &PN)
: Instruction(PN.getType(), Instruction::PHINode) {
-
- for (unsigned i = 0; i < PN.IncomingValues.size(); i++)
- IncomingValues.push_back(
- make_pair(Use(PN.IncomingValues[i].first, this),
- BasicBlockUse(PN.IncomingValues[i].second, this)));
-}
-
-void PHINode::dropAllReferences() {
- IncomingValues.clear();
-}
-
-bool PHINode::setOperand(unsigned i, Value *Val) {
- assert(Val && "PHI node must only reference nonnull definitions!");
- if (i >= IncomingValues.size()*2) return false;
-
- if (i & 1) {
- IncomingValues[i/2].second = Val->castBasicBlockAsserting();
- } else {
- IncomingValues[i/2].first = Val;
+ Operands.reserve(PN.Operands.size());
+ for (unsigned i = 0; i < PN.Operands.size(); i+=2) {
+ Operands.push_back(Use(PN.Operands[i], this));
+ Operands.push_back(Use(PN.Operands[i+1], this));
}
- return true;
}
void PHINode::addIncoming(Value *D, BasicBlock *BB) {
- IncomingValues.push_back(make_pair(Use(D, this), BasicBlockUse(BB, this)));
+ Operands.push_back(Use(D, this));
+ Operands.push_back(Use(BB, this));
}
-struct FindBBEntry {
- const BasicBlock *BB;
- inline FindBBEntry(const BasicBlock *bb) : BB(bb) {}
- inline bool operator()(const pair<Use,BasicBlockUse> &Entry) {
- return Entry.second == BB;
- }
-};
-
-
// removeIncomingValue - Remove an incoming value. This is useful if a
// predecessor basic block is deleted.
Value *PHINode::removeIncomingValue(const BasicBlock *BB) {
- vector<PairTy>::iterator Idx = find_if(IncomingValues.begin(),
- IncomingValues.end(), FindBBEntry(BB));
- assert(Idx != IncomingValues.end() && "BB not in PHI node!");
- Value *Removed = Idx->first;
- IncomingValues.erase(Idx);
+ op_iterator Idx = find(Operands.begin(), Operands.end(), (const Value*)BB);
+ assert(Idx != Operands.end() && "BB not in PHI node!");
+ --Idx; // Back up to value prior to Basic block
+ Value *Removed = *Idx;
+ Operands.erase(Idx, Idx+2); // Erase Value and BasicBlock
return Removed;
}
diff --git a/lib/VMCore/Value.cpp b/lib/VMCore/Value.cpp
index fa3c0f60fb..a051bcb3cc 100644
--- a/lib/VMCore/Value.cpp
+++ b/lib/VMCore/Value.cpp
@@ -89,14 +89,13 @@ User::User(const Type *Ty, ValueTy vty, const string &name)
void User::replaceUsesOfWith(Value *From, Value *To) {
if (From == To) return; // Duh what?
- for (unsigned OpNum = 0; Value *D = getOperand(OpNum); ++OpNum) {
- if (D == From) { // Okay, this operand is pointing to our fake def.
+ for (unsigned i = 0, E = getNumOperands(); i != E; ++i)
+ if (getOperand(i) == From) { // Is This operand is pointing to oldval?
// The side effects of this setOperand call include linking to
// "To", adding "this" to the uses list of To, and
// most importantly, removing "this" from the use list of "From".
- setOperand(OpNum, To); // Fix it now...
+ setOperand(i, To); // Fix it now...
}
- }
}
diff --git a/lib/VMCore/iBranch.cpp b/lib/VMCore/iBranch.cpp
index 05f35059a5..d0f437e293 100644
--- a/lib/VMCore/iBranch.cpp
+++ b/lib/VMCore/iBranch.cpp
@@ -13,9 +13,17 @@
#endif
BranchInst::BranchInst(BasicBlock *True, BasicBlock *False, Value *Cond)
- : TerminatorInst(Instruction::Br), TrueDest(True, this),
- FalseDest(False, this), Condition(Cond, this) {
+ : TerminatorInst(Instruction::Br) {
assert(True != 0 && "True branch destination may not be null!!!");
+ Operands.reserve(False ? 3 : 1);
+ Operands.push_back(Use(True, this));
+ if (False) {
+ Operands.push_back(Use(False, this));
+ Operands.push_back(Use(Cond, this));
+ }
+
+ assert(!!False == !!Cond &&
+ "Either both cond and false or neither can be specified!");
#ifndef NDEBUG
if (Cond != 0 && Cond->getType() != Type::BoolTy)
@@ -25,45 +33,12 @@ BranchInst::BranchInst(BasicBlock *True, BasicBlock *False, Value *Cond)
"May only branch on boolean predicates!!!!");
}
-BranchInst::BranchInst(const BranchInst &BI)
- : TerminatorInst(Instruction::Br), TrueDest(BI.TrueDest, this),
- FalseDest(BI.FalseDest, this), Condition(BI.Condition, this) {
-}
-
-
-void BranchInst::dropAllReferences() {
- Condition = 0;
- TrueDest = FalseDest = 0;
-}
-
-const Value *BranchInst::getOperand(unsigned i) const {
- return (i == 0) ? (Value*)TrueDest :
- ((i == 1) ? (Value*)FalseDest :
- ((i == 2) ? (Value*)Condition : 0));
-}
-
-const BasicBlock *BranchInst::getSuccessor(unsigned i) const {
- return (i == 0) ? (const BasicBlock*)TrueDest :
- ((i == 1) ? (const BasicBlock*)FalseDest : 0);
-}
-
-bool BranchInst::setOperand(unsigned i, Value *Val) {
- switch (i) {
- case 0:
- assert(Val && "Can't change primary direction to 0!");
- assert(Val->getType() == Type::LabelTy);
- TrueDest = (BasicBlock*)Val;
- return true;
- case 1:
- assert(Val == 0 || Val->getType() == Type::LabelTy);
- FalseDest = (BasicBlock*)Val;
- return true;
- case 2:
- Condition = Val;
- assert(!Condition || Condition->getType() == Type::BoolTy &&
- "Condition expr must be a boolean expression!");
- return true;
- }
-
- return false;
+BranchInst::BranchInst(const BranchInst &BI) : TerminatorInst(Instruction::Br) {
+ Operands.reserve(BI.Operands.size());
+ Operands.push_back(Use(BI.Operands[0], this));
+ if (BI.Operands.size() != 1) {
+ assert(BI.Operands.size() == 3 && "BR can have 1 or 3 operands!");
+ Operands.push_back(Use(BI.Operands[1], this));
+ Operands.push_back(Use(BI.Operands[2], this));
+ }
}
diff --git a/lib/VMCore/iCall.cpp b/lib/VMCore/iCall.cpp
index 7632798c66..67826ff4bc 100644
--- a/lib/VMCore/iCall.cpp
+++ b/lib/VMCore/iCall.cpp
@@ -1,6 +1,6 @@
-//===-- iCall.cpp - Implement the Call & Invoke instructions -----*- C++ -*--=//
+//===-- iCall.cpp - Implement the call & icall instructions ------*- C++ -*--=//
//
-// This file implements the call and invoke instructions.
+// This file implements the call and icall instructions.
//
//===----------------------------------------------------------------------===//
@@ -8,9 +8,12 @@
#include "llvm/DerivedTypes.h"
#include "llvm/Method.h"
-CallInst::CallInst(Method *m, vector<Value*> &params,
+CallInst::CallInst(Method *M, vector<Value*> &params,
const string &Name)
- : Instruction(m->getReturnType(), Instruction::Call, Name), M(m, this) {
+ : Instruction(M->getReturnType(), Instruction::Call, Name) {
+
+ Operands.reserve(1+params.size());
+ Operands.push_back(Use(M, this));
const MethodType* MT = M->getMethodType();
const MethodType::ParamTypes &PL = MT->getParamTypes();
@@ -19,29 +22,15 @@ CallInst::CallInst(Method *m, vector<Value*> &params,
MethodType::ParamTypes::const_iterator It = PL.begin();
#endif
for (unsigned i = 0; i < params.size(); i++) {
- assert(*It++ == params[i]->getType());
- Params.push_back(Use(params[i], this));
+ assert(*It++ == params[i]->getType() && "Call Operands not correct type!");
+ Operands.push_back(Use(params[i], this));
}
}
CallInst::CallInst(const CallInst &CI)
- : Instruction(CI.getType(), Instruction::Call), M(CI.M, this) {
- for (unsigned i = 0; i < CI.Params.size(); i++)
- Params.push_back(Use(CI.Params[i], this));
-}
-
-void CallInst::dropAllReferences() {
- M = 0;
- Params.clear();
+ : Instruction(CI.getType(), Instruction::Call) {
+ Operands.reserve(CI.Operands.size());
+ for (unsigned i = 0; i < CI.Operands.size(); ++i)
+ Operands.push_back(Use(CI.Operands[i], this));
}
-bool CallInst::setOperand(unsigned i, Value *Val) {
- if (i > Params.size()) return false;
- if (i == 0) {
- M = Val->castMethodAsserting();
- } else {
- // TODO: assert = method arg type
- Params[i-1] = Val;
- }
- return true;
-}
diff --git a/lib/VMCore/iReturn.cpp b/lib/VMCore/iReturn.cpp
index 7fa04fb42c..b28b04f643 100644
--- a/lib/VMCore/iReturn.cpp
+++ b/lib/VMCore/iReturn.cpp
@@ -1,25 +1,3 @@
-//===-- iReturn.cpp - Implement the Return instruction -----------*- C++ -*--=//
-//
-// This file implements the Return instruction...
-//
-//===----------------------------------------------------------------------===//
-#include "llvm/iTerminators.h"
-ReturnInst::ReturnInst(Value *V)
- : TerminatorInst(Instruction::Ret), Val(V, this) {
-}
-ReturnInst::ReturnInst(const ReturnInst &RI)
- : TerminatorInst(Instruction::Ret), Val(RI.Val, this) {
-}
-
-void ReturnInst::dropAllReferences() {
- Val = 0;
-}
-
-bool ReturnInst::setOperand(unsigned i, Value *V) {
- if (i) return false;
- Val = V;
- return true;
-}
diff --git a/lib/VMCore/iSwitch.cpp b/lib/VMCore/iSwitch.cpp
index 2a1eec2639..e5e3c50cfd 100644
--- a/lib/VMCore/iSwitch.cpp
+++ b/lib/VMCore/iSwitch.cpp
@@ -10,72 +10,24 @@
#include "llvm/Type.h"
#endif
-SwitchInst::SwitchInst(Value *V, BasicBlock *DefV)
- : TerminatorInst(Instruction::Switch),
- DefaultDest(DefV, this), Val(V, this) {
- assert(Val && DefV);
+SwitchInst::SwitchInst(Value *V, BasicBlock *DefDest)
+ : TerminatorInst(Instruction::Switch) {
+ assert(V && DefDest);
+ Operands.push_back(Use(V, this));
+ Operands.push_back(Use(DefDest, this));
}
SwitchInst::SwitchInst(const SwitchInst &SI)
- : TerminatorInst(Instruction::Switch), DefaultDest(SI.DefaultDest),
- Val(SI.Val) {
+ : TerminatorInst(Instruction::Switch) {
+ Operands.reserve(SI.Operands.size());
- for (dest_const_iterator I = SI.Destinations.begin(),
- end = SI.Destinations.end(); I != end; ++I)
- Destinations.push_back(dest_value(ConstPoolUse(I->first, this),
- BasicBlockUse(I->second, this)));
+ for (unsigned i = 0, E = SI.Operands.size(); i != E; i+=2) {
+ Operands.push_back(Use(SI.Operands[i], this));
+ Operands.push_back(Use(SI.Operands[i+1], this));
+ }
}
-
void SwitchInst::dest_push_back(ConstPoolVal *OnVal, BasicBlock *Dest) {
- Destinations.push_back(dest_value(ConstPoolUse(OnVal, this),
- BasicBlockUse(Dest, this)));
-}
-
-void SwitchInst::dropAllReferences() {
- Val = 0;
- DefaultDest = 0;
- Destinations.clear();
-}
-
-const BasicBlock *SwitchInst::getSuccessor(unsigned idx) const {
- if (idx == 0) return DefaultDest;
- if (idx > Destinations.size()) return 0;
- return Destinations[idx-1].second;
-}
-
-unsigned SwitchInst::getNumOperands() const {
- return 2+Destinations.size();
-}
-
-const Value *SwitchInst::getOperand(unsigned i) const {
- if (i == 0) return Val;
- else if (i == 1) return DefaultDest;
-
- unsigned slot = (i-2) >> 1;
- if (slot >= Destinations.size()) return 0;
-
- if (i & 1) return Destinations[slot].second;
- return Destinations[slot].first;
-}
-
-bool SwitchInst::setOperand(unsigned i, Value *V) {
- if (i == 0) { Val = V; return true; }
- else if (i == 1) {
- assert(V->getType() == Type::LabelTy);
- DefaultDest = (BasicBlock*)V;
- return true;
- }
-
- unsigned slot = (i-2) >> 1;
- if (slot >= Destinations.size()) return 0;
-
- if (i & 1) {
- assert(V->getType() == Type::LabelTy);
- Destinations[slot].second = (BasicBlock*)V;
- } else {
- // TODO: assert constant
- Destinations[slot].first = (ConstPoolVal*)V;
- }
- return true;
+ Operands.push_back(Use(OnVal, this));
+ Operands.push_back(Use(Dest, this));
}