File indexing completed on 2026-05-10 08:43:29
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014 #ifndef LLVM_CODEGEN_LIVEREGUNITS_H
0015 #define LLVM_CODEGEN_LIVEREGUNITS_H
0016
0017 #include "llvm/ADT/BitVector.h"
0018 #include "llvm/CodeGen/MachineInstrBundle.h"
0019 #include "llvm/CodeGen/TargetRegisterInfo.h"
0020 #include "llvm/MC/LaneBitmask.h"
0021 #include "llvm/MC/MCRegisterInfo.h"
0022 #include <cstdint>
0023
0024 namespace llvm {
0025
0026 class MachineInstr;
0027 class MachineBasicBlock;
0028
0029
0030 class LiveRegUnits {
0031 const TargetRegisterInfo *TRI = nullptr;
0032 BitVector Units;
0033
0034 public:
0035
0036 LiveRegUnits() = default;
0037
0038
0039 LiveRegUnits(const TargetRegisterInfo &TRI) {
0040 init(TRI);
0041 }
0042
0043
0044
0045
0046
0047 static void accumulateUsedDefed(const MachineInstr &MI,
0048 LiveRegUnits &ModifiedRegUnits,
0049 LiveRegUnits &UsedRegUnits,
0050 const TargetRegisterInfo *TRI) {
0051 for (ConstMIBundleOperands O(MI); O.isValid(); ++O) {
0052 if (O->isRegMask())
0053 ModifiedRegUnits.addRegsInMask(O->getRegMask());
0054 if (!O->isReg())
0055 continue;
0056 Register Reg = O->getReg();
0057 if (!Reg.isPhysical())
0058 continue;
0059 if (O->isDef()) {
0060
0061
0062
0063 if (!TRI->isConstantPhysReg(Reg))
0064 ModifiedRegUnits.addReg(Reg);
0065 } else {
0066 assert(O->isUse() && "Reg operand not a def and not a use");
0067 UsedRegUnits.addReg(Reg);
0068 }
0069 }
0070 }
0071
0072
0073 void init(const TargetRegisterInfo &TRI) {
0074 this->TRI = &TRI;
0075 Units.reset();
0076 Units.resize(TRI.getNumRegUnits());
0077 }
0078
0079
0080 void clear() { Units.reset(); }
0081
0082
0083 bool empty() const { return Units.none(); }
0084
0085
0086 void addReg(MCPhysReg Reg) {
0087 for (MCRegUnit Unit : TRI->regunits(Reg))
0088 Units.set(Unit);
0089 }
0090
0091
0092
0093 void addRegMasked(MCPhysReg Reg, LaneBitmask Mask) {
0094 for (MCRegUnitMaskIterator Unit(Reg, TRI); Unit.isValid(); ++Unit) {
0095 LaneBitmask UnitMask = (*Unit).second;
0096 if ((UnitMask & Mask).any())
0097 Units.set((*Unit).first);
0098 }
0099 }
0100
0101
0102 void removeReg(MCPhysReg Reg) {
0103 for (MCRegUnit Unit : TRI->regunits(Reg))
0104 Units.reset(Unit);
0105 }
0106
0107
0108
0109 void removeRegsNotPreserved(const uint32_t *RegMask);
0110
0111
0112
0113 void addRegsInMask(const uint32_t *RegMask);
0114
0115
0116 bool available(MCPhysReg Reg) const {
0117 for (MCRegUnit Unit : TRI->regunits(Reg)) {
0118 if (Units.test(Unit))
0119 return false;
0120 }
0121 return true;
0122 }
0123
0124
0125
0126
0127 void stepBackward(const MachineInstr &MI);
0128
0129
0130
0131
0132 void accumulate(const MachineInstr &MI);
0133
0134
0135
0136
0137
0138 void addLiveOuts(const MachineBasicBlock &MBB);
0139
0140
0141 void addLiveIns(const MachineBasicBlock &MBB);
0142
0143
0144 void addUnits(const BitVector &RegUnits) {
0145 Units |= RegUnits;
0146 }
0147
0148 void removeUnits(const BitVector &RegUnits) {
0149 Units.reset(RegUnits);
0150 }
0151
0152 const BitVector &getBitVector() const {
0153 return Units;
0154 }
0155
0156 private:
0157
0158
0159 void addPristines(const MachineFunction &MF);
0160 };
0161
0162
0163
0164 inline iterator_range<
0165 filter_iterator<ConstMIBundleOperands, bool (*)(const MachineOperand &)>>
0166 phys_regs_and_masks(const MachineInstr &MI) {
0167 auto Pred = [](const MachineOperand &MOP) {
0168 return MOP.isRegMask() ||
0169 (MOP.isReg() && !MOP.isDebug() && MOP.getReg().isPhysical());
0170 };
0171 return make_filter_range(const_mi_bundle_ops(MI),
0172 static_cast<bool (*)(const MachineOperand &)>(Pred));
0173 }
0174
0175 }
0176
0177 #endif