#include "llvm/DerivedTypes.h"
#include "llvm/Function.h"
#include "llvm/Instructions.h"
-#include "llvm/ParameterAttributes.h"
+#include "llvm/ParamAttrsList.h"
#include "llvm/Support/CallSite.h"
#include "llvm/Support/ConstantRange.h"
#include "llvm/Support/MathExtras.h"
else
cast<InvokeInst>(I)->setParamAttrs(PAL);
}
-bool CallSite::paramHasAttr(uint16_t i, unsigned attr) const {
+bool CallSite::paramHasAttr(uint16_t i, ParameterAttributes attr) const {
if (CallInst *CI = dyn_cast<CallInst>(I))
- return CI->paramHasAttr(i, (ParameterAttributes)attr);
+ return CI->paramHasAttr(i, attr);
else
- return cast<InvokeInst>(I)->paramHasAttr(i, (ParameterAttributes)attr);
+ return cast<InvokeInst>(I)->paramHasAttr(i, attr);
}
+uint16_t CallSite::getParamAlignment(uint16_t i) const {
+ if (CallInst *CI = dyn_cast<CallInst>(I))
+ return CI->getParamAlignment(i);
+ else
+ return cast<InvokeInst>(I)->getParamAlignment(i);
+}
+
bool CallSite::doesNotAccessMemory() const {
if (CallInst *CI = dyn_cast<CallInst>(I))
return CI->doesNotAccessMemory();
///
Value *PHINode::hasConstantValue(bool AllowNonDominatingInstruction) const {
// If the PHI node only has one incoming value, eliminate the PHI node...
- if (getNumIncomingValues() == 1)
+ if (getNumIncomingValues() == 1) {
if (getIncomingValue(0) != this) // not X = phi X
return getIncomingValue(0);
else
return UndefValue::get(getType()); // Self cycle is dead.
+ }
// Otherwise if all of the incoming values are the same for the PHI, replace
// the PHI node with the incoming value.
Value *InVal = 0;
bool HasUndefInput = false;
for (unsigned i = 0, e = getNumIncomingValues(); i != e; ++i)
- if (isa<UndefValue>(getIncomingValue(i)))
+ if (isa<UndefValue>(getIncomingValue(i))) {
HasUndefInput = true;
- else if (getIncomingValue(i) != this) // Not the PHI node itself...
+ } else if (getIncomingValue(i) != this) { // Not the PHI node itself...
if (InVal && getIncomingValue(i) != InVal)
return 0; // Not the same, bail out.
else
InVal = getIncomingValue(i);
+ }
// The only case that could cause InVal to be null is if we have a PHI node
// that only has entries for itself. In this case, there is no entry into the
ParamAttrs = newAttrs;
}
-bool CallInst::paramHasAttr(uint16_t i, unsigned attr) const {
- if (ParamAttrs && ParamAttrs->paramHasAttr(i, (ParameterAttributes)attr))
+bool CallInst::paramHasAttr(uint16_t i, ParameterAttributes attr) const {
+ if (ParamAttrs && ParamAttrs->paramHasAttr(i, attr))
return true;
if (const Function *F = getCalledFunction())
- return F->paramHasAttr(i, (ParameterAttributes)attr);
+ return F->paramHasAttr(i, attr);
return false;
}
+uint16_t CallInst::getParamAlignment(uint16_t i) const {
+ if (ParamAttrs && ParamAttrs->getParamAlignment(i))
+ return ParamAttrs->getParamAlignment(i);
+ if (const Function *F = getCalledFunction())
+ return F->getParamAlignment(i);
+ return 0;
+}
+
/// @brief Determine if the call does not access memory.
bool CallInst::doesNotAccessMemory() const {
return paramHasAttr(0, ParamAttr::ReadNone);
cast<FunctionType>(cast<PointerType>(Fn->getType())->getElementType());
FTy = FTy; // silence warning.
- assert((NumArgs == FTy->getNumParams()) ||
- (FTy->isVarArg() && NumArgs > FTy->getNumParams()) &&
+ assert(((NumArgs == FTy->getNumParams()) ||
+ (FTy->isVarArg() && NumArgs > FTy->getNumParams())) &&
"Calling a function with bad signature");
for (unsigned i = 0, e = NumArgs; i != e; i++) {
ParamAttrs = newAttrs;
}
-bool InvokeInst::paramHasAttr(uint16_t i, unsigned attr) const {
- if (ParamAttrs && ParamAttrs->paramHasAttr(i, (ParameterAttributes)attr))
+bool InvokeInst::paramHasAttr(uint16_t i, ParameterAttributes attr) const {
+ if (ParamAttrs && ParamAttrs->paramHasAttr(i, attr))
return true;
if (const Function *F = getCalledFunction())
- return F->paramHasAttr(i, (ParameterAttributes)attr);
+ return F->paramHasAttr(i, attr);
return false;
}
+uint16_t InvokeInst::getParamAlignment(uint16_t i) const {
+ if (ParamAttrs && ParamAttrs->getParamAlignment(i))
+ return ParamAttrs->getParamAlignment(i);
+ if (const Function *F = getCalledFunction())
+ return F->getParamAlignment(i);
+ return 0;
+}
/// @brief Determine if the call does not access memory.
bool InvokeInst::doesNotAccessMemory() const {
ReturnInst::ReturnInst(const ReturnInst &RI)
: TerminatorInst(Type::VoidTy, Instruction::Ret,
- &RetVal, RI.getNumOperands()) {
- if (RI.getNumOperands())
- RetVal.init(RI.RetVal, this);
+ OperandList, RI.getNumOperands()) {
+ unsigned N = RI.getNumOperands();
+ Use *OL = OperandList = new Use[N];
+ for (unsigned i = 0; i < N; ++i)
+ OL[i].init(RI.getOperand(i), this);
}
ReturnInst::ReturnInst(Value *retVal, Instruction *InsertBefore)
- : TerminatorInst(Type::VoidTy, Instruction::Ret, &RetVal, 0, InsertBefore) {
+ : TerminatorInst(Type::VoidTy, Instruction::Ret, OperandList, 0, InsertBefore) {
init(retVal);
}
ReturnInst::ReturnInst(Value *retVal, BasicBlock *InsertAtEnd)
- : TerminatorInst(Type::VoidTy, Instruction::Ret, &RetVal, 0, InsertAtEnd) {
+ : TerminatorInst(Type::VoidTy, Instruction::Ret, OperandList, 0, InsertAtEnd) {
init(retVal);
}
ReturnInst::ReturnInst(BasicBlock *InsertAtEnd)
- : TerminatorInst(Type::VoidTy, Instruction::Ret, &RetVal, 0, InsertAtEnd) {
+ : TerminatorInst(Type::VoidTy, Instruction::Ret, OperandList, 0, InsertAtEnd) {
}
-
+ReturnInst::ReturnInst(std::vector<Value *> &retVals, Instruction *InsertBefore)
+ : TerminatorInst(Type::VoidTy, Instruction::Ret, OperandList, retVals.size(), InsertBefore) {
+ init(retVals);
+}
+ReturnInst::ReturnInst(std::vector<Value *> &retVals, BasicBlock *InsertAtEnd)
+ : TerminatorInst(Type::VoidTy, Instruction::Ret, OperandList, retVals.size(), InsertAtEnd) {
+ init(retVals);
+}
+ReturnInst::ReturnInst(std::vector<Value *> &retVals)
+ : TerminatorInst(Type::VoidTy, Instruction::Ret, OperandList, retVals.size()) {
+ init(retVals);
+}
void ReturnInst::init(Value *retVal) {
if (retVal && retVal->getType() != Type::VoidTy) {
assert(!isa<BasicBlock>(retVal) &&
"Cannot return basic block. Probably using the incorrect ctor");
NumOperands = 1;
- RetVal.init(retVal, this);
+ Use *OL = OperandList = new Use[1];
+ OL[0].init(retVal, this);
}
}
+void ReturnInst::init(std::vector<Value *> &retVals) {
+ if (retVals.empty())
+ return;
+
+ NumOperands = retVals.size();
+ if (NumOperands == 1) {
+ Value *V = retVals[0];
+ if (V->getType() == Type::VoidTy)
+ return;
+ }
+
+ Use *OL = OperandList = new Use[NumOperands];
+ for (unsigned i = 0; i < NumOperands; ++i) {
+ Value *V = retVals[i];
+ assert(!isa<BasicBlock>(V) &&
+ "Cannot return basic block. Probably using the incorrect ctor");
+ OL[i].init(V, this);
+ }
+}
+
+Value *ReturnInst::getReturnValue(unsigned n) const {
+ if (NumOperands)
+ return OperandList[n];
+ else
+ return 0;
+}
+
unsigned ReturnInst::getNumSuccessorsV() const {
return getNumSuccessors();
}
return 0;
}
+ReturnInst::~ReturnInst() {
+ if (NumOperands)
+ delete [] OperandList;
+}
//===----------------------------------------------------------------------===//
// UnwindInst Implementation
if (!isa<PointerType>(Ptr)) return 0; // Type isn't a pointer type!
// Handle the special case of the empty set index set...
- if (NumIdx == 0)
+ if (NumIdx == 0) {
if (AllowCompositeLeaf ||
cast<PointerType>(Ptr)->getElementType()->isFirstClassType())
return cast<PointerType>(Ptr)->getElementType();
else
return 0;
+ }
unsigned CurIdx = 0;
while (const CompositeType *CT = dyn_cast<CompositeType>(Ptr)) {
assert(Op0Ty == Op1Ty &&
"Both operands to ICmp instruction are not of the same type!");
// Check that the operands are the right type
- assert(Op0Ty->isInteger() || isa<PointerType>(Op0Ty) &&
+ assert((Op0Ty->isInteger() || isa<PointerType>(Op0Ty)) &&
"Invalid operand types for ICmp instruction");
return;
}
setSuccessor(idx, B);
}
+//===----------------------------------------------------------------------===//
+// GetResultInst Implementation
+//===----------------------------------------------------------------------===//
+
+GetResultInst::GetResultInst(Value *Aggregate, unsigned Index,
+ const std::string &Name,
+ Instruction *InsertBef)
+ : Instruction(cast<StructType>(Aggregate->getType())->getElementType(Index),
+ GetResult, &Aggr, 1, InsertBef) {
+ assert(isValidOperands(Aggregate, Index) && "Invalid GetResultInst operands!");
+ Aggr.init(Aggregate, this);
+ Idx = Index;
+ setName(Name);
+}
+
+bool GetResultInst::isValidOperands(const Value *Aggregate, unsigned Index) {
+ if (!Aggregate)
+ return false;
+
+ if (const StructType *STy = dyn_cast<StructType>(Aggregate->getType())) {
+ unsigned NumElements = STy->getNumElements();
+ if (Index >= NumElements)
+ return false;
+
+ // getresult aggregate value's element types are restricted to
+ // avoid nested aggregates.
+ for (unsigned i = 0; i < NumElements; ++i)
+ if (!STy->getElementType(i)->isFirstClassType())
+ return false;
+
+ // Otherwise, Aggregate is valid.
+ return true;
+ }
+ return false;
+}
// Define these methods here so vtables don't get emitted into every translation
// unit that uses these classes.
InvokeInst *InvokeInst::clone() const { return new InvokeInst(*this); }
UnwindInst *UnwindInst::clone() const { return new UnwindInst(); }
UnreachableInst *UnreachableInst::clone() const { return new UnreachableInst();}
+GetResultInst *GetResultInst::clone() const { return new GetResultInst(*this); }