[llvm] c87bf29 - [MachineVerifier][GlobalISel] Check that branches have a MBB operand or are declared indirect. Add missing properties to G_BRJT, G_BRINDIRECT

Dominik Montada via llvm-commits llvm-commits at lists.llvm.org
Mon Jun 15 02:17:20 PDT 2020


Author: Dominik Montada
Date: 2020-06-15T11:17:09+02:00
New Revision: c87bf29149598d6dd24470fe3c22dbd40f215dcb

URL: https://github.com/llvm/llvm-project/commit/c87bf29149598d6dd24470fe3c22dbd40f215dcb
DIFF: https://github.com/llvm/llvm-project/commit/c87bf29149598d6dd24470fe3c22dbd40f215dcb.diff

LOG: [MachineVerifier][GlobalISel] Check that branches have a MBB operand or are declared indirect. Add missing properties to G_BRJT, G_BRINDIRECT

Summary:
Teach MachineVerifier to check branches for MBB operands if they are not declared indirect.

Add `isBarrier`, `isIndirectBranch` to `G_BRINDIRECT` and `G_BRJT`.
Without these, `MachineInstr.isConditionalBranch()` was giving a
false-positive for those instructions.

Reviewers: aemerson, qcolombet, dsanders, arsenm

Reviewed By: dsanders

Subscribers: hiraditya, wdng, simoncook, s.egerton, arsenm, rovka, llvm-commits

Tags: #llvm

Differential Revision: https://reviews.llvm.org/D81587

Added: 
    llvm/test/MachineVerifier/test_g_brindirect_is_indirect_branch.mir
    llvm/test/MachineVerifier/test_g_brjt_is_indirect_branch.mir

Modified: 
    llvm/include/llvm/Target/GenericOpcodes.td
    llvm/lib/CodeGen/MachineVerifier.cpp
    llvm/test/CodeGen/AArch64/GlobalISel/legalize-blockaddress.mir
    llvm/test/CodeGen/AArch64/GlobalISel/select-blockaddress.mir

Removed: 
    


################################################################################
diff  --git a/llvm/include/llvm/Target/GenericOpcodes.td b/llvm/include/llvm/Target/GenericOpcodes.td
index eafcb3d96ff3..3d8262b2404f 100644
--- a/llvm/include/llvm/Target/GenericOpcodes.td
+++ b/llvm/include/llvm/Target/GenericOpcodes.td
@@ -1085,6 +1085,8 @@ def G_BRINDIRECT : GenericInstruction {
   let hasSideEffects = 0;
   let isBranch = 1;
   let isTerminator = 1;
+  let isBarrier = 1;
+  let isIndirectBranch = 1;
 }
 
 // Generic branch to jump table entry
@@ -1094,6 +1096,8 @@ def G_BRJT : GenericInstruction {
   let hasSideEffects = 0;
   let isBranch = 1;
   let isTerminator = 1;
+  let isBarrier = 1;
+  let isIndirectBranch = 1;
 }
 
 def G_READ_REGISTER : GenericInstruction {

diff  --git a/llvm/lib/CodeGen/MachineVerifier.cpp b/llvm/lib/CodeGen/MachineVerifier.cpp
index c47762617245..592954944980 100644
--- a/llvm/lib/CodeGen/MachineVerifier.cpp
+++ b/llvm/lib/CodeGen/MachineVerifier.cpp
@@ -863,6 +863,22 @@ void MachineVerifier::verifyPreISelGenericInstruction(const MachineInstr *MI) {
   const MCInstrDesc &MCID = MI->getDesc();
   unsigned NumOps = MI->getNumOperands();
 
+  // Branches must reference a basic block if they are not indirect
+  if (MI->isBranch() && !MI->isIndirectBranch()) {
+    bool HasMBB = false;
+    for (const MachineOperand &Op : MI->operands()) {
+      if (Op.isMBB()) {
+        HasMBB = true;
+        break;
+      }
+    }
+
+    if (!HasMBB)
+      report("Branch instruction is missing a basic block operand or "
+             "isIndirectBranch property",
+             MI);
+  }
+
   // Check types.
   SmallVector<LLT, 4> Types;
   for (unsigned I = 0, E = std::min(MCID.getNumOperands(), NumOps);

diff  --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-blockaddress.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-blockaddress.mir
index dba41b36d25e..a732ae923c04 100644
--- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-blockaddress.mir
+++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-blockaddress.mir
@@ -25,7 +25,6 @@ registers:
 body:             |
   ; CHECK-LABEL: name: test_blockaddress
   ; CHECK: bb.0 (%ir-block.0):
-  ; CHECK:   successors: %bb.1(0x80000000)
   ; CHECK:   [[BLOCK_ADDR:%[0-9]+]]:_(p0) = G_BLOCK_ADDR blockaddress(@test_blockaddress, %ir-block.block)
   ; CHECK:   [[ADRP:%[0-9]+]]:gpr64(p0) = ADRP target-flags(aarch64-page) @addr
   ; CHECK:   [[ADD_LOW:%[0-9]+]]:_(p0) = G_ADD_LOW [[ADRP]](p0), target-flags(aarch64-pageoff, aarch64-nc) @addr

diff  --git a/llvm/test/CodeGen/AArch64/GlobalISel/select-blockaddress.mir b/llvm/test/CodeGen/AArch64/GlobalISel/select-blockaddress.mir
index e7b414bad7b2..bd5ee80d5841 100644
--- a/llvm/test/CodeGen/AArch64/GlobalISel/select-blockaddress.mir
+++ b/llvm/test/CodeGen/AArch64/GlobalISel/select-blockaddress.mir
@@ -30,7 +30,6 @@ registers:
 body:             |
   ; CHECK-LABEL: name: test_blockaddress
   ; CHECK: bb.0 (%ir-block.0):
-  ; CHECK:   successors: %bb.1(0x80000000)
   ; CHECK:   [[MOVaddrBA:%[0-9]+]]:gpr64 = MOVaddrBA target-flags(aarch64-page) blockaddress(@test_blockaddress, %ir-block.block), target-flags(aarch64-pageoff, aarch64-nc) blockaddress(@test_blockaddress, %ir-block.block)
   ; CHECK:   [[MOVaddr:%[0-9]+]]:gpr64common = MOVaddr target-flags(aarch64-page) @addr, target-flags(aarch64-pageoff, aarch64-nc) @addr
   ; CHECK:   STRXui [[MOVaddrBA]], [[MOVaddr]], 0 :: (store 8 into @addr)
@@ -39,7 +38,6 @@ body:             |
   ; CHECK:   RET_ReallyLR
   ; LARGE-LABEL: name: test_blockaddress
   ; LARGE: bb.0 (%ir-block.0):
-  ; LARGE:   successors: %bb.1(0x80000000)
   ; LARGE:   [[MOVZXi:%[0-9]+]]:gpr64 = MOVZXi target-flags(aarch64-g0, aarch64-nc) blockaddress(@test_blockaddress, %ir-block.block), 0
   ; LARGE:   [[MOVKXi:%[0-9]+]]:gpr64 = MOVKXi [[MOVZXi]], target-flags(aarch64-g1, aarch64-nc) blockaddress(@test_blockaddress, %ir-block.block), 16
   ; LARGE:   [[MOVKXi1:%[0-9]+]]:gpr64 = MOVKXi [[MOVKXi]], target-flags(aarch64-g2, aarch64-nc) blockaddress(@test_blockaddress, %ir-block.block), 32

diff  --git a/llvm/test/MachineVerifier/test_g_brindirect_is_indirect_branch.mir b/llvm/test/MachineVerifier/test_g_brindirect_is_indirect_branch.mir
new file mode 100644
index 000000000000..9ecfad722733
--- /dev/null
+++ b/llvm/test/MachineVerifier/test_g_brindirect_is_indirect_branch.mir
@@ -0,0 +1,20 @@
+# RUN: llc -march=riscv32 -o - -run-pass=none -verify-machineinstrs %s | FileCheck %s
+# REQUIRES: global-isel, riscv-registered-target
+
+# This test checks that the G_BRINDIRECT is an indirect branch by leveraging
+# RISCV's version of analyzeBranch. If G_BRINDIRECT would not be an indirect
+# branch, this test would crash.
+
+---
+name:            test_indirect_branch
+legalized:       true
+tracksRegLiveness: true
+body:             |
+  bb.0:
+    liveins: $x0
+    %0:_(p0) = COPY $x0
+
+    ; CHECK-NOT: Branch instruction is missing a basic block operand or isIndirectBranch property
+    G_BRINDIRECT %0
+
+...

diff  --git a/llvm/test/MachineVerifier/test_g_brjt_is_indirect_branch.mir b/llvm/test/MachineVerifier/test_g_brjt_is_indirect_branch.mir
new file mode 100644
index 000000000000..4c0af7a4efec
--- /dev/null
+++ b/llvm/test/MachineVerifier/test_g_brjt_is_indirect_branch.mir
@@ -0,0 +1,26 @@
+# RUN: llc -march=riscv32 -o - -run-pass=none -verify-machineinstrs %s | FileCheck %s
+# REQUIRES: global-isel, riscv-registered-target
+
+# This test checks that the G_BRJT is an indirect branch by leveraging RISCV's
+# version of analyzeBranch. If G_BRJT would not be an indirect branch, this
+# test would crash.
+
+---
+name:            test_jump_table
+legalized:       true
+tracksRegLiveness: true
+jumpTable:
+  kind:            block-address
+  entries:
+    - id:              0
+      blocks:          [ '%bb.0' ]
+body:             |
+  bb.0:
+    liveins: $x0
+    %0:_(s32) = COPY $x0
+    %1:_(p0) = COPY $x0
+
+    ; CHECK-NOT: Branch instruction is missing a basic block operand or isIndirectBranch property
+    G_BRJT %1, %jump-table.0, %0
+
+...


        


More information about the llvm-commits mailing list