1//===-- CSKYConstantPoolValue.h - CSKY constantpool value -----*- 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 implements the CSKY specific constantpool value class.
10//
11//===----------------------------------------------------------------------===//
12
13#ifndef LLVM_TARGET_CSKY_CONSTANTPOOLVALUE_H
14#define LLVM_TARGET_CSKY_CONSTANTPOOLVALUE_H
15
16#include "llvm/ADT/StringRef.h"
17#include "llvm/CodeGen/MachineConstantPool.h"
18#include "llvm/Support/Casting.h"
19#include "llvm/Support/ErrorHandling.h"
20#include <cstddef>
21
22namespace llvm {
23
24class BlockAddress;
25class Constant;
26class GlobalValue;
27class LLVMContext;
28class MachineBasicBlock;
29
30namespace CSKYCP {
31enum CSKYCPKind {
32 CPValue,
33 CPExtSymbol,
34 CPBlockAddress,
35 CPMachineBasicBlock,
36 CPJT,
37 CPConstPool
38};
39
40enum CSKYCPModifier { NO_MOD, ADDR, GOT, GOTOFF, PLT, TLSLE, TLSIE, TLSGD };
41} // namespace CSKYCP
42
43/// CSKYConstantPoolValue - CSKY specific constantpool value. This is used to
44/// represent PC-relative displacement between the address of the load
45/// instruction and the constant being loaded, i.e. (&GV-(LPIC+8)).
46class CSKYConstantPoolValue : public MachineConstantPoolValue {
47protected:
48 CSKYCP::CSKYCPKind Kind; // Kind of constant.
49 unsigned PCAdjust; // Extra adjustment if constantpool is pc-relative.
50 CSKYCP::CSKYCPModifier Modifier; // GV modifier
51 bool AddCurrentAddress;
52
53 unsigned LabelId = 0;
54
55 CSKYConstantPoolValue(Type *Ty, CSKYCP::CSKYCPKind Kind, unsigned PCAdjust,
56 CSKYCP::CSKYCPModifier Modifier, bool AddCurrentAddress,
57 unsigned ID = 0);
58
59public:
60 const char *getModifierText() const;
61 unsigned getPCAdjustment() const { return PCAdjust; }
62 bool mustAddCurrentAddress() const { return AddCurrentAddress; }
63 CSKYCP::CSKYCPModifier getModifier() const { return Modifier; }
64 unsigned getLabelID() const { return LabelId; }
65
66 bool isGlobalValue() const { return Kind == CSKYCP::CPValue; }
67 bool isExtSymbol() const { return Kind == CSKYCP::CPExtSymbol; }
68 bool isBlockAddress() const { return Kind == CSKYCP::CPBlockAddress; }
69 bool isMachineBasicBlock() const {
70 return Kind == CSKYCP::CPMachineBasicBlock;
71 }
72 bool isJT() const { return Kind == CSKYCP::CPJT; }
73 bool isConstPool() const { return Kind == CSKYCP::CPConstPool; }
74
75 int getExistingMachineCPValue(MachineConstantPool *CP,
76 Align Alignment) override;
77
78 void addSelectionDAGCSEId(FoldingSetNodeID &ID) override;
79
80 void print(raw_ostream &O) const override;
81
82 bool equals(const CSKYConstantPoolValue *A) const {
83 return this->LabelId == A->LabelId && this->PCAdjust == A->PCAdjust &&
84 this->Modifier == A->Modifier;
85 }
86
87 template <typename Derived>
88 int getExistingMachineCPValueImpl(MachineConstantPool *CP, Align Alignment) {
89 const std::vector<MachineConstantPoolEntry> &Constants = CP->getConstants();
90 for (unsigned i = 0, e = Constants.size(); i != e; ++i) {
91 if (Constants[i].isMachineConstantPoolEntry() &&
92 Constants[i].getAlign() >= Alignment) {
93 auto *CPV =
94 static_cast<CSKYConstantPoolValue *>(Constants[i].Val.MachineCPVal);
95 if (Derived *APC = dyn_cast<Derived>(CPV))
96 if (cast<Derived>(this)->equals(APC))
97 return i;
98 }
99 }
100
101 return -1;
102 }
103};
104
105/// CSKY-specific constant pool values for Constants,
106/// Functions, and BlockAddresses.
107class CSKYConstantPoolConstant : public CSKYConstantPoolValue {
108 const Constant *CVal; // Constant being loaded.
109
110 CSKYConstantPoolConstant(const Constant *C, Type *Ty, CSKYCP::CSKYCPKind Kind,
111 unsigned PCAdjust, CSKYCP::CSKYCPModifier Modifier,
112 bool AddCurrentAddress, unsigned ID);
113
114public:
115 static CSKYConstantPoolConstant *
116 Create(const Constant *C, CSKYCP::CSKYCPKind Kind, unsigned PCAdjust,
117 CSKYCP::CSKYCPModifier Modifier, bool AddCurrentAddress,
118 unsigned ID = 0);
119 static CSKYConstantPoolConstant *
120 Create(const Constant *C, Type *Ty, CSKYCP::CSKYCPKind Kind,
121 unsigned PCAdjust, CSKYCP::CSKYCPModifier Modifier,
122 bool AddCurrentAddress, unsigned ID = 0);
123 const GlobalValue *getGV() const;
124 const BlockAddress *getBlockAddress() const;
125 const Constant *getConstantPool() const;
126
127 int getExistingMachineCPValue(MachineConstantPool *CP,
128 Align Alignment) override;
129 void addSelectionDAGCSEId(FoldingSetNodeID &ID) override;
130 void print(raw_ostream &O) const override;
131
132 bool equals(const CSKYConstantPoolConstant *A) const {
133 return CVal == A->CVal && CSKYConstantPoolValue::equals(A);
134 }
135
136 static bool classof(const CSKYConstantPoolValue *APV) {
137 return APV->isGlobalValue() || APV->isBlockAddress() || APV->isConstPool();
138 }
139};
140
141/// CSKYConstantPoolSymbol - CSKY-specific constantpool values for external
142/// symbols.
143class CSKYConstantPoolSymbol : public CSKYConstantPoolValue {
144 const std::string S; // ExtSymbol being loaded.
145
146 CSKYConstantPoolSymbol(Type *Ty, const char *S, unsigned PCAdjust,
147 CSKYCP::CSKYCPModifier Modifier,
148 bool AddCurrentAddress);
149
150public:
151 static CSKYConstantPoolSymbol *Create(Type *Ty, const char *S,
152 unsigned PCAdjust,
153 CSKYCP::CSKYCPModifier Modifier);
154
155 StringRef getSymbol() const { return S; }
156
157 int getExistingMachineCPValue(MachineConstantPool *CP,
158 Align Alignment) override;
159 void addSelectionDAGCSEId(FoldingSetNodeID &ID) override;
160 void print(raw_ostream &O) const override;
161
162 bool equals(const CSKYConstantPoolSymbol *A) const {
163 return S == A->S && CSKYConstantPoolValue::equals(A);
164 }
165
166 static bool classof(const CSKYConstantPoolValue *ACPV) {
167 return ACPV->isExtSymbol();
168 }
169};
170
171/// CSKYConstantPoolMBB - CSKY-specific constantpool value of a machine basic
172/// block.
173class CSKYConstantPoolMBB : public CSKYConstantPoolValue {
174 const MachineBasicBlock *MBB; // Machine basic block.
175
176 CSKYConstantPoolMBB(Type *Ty, const MachineBasicBlock *Mbb, unsigned PCAdjust,
177 CSKYCP::CSKYCPModifier Modifier, bool AddCurrentAddress);
178
179public:
180 static CSKYConstantPoolMBB *Create(Type *Ty, const MachineBasicBlock *Mbb,
181 unsigned PCAdjust);
182
183 const MachineBasicBlock *getMBB() const { return MBB; }
184
185 int getExistingMachineCPValue(MachineConstantPool *CP,
186 Align Alignment) override;
187 void addSelectionDAGCSEId(FoldingSetNodeID &ID) override;
188 void print(raw_ostream &O) const override;
189
190 bool equals(const CSKYConstantPoolMBB *A) const {
191 return MBB == A->MBB && CSKYConstantPoolValue::equals(A);
192 }
193
194 static bool classof(const CSKYConstantPoolValue *ACPV) {
195 return ACPV->isMachineBasicBlock();
196 }
197};
198
199/// CSKY-specific constantpool value of a jump table.
200class CSKYConstantPoolJT : public CSKYConstantPoolValue {
201 signed JTI; // Machine basic block.
202
203 CSKYConstantPoolJT(Type *Ty, int JTIndex, unsigned PCAdj,
204 CSKYCP::CSKYCPModifier Modifier, bool AddCurrentAddress);
205
206public:
207 static CSKYConstantPoolJT *Create(Type *Ty, int JTI, unsigned PCAdj,
208 CSKYCP::CSKYCPModifier Modifier);
209
210 signed getJTI() { return JTI; }
211
212 int getExistingMachineCPValue(MachineConstantPool *CP,
213 Align Alignment) override;
214 void addSelectionDAGCSEId(FoldingSetNodeID &ID) override;
215 void print(raw_ostream &O) const override;
216
217 bool equals(const CSKYConstantPoolJT *A) const {
218 return JTI == A->JTI && CSKYConstantPoolValue::equals(A);
219 }
220
221 static bool classof(const CSKYConstantPoolValue *ACPV) {
222 return ACPV->isJT();
223 }
224};
225
226} // namespace llvm
227
228#endif
229

source code of llvm/lib/Target/CSKY/CSKYConstantPoolValue.h