Path: blob/main/contrib/llvm-project/llvm/lib/Target/ARM/ARMConstantPoolValue.h
35294 views
//===- ARMConstantPoolValue.h - ARM constantpool value ----------*- C++ -*-===//1//2// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.3// See https://llvm.org/LICENSE.txt for license information.4// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception5//6//===----------------------------------------------------------------------===//7//8// This file implements the ARM specific constantpool value class.9//10//===----------------------------------------------------------------------===//1112#ifndef LLVM_LIB_TARGET_ARM_ARMCONSTANTPOOLVALUE_H13#define LLVM_LIB_TARGET_ARM_ARMCONSTANTPOOLVALUE_H1415#include "llvm/ADT/SmallPtrSet.h"16#include "llvm/ADT/StringRef.h"17#include "llvm/ADT/iterator_range.h"18#include "llvm/CodeGen/MachineConstantPool.h"19#include "llvm/Support/Casting.h"20#include <string>21#include <vector>2223namespace llvm {2425class BlockAddress;26class Constant;27class GlobalValue;28class GlobalVariable;29class LLVMContext;30class MachineBasicBlock;31class raw_ostream;32class Type;3334namespace ARMCP {3536enum ARMCPKind {37CPValue,38CPExtSymbol,39CPBlockAddress,40CPLSDA,41CPMachineBasicBlock,42CPPromotedGlobal43};4445enum ARMCPModifier {46no_modifier, /// None47TLSGD, /// Thread Local Storage (General Dynamic Mode)48GOT_PREL, /// Global Offset Table, PC Relative49GOTTPOFF, /// Global Offset Table, Thread Pointer Offset50TPOFF, /// Thread Pointer Offset51SECREL, /// Section Relative (Windows TLS)52SBREL, /// Static Base Relative (RWPI)53};5455} // end namespace ARMCP5657/// ARMConstantPoolValue - ARM specific constantpool value. This is used to58/// represent PC-relative displacement between the address of the load59/// instruction and the constant being loaded, i.e. (&GV-(LPIC+8)).60class ARMConstantPoolValue : public MachineConstantPoolValue {61unsigned LabelId; // Label id of the load.62ARMCP::ARMCPKind Kind; // Kind of constant.63unsigned char PCAdjust; // Extra adjustment if constantpool is pc-relative.64// 8 for ARM, 4 for Thumb.65ARMCP::ARMCPModifier Modifier; // GV modifier i.e. (&GV(modifier)-(LPIC+8))66bool AddCurrentAddress;6768protected:69ARMConstantPoolValue(Type *Ty, unsigned id, ARMCP::ARMCPKind Kind,70unsigned char PCAdj, ARMCP::ARMCPModifier Modifier,71bool AddCurrentAddress);7273ARMConstantPoolValue(LLVMContext &C, unsigned id, ARMCP::ARMCPKind Kind,74unsigned char PCAdj, ARMCP::ARMCPModifier Modifier,75bool AddCurrentAddress);7677template <typename Derived>78int getExistingMachineCPValueImpl(MachineConstantPool *CP, Align Alignment) {79const std::vector<MachineConstantPoolEntry> &Constants = CP->getConstants();80for (unsigned i = 0, e = Constants.size(); i != e; ++i) {81if (Constants[i].isMachineConstantPoolEntry() &&82Constants[i].getAlign() >= Alignment) {83auto *CPV =84static_cast<ARMConstantPoolValue*>(Constants[i].Val.MachineCPVal);85if (Derived *APC = dyn_cast<Derived>(CPV))86if (cast<Derived>(this)->equals(APC))87return i;88}89}9091return -1;92}9394public:95~ARMConstantPoolValue() override;9697ARMCP::ARMCPModifier getModifier() const { return Modifier; }98StringRef getModifierText() const;99bool hasModifier() const { return Modifier != ARMCP::no_modifier; }100101bool mustAddCurrentAddress() const { return AddCurrentAddress; }102103unsigned getLabelId() const { return LabelId; }104unsigned char getPCAdjustment() const { return PCAdjust; }105106bool isGlobalValue() const { return Kind == ARMCP::CPValue; }107bool isExtSymbol() const { return Kind == ARMCP::CPExtSymbol; }108bool isBlockAddress() const { return Kind == ARMCP::CPBlockAddress; }109bool isLSDA() const { return Kind == ARMCP::CPLSDA; }110bool isMachineBasicBlock() const{ return Kind == ARMCP::CPMachineBasicBlock; }111bool isPromotedGlobal() const{ return Kind == ARMCP::CPPromotedGlobal; }112113int getExistingMachineCPValue(MachineConstantPool *CP,114Align Alignment) override;115116void addSelectionDAGCSEId(FoldingSetNodeID &ID) override;117118/// hasSameValue - Return true if this ARM constpool value can share the same119/// constantpool entry as another ARM constpool value.120virtual bool hasSameValue(ARMConstantPoolValue *ACPV);121122bool equals(const ARMConstantPoolValue *A) const {123return this->LabelId == A->LabelId &&124this->PCAdjust == A->PCAdjust &&125this->Modifier == A->Modifier;126}127128void print(raw_ostream &O) const override;129void print(raw_ostream *O) const { if (O) print(*O); }130void dump() const;131};132133inline raw_ostream &operator<<(raw_ostream &O, const ARMConstantPoolValue &V) {134V.print(O);135return O;136}137138/// ARMConstantPoolConstant - ARM-specific constant pool values for Constants,139/// Functions, and BlockAddresses.140class ARMConstantPoolConstant : public ARMConstantPoolValue {141const Constant *CVal; // Constant being loaded.142SmallPtrSet<const GlobalVariable*, 1> GVars;143144ARMConstantPoolConstant(const Constant *C,145unsigned ID,146ARMCP::ARMCPKind Kind,147unsigned char PCAdj,148ARMCP::ARMCPModifier Modifier,149bool AddCurrentAddress);150ARMConstantPoolConstant(Type *Ty, const Constant *C,151unsigned ID,152ARMCP::ARMCPKind Kind,153unsigned char PCAdj,154ARMCP::ARMCPModifier Modifier,155bool AddCurrentAddress);156ARMConstantPoolConstant(const GlobalVariable *GV, const Constant *Init);157158public:159static ARMConstantPoolConstant *Create(const Constant *C, unsigned ID);160static ARMConstantPoolConstant *Create(const GlobalValue *GV,161ARMCP::ARMCPModifier Modifier);162static ARMConstantPoolConstant *Create(const GlobalVariable *GV,163const Constant *Initializer);164static ARMConstantPoolConstant *Create(const Constant *C, unsigned ID,165ARMCP::ARMCPKind Kind,166unsigned char PCAdj);167static ARMConstantPoolConstant *Create(const Constant *C, unsigned ID,168ARMCP::ARMCPKind Kind,169unsigned char PCAdj,170ARMCP::ARMCPModifier Modifier,171bool AddCurrentAddress);172173const GlobalValue *getGV() const;174const BlockAddress *getBlockAddress() const;175176using promoted_iterator = SmallPtrSet<const GlobalVariable *, 1>::iterator;177178iterator_range<promoted_iterator> promotedGlobals() {179return iterator_range<promoted_iterator>(GVars.begin(), GVars.end());180}181182const Constant *getPromotedGlobalInit() const {183return CVal;184}185186int getExistingMachineCPValue(MachineConstantPool *CP,187Align Alignment) override;188189/// hasSameValue - Return true if this ARM constpool value can share the same190/// constantpool entry as another ARM constpool value.191bool hasSameValue(ARMConstantPoolValue *ACPV) override;192193void addSelectionDAGCSEId(FoldingSetNodeID &ID) override;194195void print(raw_ostream &O) const override;196197static bool classof(const ARMConstantPoolValue *APV) {198return APV->isGlobalValue() || APV->isBlockAddress() || APV->isLSDA() ||199APV->isPromotedGlobal();200}201202bool equals(const ARMConstantPoolConstant *A) const {203return CVal == A->CVal && ARMConstantPoolValue::equals(A);204}205};206207/// ARMConstantPoolSymbol - ARM-specific constantpool values for external208/// symbols.209class ARMConstantPoolSymbol : public ARMConstantPoolValue {210const std::string S; // ExtSymbol being loaded.211212ARMConstantPoolSymbol(LLVMContext &C, StringRef s, unsigned id,213unsigned char PCAdj, ARMCP::ARMCPModifier Modifier,214bool AddCurrentAddress);215216public:217static ARMConstantPoolSymbol *Create(LLVMContext &C, StringRef s, unsigned ID,218unsigned char PCAdj);219220StringRef getSymbol() const { return S; }221222int getExistingMachineCPValue(MachineConstantPool *CP,223Align Alignment) override;224225void addSelectionDAGCSEId(FoldingSetNodeID &ID) override;226227/// hasSameValue - Return true if this ARM constpool value can share the same228/// constantpool entry as another ARM constpool value.229bool hasSameValue(ARMConstantPoolValue *ACPV) override;230231void print(raw_ostream &O) const override;232233static bool classof(const ARMConstantPoolValue *ACPV) {234return ACPV->isExtSymbol();235}236237bool equals(const ARMConstantPoolSymbol *A) const {238return S == A->S && ARMConstantPoolValue::equals(A);239}240};241242/// ARMConstantPoolMBB - ARM-specific constantpool value of a machine basic243/// block.244class ARMConstantPoolMBB : public ARMConstantPoolValue {245const MachineBasicBlock *MBB; // Machine basic block.246247ARMConstantPoolMBB(LLVMContext &C, const MachineBasicBlock *mbb, unsigned id,248unsigned char PCAdj, ARMCP::ARMCPModifier Modifier,249bool AddCurrentAddress);250251public:252static ARMConstantPoolMBB *Create(LLVMContext &C,253const MachineBasicBlock *mbb,254unsigned ID, unsigned char PCAdj);255256const MachineBasicBlock *getMBB() const { return MBB; }257258int getExistingMachineCPValue(MachineConstantPool *CP,259Align Alignment) override;260261void addSelectionDAGCSEId(FoldingSetNodeID &ID) override;262263/// hasSameValue - Return true if this ARM constpool value can share the same264/// constantpool entry as another ARM constpool value.265bool hasSameValue(ARMConstantPoolValue *ACPV) override;266267void print(raw_ostream &O) const override;268269static bool classof(const ARMConstantPoolValue *ACPV) {270return ACPV->isMachineBasicBlock();271}272273bool equals(const ARMConstantPoolMBB *A) const {274return MBB == A->MBB && ARMConstantPoolValue::equals(A);275}276};277278} // end namespace llvm279280#endif // LLVM_LIB_TARGET_ARM_ARMCONSTANTPOOLVALUE_H281282283