[llvm] 0f9d9ed - llvm-reduce: Add reduction for custom register masks
Matt Arsenault via llvm-commits
llvm-commits at lists.llvm.org
Mon Jul 18 10:41:12 PDT 2022
Author: Matt Arsenault
Date: 2022-07-18T13:41:08-04:00
New Revision: 0f9d9edd24774678491c19aa8653d8ac6c44da97
URL: https://github.com/llvm/llvm-project/commit/0f9d9edd24774678491c19aa8653d8ac6c44da97
DIFF: https://github.com/llvm/llvm-project/commit/0f9d9edd24774678491c19aa8653d8ac6c44da97.diff
LOG: llvm-reduce: Add reduction for custom register masks
I have a register allocator failure that only reproduces with IPRA
enabled, and requires the specific regmask if I want to only run the
one relevant pass. The printed custom regmask is enormous and I would
like to reduce it.
This reduces each individual bit in the mask, but it would probably be
better to start at register units and clear all aliasing fields at a
time. This would require stricter verification that all aliasing bits
are set in regmasks (although I would prefer to switch regmasks to use
register units in the first place).
Added:
llvm/test/tools/llvm-reduce/mir/reduce-register-masks.mir
llvm/tools/llvm-reduce/deltas/ReduceRegisterMasks.cpp
llvm/tools/llvm-reduce/deltas/ReduceRegisterMasks.h
Modified:
llvm/tools/llvm-reduce/CMakeLists.txt
llvm/tools/llvm-reduce/DeltaManager.cpp
llvm/tools/llvm-reduce/ReducerWorkItem.cpp
Removed:
################################################################################
diff --git a/llvm/test/tools/llvm-reduce/mir/reduce-register-masks.mir b/llvm/test/tools/llvm-reduce/mir/reduce-register-masks.mir
new file mode 100644
index 0000000000000..396f07a4fe63a
--- /dev/null
+++ b/llvm/test/tools/llvm-reduce/mir/reduce-register-masks.mir
@@ -0,0 +1,23 @@
+# REQUIRES: amdgpu-registered-target
+# RUN: llvm-reduce -abort-on-invalid-reduction -simplify-mir --delta-passes=register-masks -mtriple=amdgcn-amd-amdhsa --test FileCheck --test-arg --check-prefix=CHECK-INTERESTINGNESS --test-arg %s --test-arg --input-file %s -o %t
+# RUN: FileCheck --match-full-lines --check-prefix=RESULT %s < %t
+
+# CHECK-INTERESTINGNESS: CustomRegMask
+# CHECK-INTERESTINGNESS-SAME: $vcc_lo,
+# CHECK-INTERESTINGNESS-SAME: $agpr8,
+# CHECK-INTERESTINGNESS-SAME: $sgpr99,
+# CHECK-INTERESTINGNESS-SAME: $vgpr23,
+# CHECK-INTERESTINGNESS-SAME: $vgpr48_vgpr49_vgpr50,
+
+# RESULT: $sgpr30_sgpr31 = SI_CALL %0, 0, CustomRegMask($vcc_lo,$agpr8,$sgpr99,$vgpr23,$vgpr48_vgpr49_vgpr50,$vgpr49_vgpr50_vgpr51)
+
+---
+name: func
+tracksRegLiveness: true
+body: |
+ bb.0:
+ liveins: $vgpr0, $vgpr1, $sgpr8_sgpr9
+ %0:sreg_64_xexec = COPY $sgpr8_sgpr9
+ $sgpr30_sgpr31 = SI_CALL %0:sreg_64_xexec, 0, CustomRegMask($vgpr8_vgpr9, $vgpr9_vgpr10_vgpr11,$vcc_lo,$agpr8,$sgpr99,$vgpr23,$vgpr48_vgpr49_vgpr50,$vgpr49_vgpr50_vgpr51, $vgpr52_vgpr53_vgpr54,$vcc_hi,$sgpr0_sgpr1_sgpr2_sgpr3,$sgpr4_sgpr5_sgpr6_sgpr7)
+ S_ENDPGM 0
+...
diff --git a/llvm/tools/llvm-reduce/CMakeLists.txt b/llvm/tools/llvm-reduce/CMakeLists.txt
index b1911f9c407b2..b28c54a851dc3 100644
--- a/llvm/tools/llvm-reduce/CMakeLists.txt
+++ b/llvm/tools/llvm-reduce/CMakeLists.txt
@@ -45,6 +45,7 @@ add_llvm_tool(llvm-reduce
deltas/ReduceInstructionFlagsMIR.cpp
deltas/ReduceIRReferences.cpp
deltas/ReduceVirtualRegisters.cpp
+ deltas/ReduceRegisterMasks.cpp
deltas/ReduceRegisterUses.cpp
deltas/SimplifyInstructions.cpp
llvm-reduce.cpp
diff --git a/llvm/tools/llvm-reduce/DeltaManager.cpp b/llvm/tools/llvm-reduce/DeltaManager.cpp
index 98fd818bb0459..f0fae0c658db1 100644
--- a/llvm/tools/llvm-reduce/DeltaManager.cpp
+++ b/llvm/tools/llvm-reduce/DeltaManager.cpp
@@ -35,6 +35,7 @@
#include "deltas/ReduceOperands.h"
#include "deltas/ReduceOperandsSkip.h"
#include "deltas/ReduceOperandsToArgs.h"
+#include "deltas/ReduceRegisterMasks.h"
#include "deltas/ReduceRegisterUses.h"
#include "deltas/ReduceSpecialGlobals.h"
#include "deltas/ReduceVirtualRegisters.h"
@@ -85,6 +86,7 @@ static cl::opt<std::string>
DELTA_PASS("instruction-flags", reduceInstructionFlagsMIRDeltaPass) \
DELTA_PASS("register-uses", reduceRegisterUsesMIRDeltaPass) \
DELTA_PASS("register-hints", reduceVirtualRegisterHintsDeltaPass) \
+ DELTA_PASS("register-masks", reduceRegisterMasksMIRDeltaPass) \
} while (false)
static void runAllDeltaPasses(TestRunner &Tester) {
diff --git a/llvm/tools/llvm-reduce/ReducerWorkItem.cpp b/llvm/tools/llvm-reduce/ReducerWorkItem.cpp
index 891553497b9bb..b6e78dd97e768 100644
--- a/llvm/tools/llvm-reduce/ReducerWorkItem.cpp
+++ b/llvm/tools/llvm-reduce/ReducerWorkItem.cpp
@@ -291,6 +291,12 @@ static std::unique_ptr<MachineFunction> cloneMF(MachineFunction *SrcMF,
}
}
+ DenseSet<const uint32_t *> ConstRegisterMasks;
+
+ // Track predefined/named regmasks which we ignore.
+ for (const uint32_t *Mask : TRI->getRegMasks())
+ ConstRegisterMasks.insert(Mask);
+
// Clone instructions.
for (auto &SrcMBB : *SrcMF) {
auto *DstMBB = Src2DstMBB[&SrcMBB];
@@ -309,9 +315,18 @@ static std::unique_ptr<MachineFunction> cloneMF(MachineFunction *SrcMF,
// Update MBB.
if (DstMO.isMBB())
DstMO.setMBB(Src2DstMBB[DstMO.getMBB()]);
- else if (DstMO.isRegMask())
+ else if (DstMO.isRegMask()) {
DstMRI->addPhysRegsUsedFromRegMask(DstMO.getRegMask());
+ if (!ConstRegisterMasks.count(DstMO.getRegMask())) {
+ uint32_t *DstMask = DstMF->allocateRegMask();
+ std::memcpy(DstMask, SrcMO.getRegMask(),
+ sizeof(*DstMask) *
+ MachineOperand::getRegMaskSize(TRI->getNumRegs()));
+ DstMO.setRegMask(DstMask);
+ }
+ }
+
DstMI->addOperand(DstMO);
}
diff --git a/llvm/tools/llvm-reduce/deltas/ReduceRegisterMasks.cpp b/llvm/tools/llvm-reduce/deltas/ReduceRegisterMasks.cpp
new file mode 100644
index 0000000000000..5cf145aa1a4a9
--- /dev/null
+++ b/llvm/tools/llvm-reduce/deltas/ReduceRegisterMasks.cpp
@@ -0,0 +1,73 @@
+//===- ReduceRegisterMasks.cpp - Specialized Delta Pass -------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+//
+// This file implements a function which calls the Generic Delta pass in order
+// to reduce custom register masks from the MachineFunction.
+//
+//===----------------------------------------------------------------------===//
+
+#include "ReduceRegisterMasks.h"
+#include "llvm/CodeGen/MachineFunction.h"
+#include "llvm/CodeGen/MachineRegisterInfo.h"
+
+using namespace llvm;
+
+static void reduceMasksInFunction(Oracle &O, MachineFunction &MF) {
+ DenseSet<const uint32_t *> ConstRegisterMasks;
+ const auto *TRI = MF.getSubtarget().getRegisterInfo();
+
+ // Track predefined/named regmasks which we ignore.
+ const unsigned NumRegs = TRI->getNumRegs();
+ for (const uint32_t *Mask : TRI->getRegMasks())
+ ConstRegisterMasks.insert(Mask);
+
+ for (MachineBasicBlock &MBB : MF) {
+ for (MachineInstr &MI : MBB) {
+ for (MachineOperand &MO : MI.operands()) {
+ if (!MO.isRegMask())
+ continue;
+
+ const uint32_t *OldRegMask = MO.getRegMask();
+ // We're only reducing custom reg masks.
+ if (ConstRegisterMasks.count(OldRegMask))
+ continue;
+ unsigned RegMaskSize =
+ MachineOperand::getRegMaskSize(TRI->getNumRegs());
+ std::vector<uint32_t> NewMask(RegMaskSize);
+
+ bool MadeChange = false;
+ for (unsigned I = 0; I != NumRegs; ++I) {
+ if (OldRegMask[I / 32] >> I % 32) {
+ if (O.shouldKeep())
+ NewMask[I / 32] |= 1u << (I % 32);
+ } else
+ MadeChange = true;
+ }
+
+ if (MadeChange) {
+ uint32_t *UpdatedMask = MF.allocateRegMask();
+ std::memcpy(UpdatedMask, NewMask.data(),
+ RegMaskSize * sizeof(*OldRegMask));
+ MO.setRegMask(UpdatedMask);
+ }
+ }
+ }
+ }
+}
+
+static void reduceMasksInModule(Oracle &O, ReducerWorkItem &WorkItem) {
+ for (const Function &F : WorkItem.getModule()) {
+ if (auto *MF = WorkItem.MMI->getMachineFunction(F))
+ reduceMasksInFunction(O, *MF);
+ }
+}
+
+void llvm::reduceRegisterMasksMIRDeltaPass(TestRunner &Test) {
+ outs() << "*** Reducing register masks...\n";
+ runDeltaPass(Test, reduceMasksInModule);
+}
diff --git a/llvm/tools/llvm-reduce/deltas/ReduceRegisterMasks.h b/llvm/tools/llvm-reduce/deltas/ReduceRegisterMasks.h
new file mode 100644
index 0000000000000..b8bb109e5c996
--- /dev/null
+++ b/llvm/tools/llvm-reduce/deltas/ReduceRegisterMasks.h
@@ -0,0 +1,18 @@
+//===- ReduceRegisterMasks.h - Specialized Delta Pass ----------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_TOOLS_LLVM_REDUCE_DELTAS_REDUCEREGISTERMASKS_H
+#define LLVM_TOOLS_LLVM_REDUCE_DELTAS_REDUCEREGISTERMASKS_H
+
+#include "Delta.h"
+
+namespace llvm {
+void reduceRegisterMasksMIRDeltaPass(TestRunner &Test);
+} // namespace llvm
+
+#endif
More information about the llvm-commits
mailing list