LLVM 19.0.0git
InstructionSimplify.h
Go to the documentation of this file.
1//===-- InstructionSimplify.h - Fold instrs into simpler forms --*- 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 declares routines for folding instructions into simpler forms
10// that do not require creating new instructions. This does constant folding
11// ("add i32 1, 1" -> "2") but can also handle non-constant operands, either
12// returning a constant ("and i32 %x, 0" -> "0") or an already existing value
13// ("and i32 %x, %x" -> "%x"). If the simplification is also an instruction
14// then it dominates the original instruction.
15//
16// These routines implicitly resolve undef uses. The easiest way to be safe when
17// using these routines to obtain simplified values for existing instructions is
18// to always replace all uses of the instructions with the resulting simplified
19// values. This will prevent other code from seeing the same undef uses and
20// resolving them to different values.
21//
22// They require that all the IR that they encounter be valid and inserted into a
23// parent function.
24//
25// Additionally, these routines can't simplify to the instructions that are not
26// def-reachable, meaning we can't just scan the basic block for instructions
27// to simplify to.
28//
29//===----------------------------------------------------------------------===//
30
31#ifndef LLVM_ANALYSIS_INSTRUCTIONSIMPLIFY_H
32#define LLVM_ANALYSIS_INSTRUCTIONSIMPLIFY_H
33
35#include "llvm/IR/FPEnv.h"
36
37namespace llvm {
38
39template <typename T, typename... TArgs> class AnalysisManager;
40template <class T> class ArrayRef;
41class AssumptionCache;
42class BinaryOperator;
43class CallBase;
44class DataLayout;
45class DominatorTree;
46class Function;
47class Instruction;
48class LoadInst;
49struct LoopStandardAnalysisResults;
50class Pass;
51template <class T, unsigned n> class SmallSetVector;
52class TargetLibraryInfo;
53class Type;
54class Value;
55
56// NOTE: the explicit multiple argument versions of these functions are
57// deprecated.
58// Please use the SimplifyQuery versions in new code.
59
60/// Given operands for an Add, fold the result or return null.
61Value *simplifyAddInst(Value *LHS, Value *RHS, bool IsNSW, bool IsNUW,
62 const SimplifyQuery &Q);
63
64/// Given operands for a Sub, fold the result or return null.
65Value *simplifySubInst(Value *LHS, Value *RHS, bool IsNSW, bool IsNUW,
66 const SimplifyQuery &Q);
67
68/// Given operands for a Mul, fold the result or return null.
69Value *simplifyMulInst(Value *LHS, Value *RHS, bool IsNSW, bool IsNUW,
70 const SimplifyQuery &Q);
71
72/// Given operands for an SDiv, fold the result or return null.
73Value *simplifySDivInst(Value *LHS, Value *RHS, bool IsExact,
74 const SimplifyQuery &Q);
75
76/// Given operands for a UDiv, fold the result or return null.
77Value *simplifyUDivInst(Value *LHS, Value *RHS, bool IsExact,
78 const SimplifyQuery &Q);
79
80/// Given operands for an SRem, fold the result or return null.
81Value *simplifySRemInst(Value *LHS, Value *RHS, const SimplifyQuery &Q);
82
83/// Given operands for a URem, fold the result or return null.
84Value *simplifyURemInst(Value *LHS, Value *RHS, const SimplifyQuery &Q);
85
86/// Given operand for an FNeg, fold the result or return null.
87Value *simplifyFNegInst(Value *Op, FastMathFlags FMF, const SimplifyQuery &Q);
88
89
90/// Given operands for an FAdd, fold the result or return null.
91Value *
92simplifyFAddInst(Value *LHS, Value *RHS, FastMathFlags FMF,
93 const SimplifyQuery &Q,
96
97/// Given operands for an FSub, fold the result or return null.
98Value *
99simplifyFSubInst(Value *LHS, Value *RHS, FastMathFlags FMF,
100 const SimplifyQuery &Q,
103
104/// Given operands for an FMul, fold the result or return null.
105Value *
106simplifyFMulInst(Value *LHS, Value *RHS, FastMathFlags FMF,
107 const SimplifyQuery &Q,
110
111/// Given operands for the multiplication of a FMA, fold the result or return
112/// null. In contrast to simplifyFMulInst, this function will not perform
113/// simplifications whose unrounded results differ when rounded to the argument
114/// type.
115Value *simplifyFMAFMul(Value *LHS, Value *RHS, FastMathFlags FMF,
116 const SimplifyQuery &Q,
119
120/// Given operands for an FDiv, fold the result or return null.
121Value *
122simplifyFDivInst(Value *LHS, Value *RHS, FastMathFlags FMF,
123 const SimplifyQuery &Q,
126
127/// Given operands for an FRem, fold the result or return null.
128Value *
129simplifyFRemInst(Value *LHS, Value *RHS, FastMathFlags FMF,
130 const SimplifyQuery &Q,
133
134/// Given operands for a Shl, fold the result or return null.
135Value *simplifyShlInst(Value *Op0, Value *Op1, bool IsNSW, bool IsNUW,
136 const SimplifyQuery &Q);
137
138/// Given operands for a LShr, fold the result or return null.
139Value *simplifyLShrInst(Value *Op0, Value *Op1, bool IsExact,
140 const SimplifyQuery &Q);
141
142/// Given operands for a AShr, fold the result or return nulll.
143Value *simplifyAShrInst(Value *Op0, Value *Op1, bool IsExact,
144 const SimplifyQuery &Q);
145
146/// Given operands for an And, fold the result or return null.
147Value *simplifyAndInst(Value *LHS, Value *RHS, const SimplifyQuery &Q);
148
149/// Given operands for an Or, fold the result or return null.
150Value *simplifyOrInst(Value *LHS, Value *RHS, const SimplifyQuery &Q);
151
152/// Given operands for an Xor, fold the result or return null.
153Value *simplifyXorInst(Value *LHS, Value *RHS, const SimplifyQuery &Q);
154
155/// Given operands for an ICmpInst, fold the result or return null.
156Value *simplifyICmpInst(unsigned Predicate, Value *LHS, Value *RHS,
157 const SimplifyQuery &Q);
158
159/// Given operands for an FCmpInst, fold the result or return null.
160Value *simplifyFCmpInst(unsigned Predicate, Value *LHS, Value *RHS,
161 FastMathFlags FMF, const SimplifyQuery &Q);
162
163/// Given operands for a SelectInst, fold the result or return null.
164Value *simplifySelectInst(Value *Cond, Value *TrueVal, Value *FalseVal,
165 const SimplifyQuery &Q);
166
167/// Given operands for a GetElementPtrInst, fold the result or return null.
168Value *simplifyGEPInst(Type *SrcTy, Value *Ptr, ArrayRef<Value *> Indices,
169 bool InBounds, const SimplifyQuery &Q);
170
171/// Given operands for an InsertValueInst, fold the result or return null.
172Value *simplifyInsertValueInst(Value *Agg, Value *Val, ArrayRef<unsigned> Idxs,
173 const SimplifyQuery &Q);
174
175/// Given operands for an InsertElement, fold the result or return null.
176Value *simplifyInsertElementInst(Value *Vec, Value *Elt, Value *Idx,
177 const SimplifyQuery &Q);
178
179/// Given operands for an ExtractValueInst, fold the result or return null.
180Value *simplifyExtractValueInst(Value *Agg, ArrayRef<unsigned> Idxs,
181 const SimplifyQuery &Q);
182
183/// Given operands for an ExtractElementInst, fold the result or return null.
184Value *simplifyExtractElementInst(Value *Vec, Value *Idx,
185 const SimplifyQuery &Q);
186
187/// Given operands for a CastInst, fold the result or return null.
188Value *simplifyCastInst(unsigned CastOpc, Value *Op, Type *Ty,
189 const SimplifyQuery &Q);
190
191/// Given operands for a BinaryIntrinsic, fold the result or return null.
192Value *simplifyBinaryIntrinsic(Intrinsic::ID IID, Type *ReturnType, Value *Op0,
193 Value *Op1, const SimplifyQuery &Q,
194 const CallBase *Call);
195
196/// Given operands for a ShuffleVectorInst, fold the result or return null.
197/// See class ShuffleVectorInst for a description of the mask representation.
198Value *simplifyShuffleVectorInst(Value *Op0, Value *Op1, ArrayRef<int> Mask,
199 Type *RetTy, const SimplifyQuery &Q);
200
201//=== Helper functions for higher up the class hierarchy.
202
203/// Given operands for a CmpInst, fold the result or return null.
204Value *simplifyCmpInst(unsigned Predicate, Value *LHS, Value *RHS,
205 const SimplifyQuery &Q);
206
207/// Given operand for a UnaryOperator, fold the result or return null.
208Value *simplifyUnOp(unsigned Opcode, Value *Op, const SimplifyQuery &Q);
209
210/// Given operand for a UnaryOperator, fold the result or return null.
211/// Try to use FastMathFlags when folding the result.
212Value *simplifyUnOp(unsigned Opcode, Value *Op, FastMathFlags FMF,
213 const SimplifyQuery &Q);
214
215/// Given operands for a BinaryOperator, fold the result or return null.
216Value *simplifyBinOp(unsigned Opcode, Value *LHS, Value *RHS,
217 const SimplifyQuery &Q);
218
219/// Given operands for a BinaryOperator, fold the result or return null.
220/// Try to use FastMathFlags when folding the result.
221Value *simplifyBinOp(unsigned Opcode, Value *LHS, Value *RHS, FastMathFlags FMF,
222 const SimplifyQuery &Q);
223
224/// Given a callsite, callee, and arguments, fold the result or return null.
225Value *simplifyCall(CallBase *Call, Value *Callee, ArrayRef<Value *> Args,
226 const SimplifyQuery &Q);
227
228/// Given a constrained FP intrinsic call, tries to compute its simplified
229/// version. Returns a simplified result or null.
230///
231/// This function provides an additional contract: it guarantees that if
232/// simplification succeeds that the intrinsic is side effect free. As a result,
233/// successful simplification can be used to delete the intrinsic not just
234/// replace its result.
235Value *simplifyConstrainedFPCall(CallBase *Call, const SimplifyQuery &Q);
236
237/// Given an operand for a Freeze, see if we can fold the result.
238/// If not, this returns null.
239Value *simplifyFreezeInst(Value *Op, const SimplifyQuery &Q);
240
241/// Given a load instruction and its pointer operand, fold the result or return
242/// null.
243Value *simplifyLoadInst(LoadInst *LI, Value *PtrOp, const SimplifyQuery &Q);
244
245/// See if we can compute a simplified version of this instruction. If not,
246/// return null.
247Value *simplifyInstruction(Instruction *I, const SimplifyQuery &Q);
248
249/// Like \p simplifyInstruction but the operands of \p I are replaced with
250/// \p NewOps. Returns a simplified value, or null if none was found.
251Value *
252simplifyInstructionWithOperands(Instruction *I, ArrayRef<Value *> NewOps,
253 const SimplifyQuery &Q);
254
255/// See if V simplifies when its operand Op is replaced with RepOp. If not,
256/// return null.
257/// AllowRefinement specifies whether the simplification can be a refinement
258/// (e.g. 0 instead of poison), or whether it needs to be strictly identical.
259/// Op and RepOp can be assumed to not be poison when determining refinement.
260///
261/// If DropFlags is passed, then the replacement result is only valid if
262/// poison-generating flags/metadata on those instructions are dropped. This
263/// is only useful in conjunction with AllowRefinement=false.
264Value *
265simplifyWithOpReplaced(Value *V, Value *Op, Value *RepOp,
266 const SimplifyQuery &Q, bool AllowRefinement,
267 SmallVectorImpl<Instruction *> *DropFlags = nullptr);
268
269/// Replace all uses of 'I' with 'SimpleV' and simplify the uses recursively.
270///
271/// This first performs a normal RAUW of I with SimpleV. It then recursively
272/// attempts to simplify those users updated by the operation. The 'I'
273/// instruction must not be equal to the simplified value 'SimpleV'.
274/// If UnsimplifiedUsers is provided, instructions that could not be simplified
275/// are added to it.
276///
277/// The function returns true if any simplifications were performed.
279 Instruction *I, Value *SimpleV, const TargetLibraryInfo *TLI = nullptr,
280 const DominatorTree *DT = nullptr, AssumptionCache *AC = nullptr,
281 SmallSetVector<Instruction *, 8> *UnsimplifiedUsers = nullptr);
282
283// These helper functions return a SimplifyQuery structure that contains as
284// many of the optional analysis we use as are currently valid. This is the
285// strongly preferred way of constructing SimplifyQuery in passes.
286const SimplifyQuery getBestSimplifyQuery(Pass &, Function &);
287template <class T, class... TArgs>
288const SimplifyQuery getBestSimplifyQuery(AnalysisManager<T, TArgs...> &,
289 Function &);
290const SimplifyQuery getBestSimplifyQuery(LoopStandardAnalysisResults &,
291 const DataLayout &);
292} // end namespace llvm
293
294#endif
aarch64 AArch64 CCMP Pass
RelocType Type
Definition: COFFYAML.cpp:391
return RetTy
Returns the sub type a function will return at a given Idx Should correspond to the result type of an ExtractValue instruction executed with just that one unsigned Idx
This file contains the declarations of entities that describe floating point environment and related ...
#define I(x, y, z)
Definition: MD5.cpp:58
#define T
const SmallVectorImpl< MachineOperand > & Cond
Value * RHS
Value * LHS
ExceptionBehavior
Exception behavior used for floating point operations.
Definition: FPEnv.h:38
@ ebIgnore
This corresponds to "fpexcept.ignore".
Definition: FPEnv.h:39
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
Value * simplifyAShrInst(Value *Op0, Value *Op1, bool IsExact, const SimplifyQuery &Q)
Given operands for a AShr, fold the result or return nulll.
Value * simplifyFMulInst(Value *LHS, Value *RHS, FastMathFlags FMF, const SimplifyQuery &Q, fp::ExceptionBehavior ExBehavior=fp::ebIgnore, RoundingMode Rounding=RoundingMode::NearestTiesToEven)
Given operands for an FMul, fold the result or return null.
Value * simplifyFreezeInst(Value *Op, const SimplifyQuery &Q)
Given an operand for a Freeze, see if we can fold the result.
Value * simplifySDivInst(Value *LHS, Value *RHS, bool IsExact, const SimplifyQuery &Q)
Given operands for an SDiv, fold the result or return null.
Value * simplifyUnOp(unsigned Opcode, Value *Op, const SimplifyQuery &Q)
Given operand for a UnaryOperator, fold the result or return null.
Value * simplifyMulInst(Value *LHS, Value *RHS, bool IsNSW, bool IsNUW, const SimplifyQuery &Q)
Given operands for a Mul, fold the result or return null.
Value * simplifyInstructionWithOperands(Instruction *I, ArrayRef< Value * > NewOps, const SimplifyQuery &Q)
Like simplifyInstruction but the operands of I are replaced with NewOps.
Value * simplifyCall(CallBase *Call, Value *Callee, ArrayRef< Value * > Args, const SimplifyQuery &Q)
Given a callsite, callee, and arguments, fold the result or return null.
Value * simplifyShuffleVectorInst(Value *Op0, Value *Op1, ArrayRef< int > Mask, Type *RetTy, const SimplifyQuery &Q)
Given operands for a ShuffleVectorInst, fold the result or return null.
Value * simplifyOrInst(Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for an Or, fold the result or return null.
Value * simplifyXorInst(Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for an Xor, fold the result or return null.
Value * simplifyCastInst(unsigned CastOpc, Value *Op, Type *Ty, const SimplifyQuery &Q)
Given operands for a CastInst, fold the result or return null.
Value * simplifyInstruction(Instruction *I, const SimplifyQuery &Q)
See if we can compute a simplified version of this instruction.
Value * simplifySubInst(Value *LHS, Value *RHS, bool IsNSW, bool IsNUW, const SimplifyQuery &Q)
Given operands for a Sub, fold the result or return null.
Value * simplifyAddInst(Value *LHS, Value *RHS, bool IsNSW, bool IsNUW, const SimplifyQuery &Q)
Given operands for an Add, fold the result or return null.
bool replaceAndRecursivelySimplify(Instruction *I, Value *SimpleV, const TargetLibraryInfo *TLI=nullptr, const DominatorTree *DT=nullptr, AssumptionCache *AC=nullptr, SmallSetVector< Instruction *, 8 > *UnsimplifiedUsers=nullptr)
Replace all uses of 'I' with 'SimpleV' and simplify the uses recursively.
Value * simplifyShlInst(Value *Op0, Value *Op1, bool IsNSW, bool IsNUW, const SimplifyQuery &Q)
Given operands for a Shl, fold the result or return null.
Value * simplifyFNegInst(Value *Op, FastMathFlags FMF, const SimplifyQuery &Q)
Given operand for an FNeg, fold the result or return null.
Value * simplifyFSubInst(Value *LHS, Value *RHS, FastMathFlags FMF, const SimplifyQuery &Q, fp::ExceptionBehavior ExBehavior=fp::ebIgnore, RoundingMode Rounding=RoundingMode::NearestTiesToEven)
Given operands for an FSub, fold the result or return null.
Value * simplifyFRemInst(Value *LHS, Value *RHS, FastMathFlags FMF, const SimplifyQuery &Q, fp::ExceptionBehavior ExBehavior=fp::ebIgnore, RoundingMode Rounding=RoundingMode::NearestTiesToEven)
Given operands for an FRem, fold the result or return null.
Value * simplifyFAddInst(Value *LHS, Value *RHS, FastMathFlags FMF, const SimplifyQuery &Q, fp::ExceptionBehavior ExBehavior=fp::ebIgnore, RoundingMode Rounding=RoundingMode::NearestTiesToEven)
Given operands for an FAdd, fold the result or return null.
Value * simplifyLShrInst(Value *Op0, Value *Op1, bool IsExact, const SimplifyQuery &Q)
Given operands for a LShr, fold the result or return null.
Value * simplifyAndInst(Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for an And, fold the result or return null.
Value * simplifyExtractValueInst(Value *Agg, ArrayRef< unsigned > Idxs, const SimplifyQuery &Q)
Given operands for an ExtractValueInst, fold the result or return null.
Value * simplifyInsertValueInst(Value *Agg, Value *Val, ArrayRef< unsigned > Idxs, const SimplifyQuery &Q)
Given operands for an InsertValueInst, fold the result or return null.
Value * simplifyICmpInst(unsigned Predicate, Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for an ICmpInst, fold the result or return null.
Value * simplifyFDivInst(Value *LHS, Value *RHS, FastMathFlags FMF, const SimplifyQuery &Q, fp::ExceptionBehavior ExBehavior=fp::ebIgnore, RoundingMode Rounding=RoundingMode::NearestTiesToEven)
Given operands for an FDiv, fold the result or return null.
Value * simplifyLoadInst(LoadInst *LI, Value *PtrOp, const SimplifyQuery &Q)
Given a load instruction and its pointer operand, fold the result or return null.
Value * simplifyFMAFMul(Value *LHS, Value *RHS, FastMathFlags FMF, const SimplifyQuery &Q, fp::ExceptionBehavior ExBehavior=fp::ebIgnore, RoundingMode Rounding=RoundingMode::NearestTiesToEven)
Given operands for the multiplication of a FMA, fold the result or return null.
Value * simplifyConstrainedFPCall(CallBase *Call, const SimplifyQuery &Q)
Given a constrained FP intrinsic call, tries to compute its simplified version.
Value * simplifyBinOp(unsigned Opcode, Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for a BinaryOperator, fold the result or return null.
Value * simplifyCmpInst(unsigned Predicate, Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for a CmpInst, fold the result or return null.
Value * simplifyUDivInst(Value *LHS, Value *RHS, bool IsExact, const SimplifyQuery &Q)
Given operands for a UDiv, fold the result or return null.
DWARFExpression::Operation Op
Value * simplifyBinaryIntrinsic(Intrinsic::ID IID, Type *ReturnType, Value *Op0, Value *Op1, const SimplifyQuery &Q, const CallBase *Call)
Given operands for a BinaryIntrinsic, fold the result or return null.
RoundingMode
Rounding mode.
@ NearestTiesToEven
roundTiesToEven.
ArrayRef(const T &OneElt) -> ArrayRef< T >
Value * simplifyInsertElementInst(Value *Vec, Value *Elt, Value *Idx, const SimplifyQuery &Q)
Given operands for an InsertElement, fold the result or return null.
Value * simplifyWithOpReplaced(Value *V, Value *Op, Value *RepOp, const SimplifyQuery &Q, bool AllowRefinement, SmallVectorImpl< Instruction * > *DropFlags=nullptr)
See if V simplifies when its operand Op is replaced with RepOp.
Value * simplifySRemInst(Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for an SRem, fold the result or return null.
const SimplifyQuery getBestSimplifyQuery(Pass &, Function &)
Value * simplifyFCmpInst(unsigned Predicate, Value *LHS, Value *RHS, FastMathFlags FMF, const SimplifyQuery &Q)
Given operands for an FCmpInst, fold the result or return null.
Value * simplifyGEPInst(Type *SrcTy, Value *Ptr, ArrayRef< Value * > Indices, bool InBounds, const SimplifyQuery &Q)
Given operands for a GetElementPtrInst, fold the result or return null.
Value * simplifyURemInst(Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for a URem, fold the result or return null.
Value * simplifyExtractElementInst(Value *Vec, Value *Idx, const SimplifyQuery &Q)
Given operands for an ExtractElementInst, fold the result or return null.
Value * simplifySelectInst(Value *Cond, Value *TrueVal, Value *FalseVal, const SimplifyQuery &Q)
Given operands for a SelectInst, fold the result or return null.