1 //===-- ARMConstantPoolValue.cpp - ARM constantpool value -----------------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This file implements the ARM specific constantpool value class. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #include "ARMConstantPoolValue.h" 15 #include "llvm/ADT/FoldingSet.h" 16 #include "llvm/CodeGen/MachineBasicBlock.h" 17 #include "llvm/IR/Constant.h" 18 #include "llvm/IR/Constants.h" 19 #include "llvm/IR/GlobalValue.h" 20 #include "llvm/IR/Type.h" 21 #include "llvm/Support/raw_ostream.h" 22 #include <cstdlib> 23 using namespace llvm; 24 25 //===----------------------------------------------------------------------===// 26 // ARMConstantPoolValue 27 //===----------------------------------------------------------------------===// 28 29 ARMConstantPoolValue::ARMConstantPoolValue(Type *Ty, unsigned id, 30 ARMCP::ARMCPKind kind, 31 unsigned char PCAdj, 32 ARMCP::ARMCPModifier modifier, 33 bool addCurrentAddress) 34 : MachineConstantPoolValue(Ty), LabelId(id), Kind(kind), 35 PCAdjust(PCAdj), Modifier(modifier), 36 AddCurrentAddress(addCurrentAddress) {} 37 38 ARMConstantPoolValue::ARMConstantPoolValue(LLVMContext &C, unsigned id, 39 ARMCP::ARMCPKind kind, 40 unsigned char PCAdj, 41 ARMCP::ARMCPModifier modifier, 42 bool addCurrentAddress) 43 : MachineConstantPoolValue((Type*)Type::getInt32Ty(C)), 44 LabelId(id), Kind(kind), PCAdjust(PCAdj), Modifier(modifier), 45 AddCurrentAddress(addCurrentAddress) {} 46 47 ARMConstantPoolValue::~ARMConstantPoolValue() {} 48 49 const char *ARMConstantPoolValue::getModifierText() const { 50 switch (Modifier) { 51 // FIXME: Are these case sensitive? It'd be nice to lower-case all the 52 // strings if that's legal. 53 case ARMCP::no_modifier: 54 return "none"; 55 case ARMCP::TLSGD: 56 return "tlsgd"; 57 case ARMCP::GOT_PREL: 58 return "GOT_PREL"; 59 case ARMCP::GOTTPOFF: 60 return "gottpoff"; 61 case ARMCP::TPOFF: 62 return "tpoff"; 63 } 64 llvm_unreachable("Unknown modifier!"); 65 } 66 67 int ARMConstantPoolValue::getExistingMachineCPValue(MachineConstantPool *CP, 68 unsigned Alignment) { 69 llvm_unreachable("Shouldn't be calling this directly!"); 70 } 71 72 void 73 ARMConstantPoolValue::addSelectionDAGCSEId(FoldingSetNodeID &ID) { 74 ID.AddInteger(LabelId); 75 ID.AddInteger(PCAdjust); 76 } 77 78 bool 79 ARMConstantPoolValue::hasSameValue(ARMConstantPoolValue *ACPV) { 80 if (ACPV->Kind == Kind && 81 ACPV->PCAdjust == PCAdjust && 82 ACPV->Modifier == Modifier && 83 ACPV->LabelId == LabelId && 84 ACPV->AddCurrentAddress == AddCurrentAddress) { 85 // Two PC relative constpool entries containing the same GV address or 86 // external symbols. FIXME: What about blockaddress? 87 if (Kind == ARMCP::CPValue || Kind == ARMCP::CPExtSymbol) 88 return true; 89 } 90 return false; 91 } 92 93 LLVM_DUMP_METHOD void ARMConstantPoolValue::dump() const { 94 errs() << " " << *this; 95 } 96 97 void ARMConstantPoolValue::print(raw_ostream &O) const { 98 if (Modifier) O << "(" << getModifierText() << ")"; 99 if (PCAdjust != 0) { 100 O << "-(LPC" << LabelId << "+" << (unsigned)PCAdjust; 101 if (AddCurrentAddress) O << "-."; 102 O << ")"; 103 } 104 } 105 106 //===----------------------------------------------------------------------===// 107 // ARMConstantPoolConstant 108 //===----------------------------------------------------------------------===// 109 110 ARMConstantPoolConstant::ARMConstantPoolConstant(Type *Ty, 111 const Constant *C, 112 unsigned ID, 113 ARMCP::ARMCPKind Kind, 114 unsigned char PCAdj, 115 ARMCP::ARMCPModifier Modifier, 116 bool AddCurrentAddress) 117 : ARMConstantPoolValue(Ty, ID, Kind, PCAdj, Modifier, AddCurrentAddress), 118 CVal(C) {} 119 120 ARMConstantPoolConstant::ARMConstantPoolConstant(const Constant *C, 121 unsigned ID, 122 ARMCP::ARMCPKind Kind, 123 unsigned char PCAdj, 124 ARMCP::ARMCPModifier Modifier, 125 bool AddCurrentAddress) 126 : ARMConstantPoolValue((Type*)C->getType(), ID, Kind, PCAdj, Modifier, 127 AddCurrentAddress), 128 CVal(C) {} 129 130 ARMConstantPoolConstant * 131 ARMConstantPoolConstant::Create(const Constant *C, unsigned ID) { 132 return new ARMConstantPoolConstant(C, ID, ARMCP::CPValue, 0, 133 ARMCP::no_modifier, false); 134 } 135 136 ARMConstantPoolConstant * 137 ARMConstantPoolConstant::Create(const GlobalValue *GV, 138 ARMCP::ARMCPModifier Modifier) { 139 return new ARMConstantPoolConstant((Type*)Type::getInt32Ty(GV->getContext()), 140 GV, 0, ARMCP::CPValue, 0, 141 Modifier, false); 142 } 143 144 ARMConstantPoolConstant * 145 ARMConstantPoolConstant::Create(const Constant *C, unsigned ID, 146 ARMCP::ARMCPKind Kind, unsigned char PCAdj) { 147 return new ARMConstantPoolConstant(C, ID, Kind, PCAdj, 148 ARMCP::no_modifier, false); 149 } 150 151 ARMConstantPoolConstant * 152 ARMConstantPoolConstant::Create(const Constant *C, unsigned ID, 153 ARMCP::ARMCPKind Kind, unsigned char PCAdj, 154 ARMCP::ARMCPModifier Modifier, 155 bool AddCurrentAddress) { 156 return new ARMConstantPoolConstant(C, ID, Kind, PCAdj, Modifier, 157 AddCurrentAddress); 158 } 159 160 const GlobalValue *ARMConstantPoolConstant::getGV() const { 161 return dyn_cast_or_null<GlobalValue>(CVal); 162 } 163 164 const BlockAddress *ARMConstantPoolConstant::getBlockAddress() const { 165 return dyn_cast_or_null<BlockAddress>(CVal); 166 } 167 168 int ARMConstantPoolConstant::getExistingMachineCPValue(MachineConstantPool *CP, 169 unsigned Alignment) { 170 return getExistingMachineCPValueImpl<ARMConstantPoolConstant>(CP, Alignment); 171 } 172 173 bool ARMConstantPoolConstant::hasSameValue(ARMConstantPoolValue *ACPV) { 174 const ARMConstantPoolConstant *ACPC = dyn_cast<ARMConstantPoolConstant>(ACPV); 175 return ACPC && ACPC->CVal == CVal && ARMConstantPoolValue::hasSameValue(ACPV); 176 } 177 178 void ARMConstantPoolConstant::addSelectionDAGCSEId(FoldingSetNodeID &ID) { 179 ID.AddPointer(CVal); 180 ARMConstantPoolValue::addSelectionDAGCSEId(ID); 181 } 182 183 void ARMConstantPoolConstant::print(raw_ostream &O) const { 184 O << CVal->getName(); 185 ARMConstantPoolValue::print(O); 186 } 187 188 //===----------------------------------------------------------------------===// 189 // ARMConstantPoolSymbol 190 //===----------------------------------------------------------------------===// 191 192 ARMConstantPoolSymbol::ARMConstantPoolSymbol(LLVMContext &C, const char *s, 193 unsigned id, 194 unsigned char PCAdj, 195 ARMCP::ARMCPModifier Modifier, 196 bool AddCurrentAddress) 197 : ARMConstantPoolValue(C, id, ARMCP::CPExtSymbol, PCAdj, Modifier, 198 AddCurrentAddress), 199 S(s) {} 200 201 ARMConstantPoolSymbol * 202 ARMConstantPoolSymbol::Create(LLVMContext &C, const char *s, 203 unsigned ID, unsigned char PCAdj) { 204 return new ARMConstantPoolSymbol(C, s, ID, PCAdj, ARMCP::no_modifier, false); 205 } 206 207 int ARMConstantPoolSymbol::getExistingMachineCPValue(MachineConstantPool *CP, 208 unsigned Alignment) { 209 return getExistingMachineCPValueImpl<ARMConstantPoolSymbol>(CP, Alignment); 210 } 211 212 bool ARMConstantPoolSymbol::hasSameValue(ARMConstantPoolValue *ACPV) { 213 const ARMConstantPoolSymbol *ACPS = dyn_cast<ARMConstantPoolSymbol>(ACPV); 214 return ACPS && ACPS->S == S && ARMConstantPoolValue::hasSameValue(ACPV); 215 } 216 217 void ARMConstantPoolSymbol::addSelectionDAGCSEId(FoldingSetNodeID &ID) { 218 ID.AddString(S); 219 ARMConstantPoolValue::addSelectionDAGCSEId(ID); 220 } 221 222 void ARMConstantPoolSymbol::print(raw_ostream &O) const { 223 O << S; 224 ARMConstantPoolValue::print(O); 225 } 226 227 //===----------------------------------------------------------------------===// 228 // ARMConstantPoolMBB 229 //===----------------------------------------------------------------------===// 230 231 ARMConstantPoolMBB::ARMConstantPoolMBB(LLVMContext &C, 232 const MachineBasicBlock *mbb, 233 unsigned id, unsigned char PCAdj, 234 ARMCP::ARMCPModifier Modifier, 235 bool AddCurrentAddress) 236 : ARMConstantPoolValue(C, id, ARMCP::CPMachineBasicBlock, PCAdj, 237 Modifier, AddCurrentAddress), 238 MBB(mbb) {} 239 240 ARMConstantPoolMBB *ARMConstantPoolMBB::Create(LLVMContext &C, 241 const MachineBasicBlock *mbb, 242 unsigned ID, 243 unsigned char PCAdj) { 244 return new ARMConstantPoolMBB(C, mbb, ID, PCAdj, ARMCP::no_modifier, false); 245 } 246 247 int ARMConstantPoolMBB::getExistingMachineCPValue(MachineConstantPool *CP, 248 unsigned Alignment) { 249 return getExistingMachineCPValueImpl<ARMConstantPoolMBB>(CP, Alignment); 250 } 251 252 bool ARMConstantPoolMBB::hasSameValue(ARMConstantPoolValue *ACPV) { 253 const ARMConstantPoolMBB *ACPMBB = dyn_cast<ARMConstantPoolMBB>(ACPV); 254 return ACPMBB && ACPMBB->MBB == MBB && 255 ARMConstantPoolValue::hasSameValue(ACPV); 256 } 257 258 void ARMConstantPoolMBB::addSelectionDAGCSEId(FoldingSetNodeID &ID) { 259 ID.AddPointer(MBB); 260 ARMConstantPoolValue::addSelectionDAGCSEId(ID); 261 } 262 263 void ARMConstantPoolMBB::print(raw_ostream &O) const { 264 O << "BB#" << MBB->getNumber(); 265 ARMConstantPoolValue::print(O); 266 } 267