#ifndef LLVM_SUPPORT_IRBUILDER_H
#define LLVM_SUPPORT_IRBUILDER_H
-#include "llvm/Constants.h"
#include "llvm/Instructions.h"
-#include "llvm/Function.h"
-#include "llvm/Metadata.h"
-#include "llvm/LLVMContext.h"
+#include "llvm/BasicBlock.h"
#include "llvm/ADT/Twine.h"
#include "llvm/Support/ConstantFolder.h"
namespace llvm {
+ class MDNode;
/// IRBuilderDefaultInserter - This provides the default implementation of the
/// IRBuilder 'InsertHelper' method that is called whenever an instruction is
/// IRBuilderBase - Common base class shared among various IRBuilders.
class IRBuilderBase {
+ DebugLoc CurDbgLocation;
protected:
BasicBlock *BB;
BasicBlock::iterator InsertPt;
- unsigned DbgMDKind;
- MDNode *CurDbgLocation;
LLVMContext &Context;
public:
IRBuilderBase(LLVMContext &context)
- : DbgMDKind(0), CurDbgLocation(0), Context(context) {
+ : Context(context) {
ClearInsertionPoint();
}
BasicBlock *GetInsertBlock() const { return BB; }
BasicBlock::iterator GetInsertPoint() const { return InsertPt; }
+ LLVMContext &getContext() const { return Context; }
/// SetInsertPoint - This specifies that created instructions should be
/// appended to the end of the specified block.
/// SetCurrentDebugLocation - Set location information used by debugging
/// information.
- void SetCurrentDebugLocation(MDNode *L) {
- if (DbgMDKind == 0)
- DbgMDKind = Context.getMetadata().getMDKindID("dbg");
+ void SetCurrentDebugLocation(const DebugLoc &L) {
CurDbgLocation = L;
}
- MDNode *getCurrentDebugLocation() const { return CurDbgLocation; }
-
- /// SetDebugLocation - Set location information for the given instruction.
- void SetDebugLocation(Instruction *I) {
- if (CurDbgLocation)
- Context.getMetadata().addMD(DbgMDKind, CurDbgLocation, I);
- }
+ /// getCurrentDebugLocation - Get location information used by debugging
+ /// information.
+ const DebugLoc &getCurrentDebugLocation() const { return CurDbgLocation; }
- /// SetDebugLocation - Set location information for the given instruction.
- void SetDebugLocation(Instruction *I, MDNode *Loc) {
- if (DbgMDKind == 0)
- DbgMDKind = Context.getMetadata().getMDKindID("dbg");
- Context.getMetadata().addMD(DbgMDKind, Loc, I);
+ /// SetInstDebugLocation - If this builder has a current debug location, set
+ /// it on the specified instruction.
+ void SetInstDebugLocation(Instruction *I) const {
+ if (!CurDbgLocation.isUnknown())
+ I->setDebugLoc(CurDbgLocation);
}
-
+
//===--------------------------------------------------------------------===//
// Miscellaneous creation methods.
//===--------------------------------------------------------------------===//
/// CreateGlobalString - Make a new global variable with an initializer that
- /// has array of i8 type filled in the the nul terminated string value
+ /// has array of i8 type filled in with the nul terminated string value
/// specified. If Name is specified, it is the name of the global variable
/// created.
Value *CreateGlobalString(const char *Str = "", const Twine &Name = "");
const Type *getVoidTy() {
return Type::getVoidTy(Context);
}
+
+ const Type *getInt8PtrTy() {
+ return Type::getInt8PtrTy(Context);
+ }
+
+ /// getCurrentFunctionReturnType - Get the return type of the current function
+ /// that we're emitting into.
+ const Type *getCurrentFunctionReturnType() const;
};
/// IRBuilder - This provides a uniform API for creating instructions and
template<typename InstTy>
InstTy *Insert(InstTy *I, const Twine &Name = "") const {
this->InsertHelper(I, Name, BB, InsertPt);
- if (CurDbgLocation)
- Context.getMetadata().addMD(DbgMDKind, CurDbgLocation, I);
+ if (!getCurrentDebugLocation().isUnknown())
+ this->SetInstDebugLocation(I);
return I;
}
ReturnInst *CreateRet(Value *V) {
return Insert(ReturnInst::Create(Context, V));
}
-
+
/// CreateAggregateRet - Create a sequence of N insertvalue instructions,
/// with one Value from the retVals array each, that build a aggregate
/// return value one value at a time, and a ret instruction to return
/// code that uses aggregate return values as a vehicle for having
/// multiple return values.
///
- ReturnInst *CreateAggregateRet(Value * const* retVals, unsigned N) {
- const Type *RetType = BB->getParent()->getReturnType();
- Value *V = UndefValue::get(RetType);
+ ReturnInst *CreateAggregateRet(Value *const *retVals, unsigned N) {
+ Value *V = UndefValue::get(getCurrentFunctionReturnType());
for (unsigned i = 0; i != N; ++i)
V = CreateInsertValue(V, retVals[i], i, "mrv");
return Insert(ReturnInst::Create(Context, V));
return Folder.CreateNSWAdd(LC, RC);
return Insert(BinaryOperator::CreateNSWAdd(LHS, RHS), Name);
}
+ Value *CreateNUWAdd(Value *LHS, Value *RHS, const Twine &Name = "") {
+ if (Constant *LC = dyn_cast<Constant>(LHS))
+ if (Constant *RC = dyn_cast<Constant>(RHS))
+ return Folder.CreateNUWAdd(LC, RC);
+ return Insert(BinaryOperator::CreateNUWAdd(LHS, RHS), Name);
+ }
Value *CreateFAdd(Value *LHS, Value *RHS, const Twine &Name = "") {
if (Constant *LC = dyn_cast<Constant>(LHS))
if (Constant *RC = dyn_cast<Constant>(RHS))
return Folder.CreateNSWSub(LC, RC);
return Insert(BinaryOperator::CreateNSWSub(LHS, RHS), Name);
}
+ Value *CreateNUWSub(Value *LHS, Value *RHS, const Twine &Name = "") {
+ if (Constant *LC = dyn_cast<Constant>(LHS))
+ if (Constant *RC = dyn_cast<Constant>(RHS))
+ return Folder.CreateNUWSub(LC, RC);
+ return Insert(BinaryOperator::CreateNUWSub(LHS, RHS), Name);
+ }
Value *CreateFSub(Value *LHS, Value *RHS, const Twine &Name = "") {
if (Constant *LC = dyn_cast<Constant>(LHS))
if (Constant *RC = dyn_cast<Constant>(RHS))
return Folder.CreateNSWMul(LC, RC);
return Insert(BinaryOperator::CreateNSWMul(LHS, RHS), Name);
}
+ Value *CreateNUWMul(Value *LHS, Value *RHS, const Twine &Name = "") {
+ if (Constant *LC = dyn_cast<Constant>(LHS))
+ if (Constant *RC = dyn_cast<Constant>(RHS))
+ return Folder.CreateNUWMul(LC, RC);
+ return Insert(BinaryOperator::CreateNUWMul(LHS, RHS), Name);
+ }
Value *CreateFMul(Value *LHS, Value *RHS, const Twine &Name = "") {
if (Constant *LC = dyn_cast<Constant>(LHS))
if (Constant *RC = dyn_cast<Constant>(RHS))
return Folder.CreateNSWNeg(VC);
return Insert(BinaryOperator::CreateNSWNeg(V), Name);
}
+ Value *CreateNUWNeg(Value *V, const Twine &Name = "") {
+ if (Constant *VC = dyn_cast<Constant>(V))
+ return Folder.CreateNUWNeg(VC);
+ return Insert(BinaryOperator::CreateNUWNeg(V), Name);
+ }
Value *CreateFNeg(Value *V, const Twine &Name = "") {
if (Constant *VC = dyn_cast<Constant>(V))
return Folder.CreateFNeg(VC);