MachineOperand.h revision 31e2c7b4c13c2f31774614b1124533628958d0cd
1//===-- llvm/CodeGen/MachineOperand.h - MachineOperand class ----*- C++ -*-===// 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 contains the declaration of the MachineOperand class. 11// 12//===----------------------------------------------------------------------===// 13 14#ifndef LLVM_CODEGEN_MACHINEOPERAND_H 15#define LLVM_CODEGEN_MACHINEOPERAND_H 16 17#include "llvm/Support/DataTypes.h" 18#include <cassert> 19 20namespace llvm { 21 22class ConstantFP; 23class MachineBasicBlock; 24class GlobalValue; 25class MDNode; 26class MachineInstr; 27class TargetMachine; 28class MachineRegisterInfo; 29class raw_ostream; 30 31/// MachineOperand class - Representation of each machine instruction operand. 32/// 33class MachineOperand { 34public: 35 enum MachineOperandType { 36 MO_Register, ///< Register operand. 37 MO_Immediate, ///< Immediate operand 38 MO_FPImmediate, ///< Floating-point immediate operand 39 MO_MachineBasicBlock, ///< MachineBasicBlock reference 40 MO_FrameIndex, ///< Abstract Stack Frame Index 41 MO_ConstantPoolIndex, ///< Address of indexed Constant in Constant Pool 42 MO_JumpTableIndex, ///< Address of indexed Jump Table for switch 43 MO_ExternalSymbol, ///< Name of external global symbol 44 MO_GlobalAddress, ///< Address of a global value 45 MO_Metadata ///< Metadata info 46 }; 47 48private: 49 /// OpKind - Specify what kind of operand this is. This discriminates the 50 /// union. 51 unsigned char OpKind; // MachineOperandType 52 53 /// SubReg - Subregister number, only valid for MO_Register. A value of 0 54 /// indicates the MO_Register has no subReg. 55 unsigned char SubReg; 56 57 /// TargetFlags - This is a set of target-specific operand flags. 58 unsigned char TargetFlags; 59 60 /// IsDef/IsImp/IsKill/IsDead flags - These are only valid for MO_Register 61 /// operands. 62 63 /// IsDef - True if this is a def, false if this is a use of the register. 64 /// 65 bool IsDef : 1; 66 67 /// IsImp - True if this is an implicit def or use, false if it is explicit. 68 /// 69 bool IsImp : 1; 70 71 /// IsKill - True if this instruction is the last use of the register on this 72 /// path through the function. This is only valid on uses of registers. 73 bool IsKill : 1; 74 75 /// IsDead - True if this register is never used by a subsequent instruction. 76 /// This is only valid on definitions of registers. 77 bool IsDead : 1; 78 79 /// IsUndef - True if this is a register def / use of "undef", i.e. register 80 /// defined by an IMPLICIT_DEF. This is only valid on registers. 81 bool IsUndef : 1; 82 83 /// IsEarlyClobber - True if this MO_Register 'def' operand is written to 84 /// by the MachineInstr before all input registers are read. This is used to 85 /// model the GCC inline asm '&' constraint modifier. 86 bool IsEarlyClobber : 1; 87 88 /// ParentMI - This is the instruction that this operand is embedded into. 89 /// This is valid for all operand types, when the operand is in an instr. 90 MachineInstr *ParentMI; 91 92 /// Contents union - This contains the payload for the various operand types. 93 union { 94 MachineBasicBlock *MBB; // For MO_MachineBasicBlock. 95 const ConstantFP *CFP; // For MO_FPImmediate. 96 int64_t ImmVal; // For MO_Immediate. 97 98 struct { // For MO_Register. 99 unsigned RegNo; 100 MachineOperand **Prev; // Access list for register. 101 MachineOperand *Next; 102 } Reg; 103 104 /// OffsetedInfo - This struct contains the offset and an object identifier. 105 /// this represent the object as with an optional offset from it. 106 struct { 107 union { 108 int Index; // For MO_*Index - The index itself. 109 const char *SymbolName; // For MO_ExternalSymbol. 110 GlobalValue *GV; // For MO_GlobalAddress. 111 MDNode *Node; // For MO_Metadata. 112 } Val; 113 int64_t Offset; // An offset from the object. 114 } OffsetedInfo; 115 } Contents; 116 117 explicit MachineOperand(MachineOperandType K) : OpKind(K), ParentMI(0) { 118 TargetFlags = 0; 119 } 120public: 121 /// getType - Returns the MachineOperandType for this operand. 122 /// 123 MachineOperandType getType() const { return (MachineOperandType)OpKind; } 124 125 unsigned char getTargetFlags() const { return TargetFlags; } 126 void setTargetFlags(unsigned char F) { TargetFlags = F; } 127 void addTargetFlag(unsigned char F) { TargetFlags |= F; } 128 129 130 /// getParent - Return the instruction that this operand belongs to. 131 /// 132 MachineInstr *getParent() { return ParentMI; } 133 const MachineInstr *getParent() const { return ParentMI; } 134 135 void print(raw_ostream &os, const TargetMachine *TM = 0) const; 136 137 //===--------------------------------------------------------------------===// 138 // Accessors that tell you what kind of MachineOperand you're looking at. 139 //===--------------------------------------------------------------------===// 140 141 /// isReg - Tests if this is a MO_Register operand. 142 bool isReg() const { return OpKind == MO_Register; } 143 /// isImm - Tests if this is a MO_Immediate operand. 144 bool isImm() const { return OpKind == MO_Immediate; } 145 /// isFPImm - Tests if this is a MO_FPImmediate operand. 146 bool isFPImm() const { return OpKind == MO_FPImmediate; } 147 /// isMBB - Tests if this is a MO_MachineBasicBlock operand. 148 bool isMBB() const { return OpKind == MO_MachineBasicBlock; } 149 /// isFI - Tests if this is a MO_FrameIndex operand. 150 bool isFI() const { return OpKind == MO_FrameIndex; } 151 /// isCPI - Tests if this is a MO_ConstantPoolIndex operand. 152 bool isCPI() const { return OpKind == MO_ConstantPoolIndex; } 153 /// isJTI - Tests if this is a MO_JumpTableIndex operand. 154 bool isJTI() const { return OpKind == MO_JumpTableIndex; } 155 /// isGlobal - Tests if this is a MO_GlobalAddress operand. 156 bool isGlobal() const { return OpKind == MO_GlobalAddress; } 157 /// isSymbol - Tests if this is a MO_ExternalSymbol operand. 158 bool isSymbol() const { return OpKind == MO_ExternalSymbol; } 159 /// isMetadata - Tests if this is a MO_Metadata operand. 160 bool isMetadata() const { return OpKind == MO_Metadata; } 161 162 //===--------------------------------------------------------------------===// 163 // Accessors for Register Operands 164 //===--------------------------------------------------------------------===// 165 166 /// getReg - Returns the register number. 167 unsigned getReg() const { 168 assert(isReg() && "This is not a register operand!"); 169 return Contents.Reg.RegNo; 170 } 171 172 unsigned getSubReg() const { 173 assert(isReg() && "Wrong MachineOperand accessor"); 174 return (unsigned)SubReg; 175 } 176 177 bool isUse() const { 178 assert(isReg() && "Wrong MachineOperand accessor"); 179 return !IsDef; 180 } 181 182 bool isDef() const { 183 assert(isReg() && "Wrong MachineOperand accessor"); 184 return IsDef; 185 } 186 187 bool isImplicit() const { 188 assert(isReg() && "Wrong MachineOperand accessor"); 189 return IsImp; 190 } 191 192 bool isDead() const { 193 assert(isReg() && "Wrong MachineOperand accessor"); 194 return IsDead; 195 } 196 197 bool isKill() const { 198 assert(isReg() && "Wrong MachineOperand accessor"); 199 return IsKill; 200 } 201 202 bool isUndef() const { 203 assert(isReg() && "Wrong MachineOperand accessor"); 204 return IsUndef; 205 } 206 207 bool isEarlyClobber() const { 208 assert(isReg() && "Wrong MachineOperand accessor"); 209 return IsEarlyClobber; 210 } 211 212 /// getNextOperandForReg - Return the next MachineOperand in the function that 213 /// uses or defines this register. 214 MachineOperand *getNextOperandForReg() const { 215 assert(isReg() && "This is not a register operand!"); 216 return Contents.Reg.Next; 217 } 218 219 //===--------------------------------------------------------------------===// 220 // Mutators for Register Operands 221 //===--------------------------------------------------------------------===// 222 223 /// Change the register this operand corresponds to. 224 /// 225 void setReg(unsigned Reg); 226 227 void setSubReg(unsigned subReg) { 228 assert(isReg() && "Wrong MachineOperand accessor"); 229 SubReg = (unsigned char)subReg; 230 } 231 232 void setIsUse(bool Val = true) { 233 assert(isReg() && "Wrong MachineOperand accessor"); 234 IsDef = !Val; 235 } 236 237 void setIsDef(bool Val = true) { 238 assert(isReg() && "Wrong MachineOperand accessor"); 239 IsDef = Val; 240 } 241 242 void setImplicit(bool Val = true) { 243 assert(isReg() && "Wrong MachineOperand accessor"); 244 IsImp = Val; 245 } 246 247 void setIsKill(bool Val = true) { 248 assert(isReg() && !IsDef && "Wrong MachineOperand accessor"); 249 IsKill = Val; 250 } 251 252 void setIsDead(bool Val = true) { 253 assert(isReg() && IsDef && "Wrong MachineOperand accessor"); 254 IsDead = Val; 255 } 256 257 void setIsUndef(bool Val = true) { 258 assert(isReg() && "Wrong MachineOperand accessor"); 259 IsUndef = Val; 260 } 261 262 void setIsEarlyClobber(bool Val = true) { 263 assert(isReg() && IsDef && "Wrong MachineOperand accessor"); 264 IsEarlyClobber = Val; 265 } 266 267 //===--------------------------------------------------------------------===// 268 // Accessors for various operand types. 269 //===--------------------------------------------------------------------===// 270 271 int64_t getImm() const { 272 assert(isImm() && "Wrong MachineOperand accessor"); 273 return Contents.ImmVal; 274 } 275 276 const ConstantFP *getFPImm() const { 277 assert(isFPImm() && "Wrong MachineOperand accessor"); 278 return Contents.CFP; 279 } 280 281 MachineBasicBlock *getMBB() const { 282 assert(isMBB() && "Wrong MachineOperand accessor"); 283 return Contents.MBB; 284 } 285 286 int getIndex() const { 287 assert((isFI() || isCPI() || isJTI()) && 288 "Wrong MachineOperand accessor"); 289 return Contents.OffsetedInfo.Val.Index; 290 } 291 292 GlobalValue *getGlobal() const { 293 assert(isGlobal() && "Wrong MachineOperand accessor"); 294 return Contents.OffsetedInfo.Val.GV; 295 } 296 297 MDNode *getMDNode() const { 298 return Contents.OffsetedInfo.Val.Node; 299 } 300 301 int64_t getOffset() const { 302 assert((isGlobal() || isSymbol() || isCPI()) && 303 "Wrong MachineOperand accessor"); 304 return Contents.OffsetedInfo.Offset; 305 } 306 307 const char *getSymbolName() const { 308 assert(isSymbol() && "Wrong MachineOperand accessor"); 309 return Contents.OffsetedInfo.Val.SymbolName; 310 } 311 312 //===--------------------------------------------------------------------===// 313 // Mutators for various operand types. 314 //===--------------------------------------------------------------------===// 315 316 void setImm(int64_t immVal) { 317 assert(isImm() && "Wrong MachineOperand mutator"); 318 Contents.ImmVal = immVal; 319 } 320 321 void setOffset(int64_t Offset) { 322 assert((isGlobal() || isSymbol() || isCPI() || isMetadata()) && 323 "Wrong MachineOperand accessor"); 324 Contents.OffsetedInfo.Offset = Offset; 325 } 326 327 void setIndex(int Idx) { 328 assert((isFI() || isCPI() || isJTI()) && 329 "Wrong MachineOperand accessor"); 330 Contents.OffsetedInfo.Val.Index = Idx; 331 } 332 333 void setMBB(MachineBasicBlock *MBB) { 334 assert(isMBB() && "Wrong MachineOperand accessor"); 335 Contents.MBB = MBB; 336 } 337 338 //===--------------------------------------------------------------------===// 339 // Other methods. 340 //===--------------------------------------------------------------------===// 341 342 /// isIdenticalTo - Return true if this operand is identical to the specified 343 /// operand. Note: This method ignores isKill and isDead properties. 344 bool isIdenticalTo(const MachineOperand &Other) const; 345 346 /// ChangeToImmediate - Replace this operand with a new immediate operand of 347 /// the specified value. If an operand is known to be an immediate already, 348 /// the setImm method should be used. 349 void ChangeToImmediate(int64_t ImmVal); 350 351 /// ChangeToRegister - Replace this operand with a new register operand of 352 /// the specified value. If an operand is known to be an register already, 353 /// the setReg method should be used. 354 void ChangeToRegister(unsigned Reg, bool isDef, bool isImp = false, 355 bool isKill = false, bool isDead = false, 356 bool isUndef = false); 357 358 //===--------------------------------------------------------------------===// 359 // Construction methods. 360 //===--------------------------------------------------------------------===// 361 362 static MachineOperand CreateImm(int64_t Val) { 363 MachineOperand Op(MachineOperand::MO_Immediate); 364 Op.setImm(Val); 365 return Op; 366 } 367 368 static MachineOperand CreateFPImm(const ConstantFP *CFP) { 369 MachineOperand Op(MachineOperand::MO_FPImmediate); 370 Op.Contents.CFP = CFP; 371 return Op; 372 } 373 374 static MachineOperand CreateReg(unsigned Reg, bool isDef, bool isImp = false, 375 bool isKill = false, bool isDead = false, 376 bool isUndef = false, 377 bool isEarlyClobber = false, 378 unsigned SubReg = 0) { 379 MachineOperand Op(MachineOperand::MO_Register); 380 Op.IsDef = isDef; 381 Op.IsImp = isImp; 382 Op.IsKill = isKill; 383 Op.IsDead = isDead; 384 Op.IsUndef = isUndef; 385 Op.IsEarlyClobber = isEarlyClobber; 386 Op.Contents.Reg.RegNo = Reg; 387 Op.Contents.Reg.Prev = 0; 388 Op.Contents.Reg.Next = 0; 389 Op.SubReg = SubReg; 390 return Op; 391 } 392 static MachineOperand CreateMBB(MachineBasicBlock *MBB, 393 unsigned char TargetFlags = 0) { 394 MachineOperand Op(MachineOperand::MO_MachineBasicBlock); 395 Op.setMBB(MBB); 396 Op.setTargetFlags(TargetFlags); 397 return Op; 398 } 399 static MachineOperand CreateFI(unsigned Idx) { 400 MachineOperand Op(MachineOperand::MO_FrameIndex); 401 Op.setIndex(Idx); 402 return Op; 403 } 404 static MachineOperand CreateCPI(unsigned Idx, int Offset, 405 unsigned char TargetFlags = 0) { 406 MachineOperand Op(MachineOperand::MO_ConstantPoolIndex); 407 Op.setIndex(Idx); 408 Op.setOffset(Offset); 409 Op.setTargetFlags(TargetFlags); 410 return Op; 411 } 412 static MachineOperand CreateJTI(unsigned Idx, 413 unsigned char TargetFlags = 0) { 414 MachineOperand Op(MachineOperand::MO_JumpTableIndex); 415 Op.setIndex(Idx); 416 Op.setTargetFlags(TargetFlags); 417 return Op; 418 } 419 static MachineOperand CreateGA(GlobalValue *GV, int64_t Offset, 420 unsigned char TargetFlags = 0) { 421 MachineOperand Op(MachineOperand::MO_GlobalAddress); 422 Op.Contents.OffsetedInfo.Val.GV = GV; 423 Op.setOffset(Offset); 424 Op.setTargetFlags(TargetFlags); 425 return Op; 426 } 427 static MachineOperand CreateMDNode(MDNode *N, int64_t Offset, 428 unsigned char TargetFlags = 0) { 429 MachineOperand Op(MachineOperand::MO_Metadata); 430 Op.Contents.OffsetedInfo.Val.Node = N; 431 Op.setOffset(Offset); 432 Op.setTargetFlags(TargetFlags); 433 return Op; 434 } 435 static MachineOperand CreateES(const char *SymName, 436 unsigned char TargetFlags = 0) { 437 MachineOperand Op(MachineOperand::MO_ExternalSymbol); 438 Op.Contents.OffsetedInfo.Val.SymbolName = SymName; 439 Op.setOffset(0); // Offset is always 0. 440 Op.setTargetFlags(TargetFlags); 441 return Op; 442 } 443 444 friend class MachineInstr; 445 friend class MachineRegisterInfo; 446private: 447 //===--------------------------------------------------------------------===// 448 // Methods for handling register use/def lists. 449 //===--------------------------------------------------------------------===// 450 451 /// isOnRegUseList - Return true if this operand is on a register use/def list 452 /// or false if not. This can only be called for register operands that are 453 /// part of a machine instruction. 454 bool isOnRegUseList() const { 455 assert(isReg() && "Can only add reg operand to use lists"); 456 return Contents.Reg.Prev != 0; 457 } 458 459 /// AddRegOperandToRegInfo - Add this register operand to the specified 460 /// MachineRegisterInfo. If it is null, then the next/prev fields should be 461 /// explicitly nulled out. 462 void AddRegOperandToRegInfo(MachineRegisterInfo *RegInfo); 463 464 /// RemoveRegOperandFromRegInfo - Remove this register operand from the 465 /// MachineRegisterInfo it is linked with. 466 void RemoveRegOperandFromRegInfo(); 467}; 468 469inline raw_ostream &operator<<(raw_ostream &OS, const MachineOperand& MO) { 470 MO.print(OS, 0); 471 return OS; 472} 473 474} // End llvm namespace 475 476#endif 477