1//===- VNCoercion.h - Value Numbering Coercion Utilities --------*- 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/// \file / This file provides routines used by LLVM's value numbering passes to
9/// perform various forms of value extraction from memory when the types are not
10/// identical. For example, given
11///
12/// store i32 8, i32 *%foo
13/// %a = bitcast i32 *%foo to i16
14/// %val = load i16, i16 *%a
15///
16/// It possible to extract the value of the load of %a from the store to %foo.
17/// These routines know how to tell whether they can do that (the analyze*
18/// routines), and can also insert the necessary IR to do it (the get*
19/// routines).
20
21#ifndef LLVM_TRANSFORMS_UTILS_VNCOERCION_H
22#define LLVM_TRANSFORMS_UTILS_VNCOERCION_H
23
24namespace llvm {
25class Constant;
26class StoreInst;
27class LoadInst;
28class MemIntrinsic;
29class Instruction;
30class IRBuilderBase;
31class Value;
32class Type;
33class DataLayout;
34namespace VNCoercion {
35/// Return true if CoerceAvailableValueToLoadType would succeed if it was
36/// called.
37bool canCoerceMustAliasedValueToLoad(Value *StoredVal, Type *LoadTy,
38 const DataLayout &DL);
39
40/// If we saw a store of a value to memory, and then a load from a must-aliased
41/// pointer of a different type, try to coerce the stored value to the loaded
42/// type. LoadedTy is the type of the load we want to replace. IRB is
43/// IRBuilder used to insert new instructions.
44///
45/// If we can't do it, return null.
46Value *coerceAvailableValueToLoadType(Value *StoredVal, Type *LoadedTy,
47 IRBuilderBase &IRB, const DataLayout &DL);
48
49/// This function determines whether a value for the pointer LoadPtr can be
50/// extracted from the store at DepSI.
51///
52/// On success, it returns the offset into DepSI that extraction would start.
53/// On failure, it returns -1.
54int analyzeLoadFromClobberingStore(Type *LoadTy, Value *LoadPtr,
55 StoreInst *DepSI, const DataLayout &DL);
56
57/// This function determines whether a value for the pointer LoadPtr can be
58/// extracted from the load at DepLI.
59///
60/// On success, it returns the offset into DepLI that extraction would start.
61/// On failure, it returns -1.
62int analyzeLoadFromClobberingLoad(Type *LoadTy, Value *LoadPtr, LoadInst *DepLI,
63 const DataLayout &DL);
64
65/// This function determines whether a value for the pointer LoadPtr can be
66/// extracted from the memory intrinsic at DepMI.
67///
68/// On success, it returns the offset into DepMI that extraction would start.
69/// On failure, it returns -1.
70int analyzeLoadFromClobberingMemInst(Type *LoadTy, Value *LoadPtr,
71 MemIntrinsic *DepMI, const DataLayout &DL);
72
73/// If analyzeLoadFromClobberingStore returned an offset, this function can be
74/// used to actually perform the extraction of the bits from the store. It
75/// inserts instructions to do so at InsertPt, and returns the extracted value.
76Value *getStoreValueForLoad(Value *SrcVal, unsigned Offset, Type *LoadTy,
77 Instruction *InsertPt, const DataLayout &DL);
78// This is the same as getStoreValueForLoad, except it performs no insertion
79// It only allows constant inputs.
80Constant *getConstantStoreValueForLoad(Constant *SrcVal, unsigned Offset,
81 Type *LoadTy, const DataLayout &DL);
82
83/// If analyzeLoadFromClobberingLoad returned an offset, this function can be
84/// used to actually perform the extraction of the bits from the load, including
85/// any necessary load widening. It inserts instructions to do so at InsertPt,
86/// and returns the extracted value.
87Value *getLoadValueForLoad(LoadInst *SrcVal, unsigned Offset, Type *LoadTy,
88 Instruction *InsertPt, const DataLayout &DL);
89// This is the same as getLoadValueForLoad, except it is given the load value as
90// a constant. It returns nullptr if it would require widening the load.
91Constant *getConstantLoadValueForLoad(Constant *SrcVal, unsigned Offset,
92 Type *LoadTy, const DataLayout &DL);
93
94/// If analyzeLoadFromClobberingMemInst returned an offset, this function can be
95/// used to actually perform the extraction of the bits from the memory
96/// intrinsic. It inserts instructions to do so at InsertPt, and returns the
97/// extracted value.
98Value *getMemInstValueForLoad(MemIntrinsic *SrcInst, unsigned Offset,
99 Type *LoadTy, Instruction *InsertPt,
100 const DataLayout &DL);
101// This is the same as getStoreValueForLoad, except it performs no insertion.
102// It returns nullptr if it cannot produce a constant.
103Constant *getConstantMemInstValueForLoad(MemIntrinsic *SrcInst, unsigned Offset,
104 Type *LoadTy, const DataLayout &DL);
105}
106}
107#endif
108