LLVM API Documentation
00001 //====-- llvm/Support/TargetFolder.h - Constant folding helper -*- C++ -*-====// 00002 // 00003 // The LLVM Compiler Infrastructure 00004 // 00005 // This file is distributed under the University of Illinois Open Source 00006 // License. See LICENSE.TXT for details. 00007 // 00008 //===----------------------------------------------------------------------===// 00009 // 00010 // This file defines the TargetFolder class, a helper for IRBuilder. 00011 // It provides IRBuilder with a set of methods for creating constants with 00012 // target dependent folding, in addition to the same target-independent 00013 // folding that the ConstantFolder class provides. For general constant 00014 // creation and folding, use ConstantExpr and the routines in 00015 // llvm/Analysis/ConstantFolding.h. 00016 // 00017 //===----------------------------------------------------------------------===// 00018 00019 #ifndef LLVM_SUPPORT_TARGETFOLDER_H 00020 #define LLVM_SUPPORT_TARGETFOLDER_H 00021 00022 #include "llvm/ADT/ArrayRef.h" 00023 #include "llvm/Analysis/ConstantFolding.h" 00024 #include "llvm/IR/Constants.h" 00025 #include "llvm/IR/InstrTypes.h" 00026 00027 namespace llvm { 00028 00029 class DataLayout; 00030 00031 /// TargetFolder - Create constants with target dependent folding. 00032 class TargetFolder { 00033 const DataLayout *TD; 00034 00035 /// Fold - Fold the constant using target specific information. 00036 Constant *Fold(Constant *C) const { 00037 if (ConstantExpr *CE = dyn_cast<ConstantExpr>(C)) 00038 if (Constant *CF = ConstantFoldConstantExpression(CE, TD)) 00039 return CF; 00040 return C; 00041 } 00042 00043 public: 00044 explicit TargetFolder(const DataLayout *TheTD) : TD(TheTD) {} 00045 00046 //===--------------------------------------------------------------------===// 00047 // Binary Operators 00048 //===--------------------------------------------------------------------===// 00049 00050 Constant *CreateAdd(Constant *LHS, Constant *RHS, 00051 bool HasNUW = false, bool HasNSW = false) const { 00052 return Fold(ConstantExpr::getAdd(LHS, RHS, HasNUW, HasNSW)); 00053 } 00054 Constant *CreateFAdd(Constant *LHS, Constant *RHS) const { 00055 return Fold(ConstantExpr::getFAdd(LHS, RHS)); 00056 } 00057 Constant *CreateSub(Constant *LHS, Constant *RHS, 00058 bool HasNUW = false, bool HasNSW = false) const { 00059 return Fold(ConstantExpr::getSub(LHS, RHS, HasNUW, HasNSW)); 00060 } 00061 Constant *CreateFSub(Constant *LHS, Constant *RHS) const { 00062 return Fold(ConstantExpr::getFSub(LHS, RHS)); 00063 } 00064 Constant *CreateMul(Constant *LHS, Constant *RHS, 00065 bool HasNUW = false, bool HasNSW = false) const { 00066 return Fold(ConstantExpr::getMul(LHS, RHS, HasNUW, HasNSW)); 00067 } 00068 Constant *CreateFMul(Constant *LHS, Constant *RHS) const { 00069 return Fold(ConstantExpr::getFMul(LHS, RHS)); 00070 } 00071 Constant *CreateUDiv(Constant *LHS, Constant *RHS, bool isExact = false)const{ 00072 return Fold(ConstantExpr::getUDiv(LHS, RHS, isExact)); 00073 } 00074 Constant *CreateSDiv(Constant *LHS, Constant *RHS, bool isExact = false)const{ 00075 return Fold(ConstantExpr::getSDiv(LHS, RHS, isExact)); 00076 } 00077 Constant *CreateFDiv(Constant *LHS, Constant *RHS) const { 00078 return Fold(ConstantExpr::getFDiv(LHS, RHS)); 00079 } 00080 Constant *CreateURem(Constant *LHS, Constant *RHS) const { 00081 return Fold(ConstantExpr::getURem(LHS, RHS)); 00082 } 00083 Constant *CreateSRem(Constant *LHS, Constant *RHS) const { 00084 return Fold(ConstantExpr::getSRem(LHS, RHS)); 00085 } 00086 Constant *CreateFRem(Constant *LHS, Constant *RHS) const { 00087 return Fold(ConstantExpr::getFRem(LHS, RHS)); 00088 } 00089 Constant *CreateShl(Constant *LHS, Constant *RHS, 00090 bool HasNUW = false, bool HasNSW = false) const { 00091 return Fold(ConstantExpr::getShl(LHS, RHS, HasNUW, HasNSW)); 00092 } 00093 Constant *CreateLShr(Constant *LHS, Constant *RHS, bool isExact = false)const{ 00094 return Fold(ConstantExpr::getLShr(LHS, RHS, isExact)); 00095 } 00096 Constant *CreateAShr(Constant *LHS, Constant *RHS, bool isExact = false)const{ 00097 return Fold(ConstantExpr::getAShr(LHS, RHS, isExact)); 00098 } 00099 Constant *CreateAnd(Constant *LHS, Constant *RHS) const { 00100 return Fold(ConstantExpr::getAnd(LHS, RHS)); 00101 } 00102 Constant *CreateOr(Constant *LHS, Constant *RHS) const { 00103 return Fold(ConstantExpr::getOr(LHS, RHS)); 00104 } 00105 Constant *CreateXor(Constant *LHS, Constant *RHS) const { 00106 return Fold(ConstantExpr::getXor(LHS, RHS)); 00107 } 00108 00109 Constant *CreateBinOp(Instruction::BinaryOps Opc, 00110 Constant *LHS, Constant *RHS) const { 00111 return Fold(ConstantExpr::get(Opc, LHS, RHS)); 00112 } 00113 00114 //===--------------------------------------------------------------------===// 00115 // Unary Operators 00116 //===--------------------------------------------------------------------===// 00117 00118 Constant *CreateNeg(Constant *C, 00119 bool HasNUW = false, bool HasNSW = false) const { 00120 return Fold(ConstantExpr::getNeg(C, HasNUW, HasNSW)); 00121 } 00122 Constant *CreateFNeg(Constant *C) const { 00123 return Fold(ConstantExpr::getFNeg(C)); 00124 } 00125 Constant *CreateNot(Constant *C) const { 00126 return Fold(ConstantExpr::getNot(C)); 00127 } 00128 00129 //===--------------------------------------------------------------------===// 00130 // Memory Instructions 00131 //===--------------------------------------------------------------------===// 00132 00133 Constant *CreateGetElementPtr(Constant *C, 00134 ArrayRef<Constant *> IdxList) const { 00135 return Fold(ConstantExpr::getGetElementPtr(C, IdxList)); 00136 } 00137 Constant *CreateGetElementPtr(Constant *C, Constant *Idx) const { 00138 // This form of the function only exists to avoid ambiguous overload 00139 // warnings about whether to convert Idx to ArrayRef<Constant *> or 00140 // ArrayRef<Value *>. 00141 return Fold(ConstantExpr::getGetElementPtr(C, Idx)); 00142 } 00143 Constant *CreateGetElementPtr(Constant *C, 00144 ArrayRef<Value *> IdxList) const { 00145 return Fold(ConstantExpr::getGetElementPtr(C, IdxList)); 00146 } 00147 00148 Constant *CreateInBoundsGetElementPtr(Constant *C, 00149 ArrayRef<Constant *> IdxList) const { 00150 return Fold(ConstantExpr::getInBoundsGetElementPtr(C, IdxList)); 00151 } 00152 Constant *CreateInBoundsGetElementPtr(Constant *C, Constant *Idx) const { 00153 // This form of the function only exists to avoid ambiguous overload 00154 // warnings about whether to convert Idx to ArrayRef<Constant *> or 00155 // ArrayRef<Value *>. 00156 return Fold(ConstantExpr::getInBoundsGetElementPtr(C, Idx)); 00157 } 00158 Constant *CreateInBoundsGetElementPtr(Constant *C, 00159 ArrayRef<Value *> IdxList) const { 00160 return Fold(ConstantExpr::getInBoundsGetElementPtr(C, IdxList)); 00161 } 00162 00163 //===--------------------------------------------------------------------===// 00164 // Cast/Conversion Operators 00165 //===--------------------------------------------------------------------===// 00166 00167 Constant *CreateCast(Instruction::CastOps Op, Constant *C, 00168 Type *DestTy) const { 00169 if (C->getType() == DestTy) 00170 return C; // avoid calling Fold 00171 return Fold(ConstantExpr::getCast(Op, C, DestTy)); 00172 } 00173 Constant *CreateIntCast(Constant *C, Type *DestTy, 00174 bool isSigned) const { 00175 if (C->getType() == DestTy) 00176 return C; // avoid calling Fold 00177 return Fold(ConstantExpr::getIntegerCast(C, DestTy, isSigned)); 00178 } 00179 Constant *CreatePointerCast(Constant *C, Type *DestTy) const { 00180 if (C->getType() == DestTy) 00181 return C; // avoid calling Fold 00182 return Fold(ConstantExpr::getPointerCast(C, DestTy)); 00183 } 00184 Constant *CreateFPCast(Constant *C, Type *DestTy) const { 00185 if (C->getType() == DestTy) 00186 return C; // avoid calling Fold 00187 return Fold(ConstantExpr::getFPCast(C, DestTy)); 00188 } 00189 Constant *CreateBitCast(Constant *C, Type *DestTy) const { 00190 return CreateCast(Instruction::BitCast, C, DestTy); 00191 } 00192 Constant *CreateIntToPtr(Constant *C, Type *DestTy) const { 00193 return CreateCast(Instruction::IntToPtr, C, DestTy); 00194 } 00195 Constant *CreatePtrToInt(Constant *C, Type *DestTy) const { 00196 return CreateCast(Instruction::PtrToInt, C, DestTy); 00197 } 00198 Constant *CreateZExtOrBitCast(Constant *C, Type *DestTy) const { 00199 if (C->getType() == DestTy) 00200 return C; // avoid calling Fold 00201 return Fold(ConstantExpr::getZExtOrBitCast(C, DestTy)); 00202 } 00203 Constant *CreateSExtOrBitCast(Constant *C, Type *DestTy) const { 00204 if (C->getType() == DestTy) 00205 return C; // avoid calling Fold 00206 return Fold(ConstantExpr::getSExtOrBitCast(C, DestTy)); 00207 } 00208 Constant *CreateTruncOrBitCast(Constant *C, Type *DestTy) const { 00209 if (C->getType() == DestTy) 00210 return C; // avoid calling Fold 00211 return Fold(ConstantExpr::getTruncOrBitCast(C, DestTy)); 00212 } 00213 00214 //===--------------------------------------------------------------------===// 00215 // Compare Instructions 00216 //===--------------------------------------------------------------------===// 00217 00218 Constant *CreateICmp(CmpInst::Predicate P, Constant *LHS, 00219 Constant *RHS) const { 00220 return Fold(ConstantExpr::getCompare(P, LHS, RHS)); 00221 } 00222 Constant *CreateFCmp(CmpInst::Predicate P, Constant *LHS, 00223 Constant *RHS) const { 00224 return Fold(ConstantExpr::getCompare(P, LHS, RHS)); 00225 } 00226 00227 //===--------------------------------------------------------------------===// 00228 // Other Instructions 00229 //===--------------------------------------------------------------------===// 00230 00231 Constant *CreateSelect(Constant *C, Constant *True, Constant *False) const { 00232 return Fold(ConstantExpr::getSelect(C, True, False)); 00233 } 00234 00235 Constant *CreateExtractElement(Constant *Vec, Constant *Idx) const { 00236 return Fold(ConstantExpr::getExtractElement(Vec, Idx)); 00237 } 00238 00239 Constant *CreateInsertElement(Constant *Vec, Constant *NewElt, 00240 Constant *Idx) const { 00241 return Fold(ConstantExpr::getInsertElement(Vec, NewElt, Idx)); 00242 } 00243 00244 Constant *CreateShuffleVector(Constant *V1, Constant *V2, 00245 Constant *Mask) const { 00246 return Fold(ConstantExpr::getShuffleVector(V1, V2, Mask)); 00247 } 00248 00249 Constant *CreateExtractValue(Constant *Agg, 00250 ArrayRef<unsigned> IdxList) const { 00251 return Fold(ConstantExpr::getExtractValue(Agg, IdxList)); 00252 } 00253 00254 Constant *CreateInsertValue(Constant *Agg, Constant *Val, 00255 ArrayRef<unsigned> IdxList) const { 00256 return Fold(ConstantExpr::getInsertValue(Agg, Val, IdxList)); 00257 } 00258 }; 00259 00260 } 00261 00262 #endif