1 //===- ConstantFolder.h - Constant folding helper ---------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file defines the ConstantFolder class, a helper for IRBuilder. 10 // It provides IRBuilder with a set of methods for creating constants 11 // with minimal folding. For general constant creation and folding, 12 // use ConstantExpr and the routines in llvm/Analysis/ConstantFolding.h. 13 // 14 //===----------------------------------------------------------------------===// 15 16 #ifndef LLVM_IR_CONSTANTFOLDER_H 17 #define LLVM_IR_CONSTANTFOLDER_H 18 19 #include "llvm/ADT/ArrayRef.h" 20 #include "llvm/IR/Constants.h" 21 #include "llvm/IR/InstrTypes.h" 22 #include "llvm/IR/Instruction.h" 23 24 namespace llvm { 25 26 /// ConstantFolder - Create constants with minimum, target independent, folding. 27 class ConstantFolder { 28 public: 29 explicit ConstantFolder() = default; 30 31 //===--------------------------------------------------------------------===// 32 // Binary Operators 33 //===--------------------------------------------------------------------===// 34 35 Constant *CreateAdd(Constant *LHS, Constant *RHS, 36 bool HasNUW = false, bool HasNSW = false) const { 37 return ConstantExpr::getAdd(LHS, RHS, HasNUW, HasNSW); 38 } 39 40 Constant *CreateFAdd(Constant *LHS, Constant *RHS) const { 41 return ConstantExpr::getFAdd(LHS, RHS); 42 } 43 44 Constant *CreateSub(Constant *LHS, Constant *RHS, 45 bool HasNUW = false, bool HasNSW = false) const { 46 return ConstantExpr::getSub(LHS, RHS, HasNUW, HasNSW); 47 } 48 49 Constant *CreateFSub(Constant *LHS, Constant *RHS) const { 50 return ConstantExpr::getFSub(LHS, RHS); 51 } 52 53 Constant *CreateMul(Constant *LHS, Constant *RHS, 54 bool HasNUW = false, bool HasNSW = false) const { 55 return ConstantExpr::getMul(LHS, RHS, HasNUW, HasNSW); 56 } 57 58 Constant *CreateFMul(Constant *LHS, Constant *RHS) const { 59 return ConstantExpr::getFMul(LHS, RHS); 60 } 61 62 Constant *CreateUDiv(Constant *LHS, Constant *RHS, 63 bool isExact = false) const { 64 return ConstantExpr::getUDiv(LHS, RHS, isExact); 65 } 66 67 Constant *CreateSDiv(Constant *LHS, Constant *RHS, 68 bool isExact = false) const { 69 return ConstantExpr::getSDiv(LHS, RHS, isExact); 70 } 71 72 Constant *CreateFDiv(Constant *LHS, Constant *RHS) const { 73 return ConstantExpr::getFDiv(LHS, RHS); 74 } 75 76 Constant *CreateURem(Constant *LHS, Constant *RHS) const { 77 return ConstantExpr::getURem(LHS, RHS); 78 } 79 80 Constant *CreateSRem(Constant *LHS, Constant *RHS) const { 81 return ConstantExpr::getSRem(LHS, RHS); 82 } 83 84 Constant *CreateFRem(Constant *LHS, Constant *RHS) const { 85 return ConstantExpr::getFRem(LHS, RHS); 86 } 87 88 Constant *CreateShl(Constant *LHS, Constant *RHS, 89 bool HasNUW = false, bool HasNSW = false) const { 90 return ConstantExpr::getShl(LHS, RHS, HasNUW, HasNSW); 91 } 92 93 Constant *CreateLShr(Constant *LHS, Constant *RHS, 94 bool isExact = false) const { 95 return ConstantExpr::getLShr(LHS, RHS, isExact); 96 } 97 98 Constant *CreateAShr(Constant *LHS, Constant *RHS, 99 bool isExact = false) const { 100 return ConstantExpr::getAShr(LHS, RHS, isExact); 101 } 102 103 Constant *CreateAnd(Constant *LHS, Constant *RHS) const { 104 return ConstantExpr::getAnd(LHS, RHS); 105 } 106 107 Constant *CreateOr(Constant *LHS, Constant *RHS) const { 108 return ConstantExpr::getOr(LHS, RHS); 109 } 110 111 Constant *CreateXor(Constant *LHS, Constant *RHS) const { 112 return ConstantExpr::getXor(LHS, RHS); 113 } 114 115 Constant *CreateBinOp(Instruction::BinaryOps Opc, 116 Constant *LHS, Constant *RHS) const { 117 return ConstantExpr::get(Opc, LHS, RHS); 118 } 119 120 //===--------------------------------------------------------------------===// 121 // Unary Operators 122 //===--------------------------------------------------------------------===// 123 124 Constant *CreateNeg(Constant *C, 125 bool HasNUW = false, bool HasNSW = false) const { 126 return ConstantExpr::getNeg(C, HasNUW, HasNSW); 127 } 128 129 Constant *CreateFNeg(Constant *C) const { 130 return ConstantExpr::getFNeg(C); 131 } 132 133 Constant *CreateNot(Constant *C) const { 134 return ConstantExpr::getNot(C); 135 } 136 137 Constant *CreateUnOp(Instruction::UnaryOps Opc, Constant *C) const { 138 return ConstantExpr::get(Opc, C); 139 } 140 141 //===--------------------------------------------------------------------===// 142 // Memory Instructions 143 //===--------------------------------------------------------------------===// 144 145 Constant *CreateGetElementPtr(Type *Ty, Constant *C, 146 ArrayRef<Constant *> IdxList) const { 147 return ConstantExpr::getGetElementPtr(Ty, C, IdxList); 148 } 149 150 Constant *CreateGetElementPtr(Type *Ty, Constant *C, Constant *Idx) const { 151 // This form of the function only exists to avoid ambiguous overload 152 // warnings about whether to convert Idx to ArrayRef<Constant *> or 153 // ArrayRef<Value *>. 154 return ConstantExpr::getGetElementPtr(Ty, C, Idx); 155 } 156 157 Constant *CreateGetElementPtr(Type *Ty, Constant *C, 158 ArrayRef<Value *> IdxList) const { 159 return ConstantExpr::getGetElementPtr(Ty, C, IdxList); 160 } 161 162 Constant *CreateInBoundsGetElementPtr(Type *Ty, Constant *C, 163 ArrayRef<Constant *> IdxList) const { 164 return ConstantExpr::getInBoundsGetElementPtr(Ty, C, IdxList); 165 } 166 167 Constant *CreateInBoundsGetElementPtr(Type *Ty, Constant *C, 168 Constant *Idx) const { 169 // This form of the function only exists to avoid ambiguous overload 170 // warnings about whether to convert Idx to ArrayRef<Constant *> or 171 // ArrayRef<Value *>. 172 return ConstantExpr::getInBoundsGetElementPtr(Ty, C, Idx); 173 } 174 175 Constant *CreateInBoundsGetElementPtr(Type *Ty, Constant *C, 176 ArrayRef<Value *> IdxList) const { 177 return ConstantExpr::getInBoundsGetElementPtr(Ty, C, IdxList); 178 } 179 180 //===--------------------------------------------------------------------===// 181 // Cast/Conversion Operators 182 //===--------------------------------------------------------------------===// 183 184 Constant *CreateCast(Instruction::CastOps Op, Constant *C, 185 Type *DestTy) const { 186 return ConstantExpr::getCast(Op, C, DestTy); 187 } 188 189 Constant *CreatePointerCast(Constant *C, Type *DestTy) const { 190 return ConstantExpr::getPointerCast(C, DestTy); 191 } 192 193 Constant *CreatePointerBitCastOrAddrSpaceCast(Constant *C, 194 Type *DestTy) const { 195 return ConstantExpr::getPointerBitCastOrAddrSpaceCast(C, DestTy); 196 } 197 198 Constant *CreateIntCast(Constant *C, Type *DestTy, 199 bool isSigned) const { 200 return ConstantExpr::getIntegerCast(C, DestTy, isSigned); 201 } 202 203 Constant *CreateFPCast(Constant *C, Type *DestTy) const { 204 return ConstantExpr::getFPCast(C, DestTy); 205 } 206 207 Constant *CreateBitCast(Constant *C, Type *DestTy) const { 208 return CreateCast(Instruction::BitCast, C, DestTy); 209 } 210 211 Constant *CreateIntToPtr(Constant *C, Type *DestTy) const { 212 return CreateCast(Instruction::IntToPtr, C, DestTy); 213 } 214 215 Constant *CreatePtrToInt(Constant *C, Type *DestTy) const { 216 return CreateCast(Instruction::PtrToInt, C, DestTy); 217 } 218 219 Constant *CreateZExtOrBitCast(Constant *C, Type *DestTy) const { 220 return ConstantExpr::getZExtOrBitCast(C, DestTy); 221 } 222 223 Constant *CreateSExtOrBitCast(Constant *C, Type *DestTy) const { 224 return ConstantExpr::getSExtOrBitCast(C, DestTy); 225 } 226 227 Constant *CreateTruncOrBitCast(Constant *C, Type *DestTy) const { 228 return ConstantExpr::getTruncOrBitCast(C, DestTy); 229 } 230 231 //===--------------------------------------------------------------------===// 232 // Compare Instructions 233 //===--------------------------------------------------------------------===// 234 235 Constant *CreateICmp(CmpInst::Predicate P, Constant *LHS, 236 Constant *RHS) const { 237 return ConstantExpr::getCompare(P, LHS, RHS); 238 } 239 240 Constant *CreateFCmp(CmpInst::Predicate P, Constant *LHS, 241 Constant *RHS) const { 242 return ConstantExpr::getCompare(P, LHS, RHS); 243 } 244 245 //===--------------------------------------------------------------------===// 246 // Other Instructions 247 //===--------------------------------------------------------------------===// 248 249 Constant *CreateSelect(Constant *C, Constant *True, Constant *False) const { 250 return ConstantExpr::getSelect(C, True, False); 251 } 252 253 Constant *CreateExtractElement(Constant *Vec, Constant *Idx) const { 254 return ConstantExpr::getExtractElement(Vec, Idx); 255 } 256 257 Constant *CreateInsertElement(Constant *Vec, Constant *NewElt, 258 Constant *Idx) const { 259 return ConstantExpr::getInsertElement(Vec, NewElt, Idx); 260 } 261 262 Constant *CreateShuffleVector(Constant *V1, Constant *V2, 263 Constant *Mask) const { 264 return ConstantExpr::getShuffleVector(V1, V2, Mask); 265 } 266 267 Constant *CreateExtractValue(Constant *Agg, 268 ArrayRef<unsigned> IdxList) const { 269 return ConstantExpr::getExtractValue(Agg, IdxList); 270 } 271 272 Constant *CreateInsertValue(Constant *Agg, Constant *Val, 273 ArrayRef<unsigned> IdxList) const { 274 return ConstantExpr::getInsertValue(Agg, Val, IdxList); 275 } 276 }; 277 278 } // end namespace llvm 279 280 #endif // LLVM_IR_CONSTANTFOLDER_H 281