[llvm] [AMDGPU][GlobalISel] Fix register count for d16 gather4 on gfx8.1/gfx9 (PR #219891)

Arseniy Obolenskiy via llvm-commits llvm-commits at lists.llvm.org
Mon Aug 31 06:51:18 PDT 2026


https://github.com/aobolensk updated https://github.com/llvm/llvm-project/pull/219891

>From 1e1606be45ec0bc2a113c237db0e266b7546fff5 Mon Sep 17 00:00:00 2001
From: Arseniy Obolenskiy <arseniy.obolenskiy at amd.com>
Date: Mon, 31 Aug 2026 08:01:25 +0200
Subject: [PATCH 1/3] [AMDGPU][GlobalISel] Fix register count for d16 gather4
 on gfx8.1/gfx9

Match SDAG workaround for the sq block bug that miscounts registers for packed d16 gather4 results
---
 .../AMDGPU/AMDGPUInstructionSelector.cpp      |  21 +-
 .../llvm.amdgcn.image.gather4.d16.dim.ll      | 193 ++++++++++++++++++
 .../llvm.amdgcn.image.gather4.d16.tfe.dim.ll  | 105 ++++++++++
 .../llvm.amdgcn.image.gather4.d16.dim.ll      |  28 +++
 4 files changed, 340 insertions(+), 7 deletions(-)
 create mode 100644 llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll
 create mode 100644 llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll

diff --git a/llvm/lib/Target/AMDGPU/AMDGPUInstructionSelector.cpp b/llvm/lib/Target/AMDGPU/AMDGPUInstructionSelector.cpp
index 353506378b229..87df342c6ee21 100644
--- a/llvm/lib/Target/AMDGPU/AMDGPUInstructionSelector.cpp
+++ b/llvm/lib/Target/AMDGPU/AMDGPUInstructionSelector.cpp
@@ -2130,6 +2130,11 @@ bool AMDGPUInstructionSelector::selectImageIntrinsic(
   bool IsD16 = MI.getOpcode() == AMDGPU::G_AMDGPU_INTRIN_IMAGE_LOAD_D16 ||
                MI.getOpcode() == AMDGPU::G_AMDGPU_INTRIN_IMAGE_STORE_D16;
 
+  const bool NoUnpackedD16VMem = !STI.hasUnpackedD16VMem();
+  const bool HasGather4D16Bug = BaseOpcode->Gather4 && IsD16 &&
+                                NoUnpackedD16VMem &&
+                                STI.hasImageGather4D16Bug();
+
   bool Unorm;
   if (!BaseOpcode->Sampler)
     Unorm = true;
@@ -2189,7 +2194,7 @@ bool AMDGPUInstructionSelector::selectImageIntrinsic(
       VDataTy = MRI->getType(VDataOut);
       NumVDataDwords = DMaskLanes;
 
-      if (IsD16 && !STI.hasUnpackedD16VMem())
+      if (IsD16 && NoUnpackedD16VMem && !HasGather4D16Bug)
         NumVDataDwords = (DMaskLanes + 1) / 2;
     }
   }
@@ -2287,17 +2292,19 @@ bool AMDGPUInstructionSelector::selectImageIntrinsic(
     .cloneMemRefs(MI);
 
   if (VDataOut) {
-    if (BaseOpcode->AtomicX2) {
-      const bool Is64 = MRI->getType(VDataOut).getSizeInBits() == 64;
-
+    if (BaseOpcode->AtomicX2 || HasGather4D16Bug) {
+      assert(!HasGather4D16Bug ||
+             NumVDataDwords == static_cast<int>(DMaskLanes + IsTexFail));
+      const unsigned DataDwords =
+          divideCeil(MRI->getType(VDataOut).getSizeInBits(), 32);
       Register TmpReg = MRI->createVirtualRegister(
-        Is64 ? &AMDGPU::VReg_128RegClass : &AMDGPU::VReg_64RegClass);
-      unsigned SubReg = Is64 ? AMDGPU::sub0_sub1 : AMDGPU::sub0;
+          TRI.getVGPRClassForBitWidth(NumVDataDwords * 32));
 
       MIB.addDef(TmpReg);
       if (!MRI->use_empty(VDataOut)) {
         BuildMI(*MBB, &MI, DL, TII.get(AMDGPU::COPY), VDataOut)
-            .addReg(TmpReg, RegState::Kill, SubReg);
+            .addReg(TmpReg, RegState::Kill,
+                    TRI.getSubRegFromChannel(0, DataDwords));
       }
 
     } else {
diff --git a/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll
new file mode 100644
index 0000000000000..7dfbc5bb9f31b
--- /dev/null
+++ b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll
@@ -0,0 +1,193 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
+; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=tonga -o - %s | FileCheck -check-prefix=GFX8-UNPACKED %s
+; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=gfx810 -o - %s | FileCheck -check-prefix=GFX81 %s
+; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=gfx900 -o - %s | FileCheck -check-prefix=GFX9 %s
+; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=gfx1010 -o - %s | FileCheck -check-prefix=GFX10 %s
+
+; gfx8.1/gfx9 sq misestimates register use for d16 gather4, so it needs one
+; dest register per dmask lane even though data packs into two registers.
+
+define amdgpu_ps <2 x float> @image_gather4_b_2d_v4f16(<8 x i32> inreg %rsrc, <4 x i32> inreg %samp, float %bias, float %s, float %t) {
+; GFX8-UNPACKED-LABEL: image_gather4_b_2d_v4f16:
+; GFX8-UNPACKED:       ; %bb.0: ; %main_body
+; GFX8-UNPACKED-NEXT:    s_mov_b64 s[14:15], exec
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s0, s2
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s1, s3
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s2, s4
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s3, s5
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s4, s6
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s5, s7
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s6, s8
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s7, s9
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s8, s10
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s9, s11
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s10, s12
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s11, s13
+; GFX8-UNPACKED-NEXT:    s_wqm_b64 exec, exec
+; GFX8-UNPACKED-NEXT:    s_and_b64 exec, exec, s[14:15]
+; GFX8-UNPACKED-NEXT:    image_gather4_b v[0:3], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
+; GFX8-UNPACKED-NEXT:    s_waitcnt vmcnt(0)
+; GFX8-UNPACKED-NEXT:    v_and_b32_e32 v1, 0xffff, v1
+; GFX8-UNPACKED-NEXT:    v_and_b32_e32 v3, 0xffff, v3
+; GFX8-UNPACKED-NEXT:    v_lshlrev_b32_e32 v1, 16, v1
+; GFX8-UNPACKED-NEXT:    v_lshlrev_b32_e32 v3, 16, v3
+; GFX8-UNPACKED-NEXT:    v_or_b32_sdwa v0, v0, v1 dst_sel:DWORD dst_unused:UNUSED_PAD src0_sel:WORD_0 src1_sel:DWORD
+; GFX8-UNPACKED-NEXT:    v_or_b32_sdwa v1, v2, v3 dst_sel:DWORD dst_unused:UNUSED_PAD src0_sel:WORD_0 src1_sel:DWORD
+; GFX8-UNPACKED-NEXT:    ; return to shader part epilog
+;
+; GFX81-LABEL: image_gather4_b_2d_v4f16:
+; GFX81:       ; %bb.0: ; %main_body
+; GFX81-NEXT:    s_mov_b64 s[14:15], exec
+; GFX81-NEXT:    s_mov_b32 s0, s2
+; GFX81-NEXT:    s_mov_b32 s1, s3
+; GFX81-NEXT:    s_mov_b32 s2, s4
+; GFX81-NEXT:    s_mov_b32 s3, s5
+; GFX81-NEXT:    s_mov_b32 s4, s6
+; GFX81-NEXT:    s_mov_b32 s5, s7
+; GFX81-NEXT:    s_mov_b32 s6, s8
+; GFX81-NEXT:    s_mov_b32 s7, s9
+; GFX81-NEXT:    s_mov_b32 s8, s10
+; GFX81-NEXT:    s_mov_b32 s9, s11
+; GFX81-NEXT:    s_mov_b32 s10, s12
+; GFX81-NEXT:    s_mov_b32 s11, s13
+; GFX81-NEXT:    s_wqm_b64 exec, exec
+; GFX81-NEXT:    s_and_b64 exec, exec, s[14:15]
+; GFX81-NEXT:    image_gather4_b v[0:3], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
+; GFX81-NEXT:    s_waitcnt vmcnt(0)
+; GFX81-NEXT:    ; return to shader part epilog
+;
+; GFX9-LABEL: image_gather4_b_2d_v4f16:
+; GFX9:       ; %bb.0: ; %main_body
+; GFX9-NEXT:    s_mov_b64 s[14:15], exec
+; GFX9-NEXT:    s_mov_b32 s0, s2
+; GFX9-NEXT:    s_mov_b32 s1, s3
+; GFX9-NEXT:    s_mov_b32 s2, s4
+; GFX9-NEXT:    s_mov_b32 s3, s5
+; GFX9-NEXT:    s_mov_b32 s4, s6
+; GFX9-NEXT:    s_mov_b32 s5, s7
+; GFX9-NEXT:    s_mov_b32 s6, s8
+; GFX9-NEXT:    s_mov_b32 s7, s9
+; GFX9-NEXT:    s_mov_b32 s8, s10
+; GFX9-NEXT:    s_mov_b32 s9, s11
+; GFX9-NEXT:    s_mov_b32 s10, s12
+; GFX9-NEXT:    s_mov_b32 s11, s13
+; GFX9-NEXT:    s_wqm_b64 exec, exec
+; GFX9-NEXT:    s_and_b64 exec, exec, s[14:15]
+; GFX9-NEXT:    image_gather4_b v[0:3], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
+; GFX9-NEXT:    s_waitcnt vmcnt(0)
+; GFX9-NEXT:    ; return to shader part epilog
+;
+; GFX10-LABEL: image_gather4_b_2d_v4f16:
+; GFX10:       ; %bb.0: ; %main_body
+; GFX10-NEXT:    s_mov_b32 s1, exec_lo
+; GFX10-NEXT:    s_mov_b32 s0, s2
+; GFX10-NEXT:    s_wqm_b32 exec_lo, exec_lo
+; GFX10-NEXT:    s_and_b32 exec_lo, exec_lo, s1
+; GFX10-NEXT:    s_mov_b32 s1, s3
+; GFX10-NEXT:    s_mov_b32 s2, s4
+; GFX10-NEXT:    s_mov_b32 s3, s5
+; GFX10-NEXT:    s_mov_b32 s4, s6
+; GFX10-NEXT:    s_mov_b32 s5, s7
+; GFX10-NEXT:    s_mov_b32 s6, s8
+; GFX10-NEXT:    s_mov_b32 s7, s9
+; GFX10-NEXT:    s_mov_b32 s8, s10
+; GFX10-NEXT:    s_mov_b32 s9, s11
+; GFX10-NEXT:    s_mov_b32 s10, s12
+; GFX10-NEXT:    s_mov_b32 s11, s13
+; GFX10-NEXT:    image_gather4_b v[0:1], v[0:2], s[0:7], s[8:11] dmask:0x4 dim:SQ_RSRC_IMG_2D d16
+; GFX10-NEXT:    s_waitcnt vmcnt(0)
+; GFX10-NEXT:    ; return to shader part epilog
+main_body:
+  %tex = call <4 x half> @llvm.amdgcn.image.gather4.b.2d.v4f16.f32.f32(i32 4, float %bias, float %s, float %t, <8 x i32> %rsrc, <4 x i32> %samp, i1 false, i32 0, i32 0)
+  %r = bitcast <4 x half> %tex to <2 x float>
+  ret <2 x float> %r
+}
+
+define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16(<8 x i32> inreg %rsrc, <4 x i32> inreg %samp, float %s, float %t) {
+; GFX8-UNPACKED-LABEL: image_gather4_lz_2d_v4f16:
+; GFX8-UNPACKED:       ; %bb.0: ; %main_body
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s0, s2
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s1, s3
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s2, s4
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s3, s5
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s4, s6
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s5, s7
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s6, s8
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s7, s9
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s8, s10
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s9, s11
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s10, s12
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s11, s13
+; GFX8-UNPACKED-NEXT:    image_gather4_lz v[0:3], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
+; GFX8-UNPACKED-NEXT:    s_waitcnt vmcnt(0)
+; GFX8-UNPACKED-NEXT:    v_and_b32_e32 v1, 0xffff, v1
+; GFX8-UNPACKED-NEXT:    v_and_b32_e32 v3, 0xffff, v3
+; GFX8-UNPACKED-NEXT:    v_lshlrev_b32_e32 v1, 16, v1
+; GFX8-UNPACKED-NEXT:    v_lshlrev_b32_e32 v3, 16, v3
+; GFX8-UNPACKED-NEXT:    v_or_b32_sdwa v0, v0, v1 dst_sel:DWORD dst_unused:UNUSED_PAD src0_sel:WORD_0 src1_sel:DWORD
+; GFX8-UNPACKED-NEXT:    v_or_b32_sdwa v1, v2, v3 dst_sel:DWORD dst_unused:UNUSED_PAD src0_sel:WORD_0 src1_sel:DWORD
+; GFX8-UNPACKED-NEXT:    ; return to shader part epilog
+;
+; GFX81-LABEL: image_gather4_lz_2d_v4f16:
+; GFX81:       ; %bb.0: ; %main_body
+; GFX81-NEXT:    s_mov_b32 s0, s2
+; GFX81-NEXT:    s_mov_b32 s1, s3
+; GFX81-NEXT:    s_mov_b32 s2, s4
+; GFX81-NEXT:    s_mov_b32 s3, s5
+; GFX81-NEXT:    s_mov_b32 s4, s6
+; GFX81-NEXT:    s_mov_b32 s5, s7
+; GFX81-NEXT:    s_mov_b32 s6, s8
+; GFX81-NEXT:    s_mov_b32 s7, s9
+; GFX81-NEXT:    s_mov_b32 s8, s10
+; GFX81-NEXT:    s_mov_b32 s9, s11
+; GFX81-NEXT:    s_mov_b32 s10, s12
+; GFX81-NEXT:    s_mov_b32 s11, s13
+; GFX81-NEXT:    image_gather4_lz v[0:3], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
+; GFX81-NEXT:    s_waitcnt vmcnt(0)
+; GFX81-NEXT:    ; return to shader part epilog
+;
+; GFX9-LABEL: image_gather4_lz_2d_v4f16:
+; GFX9:       ; %bb.0: ; %main_body
+; GFX9-NEXT:    s_mov_b32 s0, s2
+; GFX9-NEXT:    s_mov_b32 s1, s3
+; GFX9-NEXT:    s_mov_b32 s2, s4
+; GFX9-NEXT:    s_mov_b32 s3, s5
+; GFX9-NEXT:    s_mov_b32 s4, s6
+; GFX9-NEXT:    s_mov_b32 s5, s7
+; GFX9-NEXT:    s_mov_b32 s6, s8
+; GFX9-NEXT:    s_mov_b32 s7, s9
+; GFX9-NEXT:    s_mov_b32 s8, s10
+; GFX9-NEXT:    s_mov_b32 s9, s11
+; GFX9-NEXT:    s_mov_b32 s10, s12
+; GFX9-NEXT:    s_mov_b32 s11, s13
+; GFX9-NEXT:    image_gather4_lz v[0:3], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
+; GFX9-NEXT:    s_waitcnt vmcnt(0)
+; GFX9-NEXT:    ; return to shader part epilog
+;
+; GFX10-LABEL: image_gather4_lz_2d_v4f16:
+; GFX10:       ; %bb.0: ; %main_body
+; GFX10-NEXT:    s_mov_b32 s0, s2
+; GFX10-NEXT:    s_mov_b32 s1, s3
+; GFX10-NEXT:    s_mov_b32 s2, s4
+; GFX10-NEXT:    s_mov_b32 s3, s5
+; GFX10-NEXT:    s_mov_b32 s4, s6
+; GFX10-NEXT:    s_mov_b32 s5, s7
+; GFX10-NEXT:    s_mov_b32 s6, s8
+; GFX10-NEXT:    s_mov_b32 s7, s9
+; GFX10-NEXT:    s_mov_b32 s8, s10
+; GFX10-NEXT:    s_mov_b32 s9, s11
+; GFX10-NEXT:    s_mov_b32 s10, s12
+; GFX10-NEXT:    s_mov_b32 s11, s13
+; GFX10-NEXT:    image_gather4_lz v[0:1], v[0:1], s[0:7], s[8:11] dmask:0x1 dim:SQ_RSRC_IMG_2D d16
+; GFX10-NEXT:    s_waitcnt vmcnt(0)
+; GFX10-NEXT:    ; return to shader part epilog
+main_body:
+  %tex = call <4 x half> @llvm.amdgcn.image.gather4.lz.2d.v4f16.f32(i32 1, float %s, float %t, <8 x i32> %rsrc, <4 x i32> %samp, i1 false, i32 0, i32 0)
+  %r = bitcast <4 x half> %tex to <2 x float>
+  ret <2 x float> %r
+}
+
+declare <4 x half> @llvm.amdgcn.image.gather4.b.2d.v4f16.f32.f32(i32, float, float, float, <8 x i32>, <4 x i32>, i1, i32, i32) #0
+declare <4 x half> @llvm.amdgcn.image.gather4.lz.2d.v4f16.f32(i32, float, float, <8 x i32>, <4 x i32>, i1, i32, i32) #0
+
+attributes #0 = { nounwind readonly }
diff --git a/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll
new file mode 100644
index 0000000000000..e19a68c422e21
--- /dev/null
+++ b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll
@@ -0,0 +1,105 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
+; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=tonga -o - %s | FileCheck -check-prefix=GFX8-UNPACKED %s
+; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=gfx810 -o - %s | FileCheck -check-prefix=GFX81 %s
+; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=gfx900 -o - %s | FileCheck -check-prefix=GFX9 %s
+
+; With tfe the workaround needs five dest registers (4 dmask lanes + status),
+; but only the first three hold data.
+
+define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16_tfe(<8 x i32> inreg %rsrc, <4 x i32> inreg %samp, float %s, float %t, ptr addrspace(1) %out) {
+; GFX8-UNPACKED-LABEL: image_gather4_lz_2d_v4f16_tfe:
+; GFX8-UNPACKED:       ; %bb.0: ; %main_body
+; GFX8-UNPACKED-NEXT:    v_mov_b32_e32 v4, 0
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s0, s2
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s1, s3
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s2, s4
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s3, s5
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s4, s6
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s5, s7
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s6, s8
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s7, s9
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s8, s10
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s9, s11
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s10, s12
+; GFX8-UNPACKED-NEXT:    s_mov_b32 s11, s13
+; GFX8-UNPACKED-NEXT:    v_mov_b32_e32 v5, v4
+; GFX8-UNPACKED-NEXT:    v_mov_b32_e32 v6, v4
+; GFX8-UNPACKED-NEXT:    v_mov_b32_e32 v7, v4
+; GFX8-UNPACKED-NEXT:    v_mov_b32_e32 v8, v4
+; GFX8-UNPACKED-NEXT:    image_gather4_lz v[4:8], v[0:1], s[0:7], s[8:11] dmask:0x1 tfe d16
+; GFX8-UNPACKED-NEXT:    s_waitcnt vmcnt(0)
+; GFX8-UNPACKED-NEXT:    v_and_b32_e32 v0, 0xffff, v5
+; GFX8-UNPACKED-NEXT:    v_and_b32_e32 v1, 0xffff, v7
+; GFX8-UNPACKED-NEXT:    v_lshlrev_b32_e32 v0, 16, v0
+; GFX8-UNPACKED-NEXT:    v_lshlrev_b32_e32 v1, 16, v1
+; GFX8-UNPACKED-NEXT:    v_or_b32_sdwa v0, v4, v0 dst_sel:DWORD dst_unused:UNUSED_PAD src0_sel:WORD_0 src1_sel:DWORD
+; GFX8-UNPACKED-NEXT:    v_or_b32_sdwa v1, v6, v1 dst_sel:DWORD dst_unused:UNUSED_PAD src0_sel:WORD_0 src1_sel:DWORD
+; GFX8-UNPACKED-NEXT:    flat_store_dword v[2:3], v8
+; GFX8-UNPACKED-NEXT:    s_waitcnt vmcnt(0)
+; GFX8-UNPACKED-NEXT:    ; return to shader part epilog
+;
+; GFX81-LABEL: image_gather4_lz_2d_v4f16_tfe:
+; GFX81:       ; %bb.0: ; %main_body
+; GFX81-NEXT:    v_mov_b32_e32 v4, v0
+; GFX81-NEXT:    v_mov_b32_e32 v0, 0
+; GFX81-NEXT:    s_mov_b32 s0, s2
+; GFX81-NEXT:    s_mov_b32 s1, s3
+; GFX81-NEXT:    s_mov_b32 s2, s4
+; GFX81-NEXT:    s_mov_b32 s3, s5
+; GFX81-NEXT:    s_mov_b32 s4, s6
+; GFX81-NEXT:    s_mov_b32 s5, s7
+; GFX81-NEXT:    s_mov_b32 s6, s8
+; GFX81-NEXT:    s_mov_b32 s7, s9
+; GFX81-NEXT:    s_mov_b32 s8, s10
+; GFX81-NEXT:    s_mov_b32 s9, s11
+; GFX81-NEXT:    s_mov_b32 s10, s12
+; GFX81-NEXT:    s_mov_b32 s11, s13
+; GFX81-NEXT:    v_mov_b32_e32 v5, v1
+; GFX81-NEXT:    v_mov_b32_e32 v6, v2
+; GFX81-NEXT:    v_mov_b32_e32 v1, v0
+; GFX81-NEXT:    v_mov_b32_e32 v2, v0
+; GFX81-NEXT:    v_mov_b32_e32 v7, v3
+; GFX81-NEXT:    image_gather4_lz v[0:4], v[4:5], s[0:7], s[8:11] dmask:0x1 tfe d16
+; GFX81-NEXT:    s_waitcnt vmcnt(0)
+; GFX81-NEXT:    flat_store_dword v[6:7], v2
+; GFX81-NEXT:    s_waitcnt vmcnt(0)
+; GFX81-NEXT:    ; return to shader part epilog
+;
+; GFX9-LABEL: image_gather4_lz_2d_v4f16_tfe:
+; GFX9:       ; %bb.0: ; %main_body
+; GFX9-NEXT:    v_mov_b32_e32 v4, v0
+; GFX9-NEXT:    v_mov_b32_e32 v0, 0
+; GFX9-NEXT:    s_mov_b32 s0, s2
+; GFX9-NEXT:    s_mov_b32 s1, s3
+; GFX9-NEXT:    s_mov_b32 s2, s4
+; GFX9-NEXT:    s_mov_b32 s3, s5
+; GFX9-NEXT:    s_mov_b32 s4, s6
+; GFX9-NEXT:    s_mov_b32 s5, s7
+; GFX9-NEXT:    s_mov_b32 s6, s8
+; GFX9-NEXT:    s_mov_b32 s7, s9
+; GFX9-NEXT:    s_mov_b32 s8, s10
+; GFX9-NEXT:    s_mov_b32 s9, s11
+; GFX9-NEXT:    s_mov_b32 s10, s12
+; GFX9-NEXT:    s_mov_b32 s11, s13
+; GFX9-NEXT:    v_mov_b32_e32 v5, v1
+; GFX9-NEXT:    v_mov_b32_e32 v6, v2
+; GFX9-NEXT:    v_mov_b32_e32 v1, v0
+; GFX9-NEXT:    v_mov_b32_e32 v2, v0
+; GFX9-NEXT:    v_mov_b32_e32 v7, v3
+; GFX9-NEXT:    image_gather4_lz v[0:4], v[4:5], s[0:7], s[8:11] dmask:0x1 tfe d16
+; GFX9-NEXT:    s_waitcnt vmcnt(0)
+; GFX9-NEXT:    global_store_dword v[6:7], v2, off
+; GFX9-NEXT:    s_waitcnt vmcnt(0)
+; GFX9-NEXT:    ; return to shader part epilog
+main_body:
+  %tex = call {<4 x half>, i32} @llvm.amdgcn.image.gather4.lz.2d.sl_v4f16i32s.f32(i32 1, float %s, float %t, <8 x i32> %rsrc, <4 x i32> %samp, i1 false, i32 1, i32 0)
+  %data = extractvalue {<4 x half>, i32} %tex, 0
+  %status = extractvalue {<4 x half>, i32} %tex, 1
+  store i32 %status, ptr addrspace(1) %out
+  %r = bitcast <4 x half> %data to <2 x float>
+  ret <2 x float> %r
+}
+
+declare {<4 x half>, i32} @llvm.amdgcn.image.gather4.lz.2d.sl_v4f16i32s.f32(i32, float, float, <8 x i32>, <4 x i32>, i1, i32, i32) #0
+
+attributes #0 = { nounwind readonly }
diff --git a/llvm/test/CodeGen/AMDGPU/llvm.amdgcn.image.gather4.d16.dim.ll b/llvm/test/CodeGen/AMDGPU/llvm.amdgcn.image.gather4.d16.dim.ll
index 6f89dc9eb74bd..977eab56aeaa4 100644
--- a/llvm/test/CodeGen/AMDGPU/llvm.amdgcn.image.gather4.d16.dim.ll
+++ b/llvm/test/CodeGen/AMDGPU/llvm.amdgcn.image.gather4.d16.dim.ll
@@ -37,8 +37,36 @@ main_body:
   ret <4 x half> %tex
 }
 
+; GCN-LABEL: {{^}}image_gather4_lz_2d_v4f16:
+; UNPACKED: image_gather4_lz v[0:3], v[0:1], s[0:7], s[8:11] dmask:0x1 d16{{$}}
+; GFX9: image_gather4_lz v[0:3], v[0:1], s[0:7], s[8:11] dmask:0x1 d16{{$}}
+; GFX10: image_gather4_lz v[0:1], v[0:1], s[0:7], s[8:11] dmask:0x1 dim:SQ_RSRC_IMG_2D d16{{$}}
+; GFX12PLUS: image_gather4_lz v[0:1], [v0, v1], s[0:7], s[8:11] dmask:0x1 dim:SQ_RSRC_IMG_2D d16{{$}}
+define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16(<8 x i32> inreg %rsrc, <4 x i32> inreg %samp, float %s, float %t) {
+main_body:
+  %tex = call <4 x half> @llvm.amdgcn.image.gather4.lz.2d.v4f16.f32(i32 1, float %s, float %t, <8 x i32> %rsrc, <4 x i32> %samp, i1 false, i32 0, i32 0)
+  %r = bitcast <4 x half> %tex to <2 x float>
+  ret <2 x float> %r
+}
+
+; GCN-LABEL: {{^}}image_gather4_lz_2d_v4f16_tfe:
+; UNPACKED: image_gather4_lz v[{{[0-9]+:[0-9]+}}], v[{{[0-9]+:[0-9]+}}], s[0:7], s[8:11] dmask:0x1 tfe d16{{$}}
+; GFX9: image_gather4_lz v[0:4], v[{{[0-9]+:[0-9]+}}], s[0:7], s[8:11] dmask:0x1 tfe d16{{$}}
+; GFX10: image_gather4_lz v[0:2], v[{{[0-9]+:[0-9]+}}], s[0:7], s[8:11] dmask:0x1 dim:SQ_RSRC_IMG_2D tfe d16{{$}}
+; GFX12PLUS: image_gather4_lz v[0:2], [v{{[0-9]+}}, v{{[0-9]+}}], s[0:7], s[8:11] dmask:0x1 dim:SQ_RSRC_IMG_2D tfe d16{{$}}
+define amdgpu_ps <4 x half> @image_gather4_lz_2d_v4f16_tfe(<8 x i32> inreg %rsrc, <4 x i32> inreg %samp, float %s, float %t, ptr addrspace(1) %out) {
+main_body:
+  %r = call { <4 x half>, i32 } @llvm.amdgcn.image.gather4.lz.2d.sl_v4f16i32s.f32(i32 1, float %s, float %t, <8 x i32> %rsrc, <4 x i32> %samp, i1 false, i32 1, i32 0)
+  %tex = extractvalue { <4 x half>, i32 } %r, 0
+  %tfe = extractvalue { <4 x half>, i32 } %r, 1
+  store i32 %tfe, ptr addrspace(1) %out
+  ret <4 x half> %tex
+}
+
 declare <4 x half> @llvm.amdgcn.image.gather4.b.2d.v4f16.f32.f32(i32, float, float, float, <8 x i32>, <4 x i32>, i1, i32, i32) #1
 declare { <4 x half>, i32 } @llvm.amdgcn.image.gather4.b.2d.sl_v4f16i32s.f32.f32(i32, float, float, float, <8 x i32>, <4 x i32>, i1, i32, i32) #1
+declare <4 x half> @llvm.amdgcn.image.gather4.lz.2d.v4f16.f32(i32, float, float, <8 x i32>, <4 x i32>, i1, i32, i32) #1
+declare { <4 x half>, i32 } @llvm.amdgcn.image.gather4.lz.2d.sl_v4f16i32s.f32(i32, float, float, <8 x i32>, <4 x i32>, i1, i32, i32) #1
 
 attributes #0 = { nounwind }
 attributes #1 = { nounwind readonly }

>From 0cc9925bd0018aa0af261c32d69a3a22bf026a43 Mon Sep 17 00:00:00 2001
From: Arseniy Obolenskiy <arseniy.obolenskiy at amd.com>
Date: Mon, 31 Aug 2026 14:44:12 +0200
Subject: [PATCH 2/3] change triples

---
 .../llvm.amdgcn.image.gather4.d16.dim.ll      | 128 +++---------------
 .../llvm.amdgcn.image.gather4.d16.tfe.dim.ll  |  46 +------
 2 files changed, 21 insertions(+), 153 deletions(-)

diff --git a/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll
index 7dfbc5bb9f31b..98d3f34b9b068 100644
--- a/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll
+++ b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll
@@ -1,8 +1,8 @@
 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
-; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=tonga -o - %s | FileCheck -check-prefix=GFX8-UNPACKED %s
-; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=gfx810 -o - %s | FileCheck -check-prefix=GFX81 %s
-; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=gfx900 -o - %s | FileCheck -check-prefix=GFX9 %s
-; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=gfx1010 -o - %s | FileCheck -check-prefix=GFX10 %s
+; RUN: llc -global-isel -mtriple=amdgpu8.02 -o - %s | FileCheck -check-prefix=GFX8-UNPACKED %s
+; RUN: llc -global-isel -mtriple=amdgpu8.10 -o - %s | FileCheck -check-prefix=GFX81 %s
+; RUN: llc -global-isel -mtriple=amdgpu9.00 -o - %s | FileCheck -check-prefix=GFX9 %s
+; RUN: llc -global-isel -mtriple=amdgpu10.10 -o - %s | FileCheck -check-prefix=GFX10 %s
 
 ; gfx8.1/gfx9 sq misestimates register use for d16 gather4, so it needs one
 ; dest register per dmask lane even though data packs into two registers.
@@ -10,21 +10,9 @@
 define amdgpu_ps <2 x float> @image_gather4_b_2d_v4f16(<8 x i32> inreg %rsrc, <4 x i32> inreg %samp, float %bias, float %s, float %t) {
 ; GFX8-UNPACKED-LABEL: image_gather4_b_2d_v4f16:
 ; GFX8-UNPACKED:       ; %bb.0: ; %main_body
-; GFX8-UNPACKED-NEXT:    s_mov_b64 s[14:15], exec
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s0, s2
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s1, s3
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s2, s4
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s3, s5
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s4, s6
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s5, s7
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s6, s8
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s7, s9
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s8, s10
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s9, s11
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s10, s12
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s11, s13
+; GFX8-UNPACKED-NEXT:    s_mov_b64 s[12:13], exec
 ; GFX8-UNPACKED-NEXT:    s_wqm_b64 exec, exec
-; GFX8-UNPACKED-NEXT:    s_and_b64 exec, exec, s[14:15]
+; GFX8-UNPACKED-NEXT:    s_and_b64 exec, exec, s[12:13]
 ; GFX8-UNPACKED-NEXT:    image_gather4_b v[0:3], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
 ; GFX8-UNPACKED-NEXT:    s_waitcnt vmcnt(0)
 ; GFX8-UNPACKED-NEXT:    v_and_b32_e32 v1, 0xffff, v1
@@ -37,63 +25,27 @@ define amdgpu_ps <2 x float> @image_gather4_b_2d_v4f16(<8 x i32> inreg %rsrc, <4
 ;
 ; GFX81-LABEL: image_gather4_b_2d_v4f16:
 ; GFX81:       ; %bb.0: ; %main_body
-; GFX81-NEXT:    s_mov_b64 s[14:15], exec
-; GFX81-NEXT:    s_mov_b32 s0, s2
-; GFX81-NEXT:    s_mov_b32 s1, s3
-; GFX81-NEXT:    s_mov_b32 s2, s4
-; GFX81-NEXT:    s_mov_b32 s3, s5
-; GFX81-NEXT:    s_mov_b32 s4, s6
-; GFX81-NEXT:    s_mov_b32 s5, s7
-; GFX81-NEXT:    s_mov_b32 s6, s8
-; GFX81-NEXT:    s_mov_b32 s7, s9
-; GFX81-NEXT:    s_mov_b32 s8, s10
-; GFX81-NEXT:    s_mov_b32 s9, s11
-; GFX81-NEXT:    s_mov_b32 s10, s12
-; GFX81-NEXT:    s_mov_b32 s11, s13
+; GFX81-NEXT:    s_mov_b64 s[12:13], exec
 ; GFX81-NEXT:    s_wqm_b64 exec, exec
-; GFX81-NEXT:    s_and_b64 exec, exec, s[14:15]
-; GFX81-NEXT:    image_gather4_b v[0:3], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
+; GFX81-NEXT:    s_and_b64 exec, exec, s[12:13]
+; GFX81-NEXT:    image_gather4_b v[0:1], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
 ; GFX81-NEXT:    s_waitcnt vmcnt(0)
 ; GFX81-NEXT:    ; return to shader part epilog
 ;
 ; GFX9-LABEL: image_gather4_b_2d_v4f16:
 ; GFX9:       ; %bb.0: ; %main_body
-; GFX9-NEXT:    s_mov_b64 s[14:15], exec
-; GFX9-NEXT:    s_mov_b32 s0, s2
-; GFX9-NEXT:    s_mov_b32 s1, s3
-; GFX9-NEXT:    s_mov_b32 s2, s4
-; GFX9-NEXT:    s_mov_b32 s3, s5
-; GFX9-NEXT:    s_mov_b32 s4, s6
-; GFX9-NEXT:    s_mov_b32 s5, s7
-; GFX9-NEXT:    s_mov_b32 s6, s8
-; GFX9-NEXT:    s_mov_b32 s7, s9
-; GFX9-NEXT:    s_mov_b32 s8, s10
-; GFX9-NEXT:    s_mov_b32 s9, s11
-; GFX9-NEXT:    s_mov_b32 s10, s12
-; GFX9-NEXT:    s_mov_b32 s11, s13
+; GFX9-NEXT:    s_mov_b64 s[12:13], exec
 ; GFX9-NEXT:    s_wqm_b64 exec, exec
-; GFX9-NEXT:    s_and_b64 exec, exec, s[14:15]
-; GFX9-NEXT:    image_gather4_b v[0:3], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
+; GFX9-NEXT:    s_and_b64 exec, exec, s[12:13]
+; GFX9-NEXT:    image_gather4_b v[0:1], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
 ; GFX9-NEXT:    s_waitcnt vmcnt(0)
 ; GFX9-NEXT:    ; return to shader part epilog
 ;
 ; GFX10-LABEL: image_gather4_b_2d_v4f16:
 ; GFX10:       ; %bb.0: ; %main_body
-; GFX10-NEXT:    s_mov_b32 s1, exec_lo
-; GFX10-NEXT:    s_mov_b32 s0, s2
+; GFX10-NEXT:    s_mov_b32 s12, exec_lo
 ; GFX10-NEXT:    s_wqm_b32 exec_lo, exec_lo
-; GFX10-NEXT:    s_and_b32 exec_lo, exec_lo, s1
-; GFX10-NEXT:    s_mov_b32 s1, s3
-; GFX10-NEXT:    s_mov_b32 s2, s4
-; GFX10-NEXT:    s_mov_b32 s3, s5
-; GFX10-NEXT:    s_mov_b32 s4, s6
-; GFX10-NEXT:    s_mov_b32 s5, s7
-; GFX10-NEXT:    s_mov_b32 s6, s8
-; GFX10-NEXT:    s_mov_b32 s7, s9
-; GFX10-NEXT:    s_mov_b32 s8, s10
-; GFX10-NEXT:    s_mov_b32 s9, s11
-; GFX10-NEXT:    s_mov_b32 s10, s12
-; GFX10-NEXT:    s_mov_b32 s11, s13
+; GFX10-NEXT:    s_and_b32 exec_lo, exec_lo, s12
 ; GFX10-NEXT:    image_gather4_b v[0:1], v[0:2], s[0:7], s[8:11] dmask:0x4 dim:SQ_RSRC_IMG_2D d16
 ; GFX10-NEXT:    s_waitcnt vmcnt(0)
 ; GFX10-NEXT:    ; return to shader part epilog
@@ -106,18 +58,6 @@ main_body:
 define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16(<8 x i32> inreg %rsrc, <4 x i32> inreg %samp, float %s, float %t) {
 ; GFX8-UNPACKED-LABEL: image_gather4_lz_2d_v4f16:
 ; GFX8-UNPACKED:       ; %bb.0: ; %main_body
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s0, s2
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s1, s3
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s2, s4
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s3, s5
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s4, s6
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s5, s7
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s6, s8
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s7, s9
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s8, s10
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s9, s11
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s10, s12
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s11, s13
 ; GFX8-UNPACKED-NEXT:    image_gather4_lz v[0:3], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
 ; GFX8-UNPACKED-NEXT:    s_waitcnt vmcnt(0)
 ; GFX8-UNPACKED-NEXT:    v_and_b32_e32 v1, 0xffff, v1
@@ -130,54 +70,18 @@ define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16(<8 x i32> inreg %rsrc, <
 ;
 ; GFX81-LABEL: image_gather4_lz_2d_v4f16:
 ; GFX81:       ; %bb.0: ; %main_body
-; GFX81-NEXT:    s_mov_b32 s0, s2
-; GFX81-NEXT:    s_mov_b32 s1, s3
-; GFX81-NEXT:    s_mov_b32 s2, s4
-; GFX81-NEXT:    s_mov_b32 s3, s5
-; GFX81-NEXT:    s_mov_b32 s4, s6
-; GFX81-NEXT:    s_mov_b32 s5, s7
-; GFX81-NEXT:    s_mov_b32 s6, s8
-; GFX81-NEXT:    s_mov_b32 s7, s9
-; GFX81-NEXT:    s_mov_b32 s8, s10
-; GFX81-NEXT:    s_mov_b32 s9, s11
-; GFX81-NEXT:    s_mov_b32 s10, s12
-; GFX81-NEXT:    s_mov_b32 s11, s13
-; GFX81-NEXT:    image_gather4_lz v[0:3], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
+; GFX81-NEXT:    image_gather4_lz v[0:1], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
 ; GFX81-NEXT:    s_waitcnt vmcnt(0)
 ; GFX81-NEXT:    ; return to shader part epilog
 ;
 ; GFX9-LABEL: image_gather4_lz_2d_v4f16:
 ; GFX9:       ; %bb.0: ; %main_body
-; GFX9-NEXT:    s_mov_b32 s0, s2
-; GFX9-NEXT:    s_mov_b32 s1, s3
-; GFX9-NEXT:    s_mov_b32 s2, s4
-; GFX9-NEXT:    s_mov_b32 s3, s5
-; GFX9-NEXT:    s_mov_b32 s4, s6
-; GFX9-NEXT:    s_mov_b32 s5, s7
-; GFX9-NEXT:    s_mov_b32 s6, s8
-; GFX9-NEXT:    s_mov_b32 s7, s9
-; GFX9-NEXT:    s_mov_b32 s8, s10
-; GFX9-NEXT:    s_mov_b32 s9, s11
-; GFX9-NEXT:    s_mov_b32 s10, s12
-; GFX9-NEXT:    s_mov_b32 s11, s13
-; GFX9-NEXT:    image_gather4_lz v[0:3], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
+; GFX9-NEXT:    image_gather4_lz v[0:1], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
 ; GFX9-NEXT:    s_waitcnt vmcnt(0)
 ; GFX9-NEXT:    ; return to shader part epilog
 ;
 ; GFX10-LABEL: image_gather4_lz_2d_v4f16:
 ; GFX10:       ; %bb.0: ; %main_body
-; GFX10-NEXT:    s_mov_b32 s0, s2
-; GFX10-NEXT:    s_mov_b32 s1, s3
-; GFX10-NEXT:    s_mov_b32 s2, s4
-; GFX10-NEXT:    s_mov_b32 s3, s5
-; GFX10-NEXT:    s_mov_b32 s4, s6
-; GFX10-NEXT:    s_mov_b32 s5, s7
-; GFX10-NEXT:    s_mov_b32 s6, s8
-; GFX10-NEXT:    s_mov_b32 s7, s9
-; GFX10-NEXT:    s_mov_b32 s8, s10
-; GFX10-NEXT:    s_mov_b32 s9, s11
-; GFX10-NEXT:    s_mov_b32 s10, s12
-; GFX10-NEXT:    s_mov_b32 s11, s13
 ; GFX10-NEXT:    image_gather4_lz v[0:1], v[0:1], s[0:7], s[8:11] dmask:0x1 dim:SQ_RSRC_IMG_2D d16
 ; GFX10-NEXT:    s_waitcnt vmcnt(0)
 ; GFX10-NEXT:    ; return to shader part epilog
diff --git a/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll
index e19a68c422e21..932bd8930b20f 100644
--- a/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll
+++ b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll
@@ -1,7 +1,7 @@
 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
-; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=tonga -o - %s | FileCheck -check-prefix=GFX8-UNPACKED %s
-; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=gfx810 -o - %s | FileCheck -check-prefix=GFX81 %s
-; RUN: llc -global-isel -mtriple=amdgcn-mesa-mesa3d -mcpu=gfx900 -o - %s | FileCheck -check-prefix=GFX9 %s
+; RUN: llc -global-isel -mtriple=amdgpu8.02 -o - %s | FileCheck -check-prefix=GFX8-UNPACKED %s
+; RUN: llc -global-isel -mtriple=amdgpu8.10 -o - %s | FileCheck -check-prefix=GFX81 %s
+; RUN: llc -global-isel -mtriple=amdgpu9.00 -o - %s | FileCheck -check-prefix=GFX9 %s
 
 ; With tfe the workaround needs five dest registers (4 dmask lanes + status),
 ; but only the first three hold data.
@@ -10,18 +10,6 @@ define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16_tfe(<8 x i32> inreg %rsr
 ; GFX8-UNPACKED-LABEL: image_gather4_lz_2d_v4f16_tfe:
 ; GFX8-UNPACKED:       ; %bb.0: ; %main_body
 ; GFX8-UNPACKED-NEXT:    v_mov_b32_e32 v4, 0
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s0, s2
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s1, s3
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s2, s4
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s3, s5
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s4, s6
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s5, s7
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s6, s8
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s7, s9
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s8, s10
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s9, s11
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s10, s12
-; GFX8-UNPACKED-NEXT:    s_mov_b32 s11, s13
 ; GFX8-UNPACKED-NEXT:    v_mov_b32_e32 v5, v4
 ; GFX8-UNPACKED-NEXT:    v_mov_b32_e32 v6, v4
 ; GFX8-UNPACKED-NEXT:    v_mov_b32_e32 v7, v4
@@ -42,24 +30,12 @@ define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16_tfe(<8 x i32> inreg %rsr
 ; GFX81:       ; %bb.0: ; %main_body
 ; GFX81-NEXT:    v_mov_b32_e32 v4, v0
 ; GFX81-NEXT:    v_mov_b32_e32 v0, 0
-; GFX81-NEXT:    s_mov_b32 s0, s2
-; GFX81-NEXT:    s_mov_b32 s1, s3
-; GFX81-NEXT:    s_mov_b32 s2, s4
-; GFX81-NEXT:    s_mov_b32 s3, s5
-; GFX81-NEXT:    s_mov_b32 s4, s6
-; GFX81-NEXT:    s_mov_b32 s5, s7
-; GFX81-NEXT:    s_mov_b32 s6, s8
-; GFX81-NEXT:    s_mov_b32 s7, s9
-; GFX81-NEXT:    s_mov_b32 s8, s10
-; GFX81-NEXT:    s_mov_b32 s9, s11
-; GFX81-NEXT:    s_mov_b32 s10, s12
-; GFX81-NEXT:    s_mov_b32 s11, s13
 ; GFX81-NEXT:    v_mov_b32_e32 v5, v1
 ; GFX81-NEXT:    v_mov_b32_e32 v6, v2
 ; GFX81-NEXT:    v_mov_b32_e32 v1, v0
 ; GFX81-NEXT:    v_mov_b32_e32 v2, v0
+; GFX81-NEXT:    image_gather4_lz v[0:2], v[4:5], s[0:7], s[8:11] dmask:0x1 tfe d16
 ; GFX81-NEXT:    v_mov_b32_e32 v7, v3
-; GFX81-NEXT:    image_gather4_lz v[0:4], v[4:5], s[0:7], s[8:11] dmask:0x1 tfe d16
 ; GFX81-NEXT:    s_waitcnt vmcnt(0)
 ; GFX81-NEXT:    flat_store_dword v[6:7], v2
 ; GFX81-NEXT:    s_waitcnt vmcnt(0)
@@ -69,24 +45,12 @@ define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16_tfe(<8 x i32> inreg %rsr
 ; GFX9:       ; %bb.0: ; %main_body
 ; GFX9-NEXT:    v_mov_b32_e32 v4, v0
 ; GFX9-NEXT:    v_mov_b32_e32 v0, 0
-; GFX9-NEXT:    s_mov_b32 s0, s2
-; GFX9-NEXT:    s_mov_b32 s1, s3
-; GFX9-NEXT:    s_mov_b32 s2, s4
-; GFX9-NEXT:    s_mov_b32 s3, s5
-; GFX9-NEXT:    s_mov_b32 s4, s6
-; GFX9-NEXT:    s_mov_b32 s5, s7
-; GFX9-NEXT:    s_mov_b32 s6, s8
-; GFX9-NEXT:    s_mov_b32 s7, s9
-; GFX9-NEXT:    s_mov_b32 s8, s10
-; GFX9-NEXT:    s_mov_b32 s9, s11
-; GFX9-NEXT:    s_mov_b32 s10, s12
-; GFX9-NEXT:    s_mov_b32 s11, s13
 ; GFX9-NEXT:    v_mov_b32_e32 v5, v1
 ; GFX9-NEXT:    v_mov_b32_e32 v6, v2
 ; GFX9-NEXT:    v_mov_b32_e32 v1, v0
 ; GFX9-NEXT:    v_mov_b32_e32 v2, v0
+; GFX9-NEXT:    image_gather4_lz v[0:2], v[4:5], s[0:7], s[8:11] dmask:0x1 tfe d16
 ; GFX9-NEXT:    v_mov_b32_e32 v7, v3
-; GFX9-NEXT:    image_gather4_lz v[0:4], v[4:5], s[0:7], s[8:11] dmask:0x1 tfe d16
 ; GFX9-NEXT:    s_waitcnt vmcnt(0)
 ; GFX9-NEXT:    global_store_dword v[6:7], v2, off
 ; GFX9-NEXT:    s_waitcnt vmcnt(0)

>From 020ad564af8a8c017f10a27af5867476ca79c38f Mon Sep 17 00:00:00 2001
From: Arseniy Obolenskiy <arseniy.obolenskiy at amd.com>
Date: Mon, 31 Aug 2026 15:51:03 +0200
Subject: [PATCH 3/3] fix lines

---
 .../GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll       | 8 ++++----
 .../GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll   | 4 ++--
 2 files changed, 6 insertions(+), 6 deletions(-)

diff --git a/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll
index 98d3f34b9b068..983b027b54dc2 100644
--- a/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll
+++ b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.dim.ll
@@ -28,7 +28,7 @@ define amdgpu_ps <2 x float> @image_gather4_b_2d_v4f16(<8 x i32> inreg %rsrc, <4
 ; GFX81-NEXT:    s_mov_b64 s[12:13], exec
 ; GFX81-NEXT:    s_wqm_b64 exec, exec
 ; GFX81-NEXT:    s_and_b64 exec, exec, s[12:13]
-; GFX81-NEXT:    image_gather4_b v[0:1], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
+; GFX81-NEXT:    image_gather4_b v[0:3], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
 ; GFX81-NEXT:    s_waitcnt vmcnt(0)
 ; GFX81-NEXT:    ; return to shader part epilog
 ;
@@ -37,7 +37,7 @@ define amdgpu_ps <2 x float> @image_gather4_b_2d_v4f16(<8 x i32> inreg %rsrc, <4
 ; GFX9-NEXT:    s_mov_b64 s[12:13], exec
 ; GFX9-NEXT:    s_wqm_b64 exec, exec
 ; GFX9-NEXT:    s_and_b64 exec, exec, s[12:13]
-; GFX9-NEXT:    image_gather4_b v[0:1], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
+; GFX9-NEXT:    image_gather4_b v[0:3], v[0:2], s[0:7], s[8:11] dmask:0x4 d16
 ; GFX9-NEXT:    s_waitcnt vmcnt(0)
 ; GFX9-NEXT:    ; return to shader part epilog
 ;
@@ -70,13 +70,13 @@ define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16(<8 x i32> inreg %rsrc, <
 ;
 ; GFX81-LABEL: image_gather4_lz_2d_v4f16:
 ; GFX81:       ; %bb.0: ; %main_body
-; GFX81-NEXT:    image_gather4_lz v[0:1], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
+; GFX81-NEXT:    image_gather4_lz v[0:3], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
 ; GFX81-NEXT:    s_waitcnt vmcnt(0)
 ; GFX81-NEXT:    ; return to shader part epilog
 ;
 ; GFX9-LABEL: image_gather4_lz_2d_v4f16:
 ; GFX9:       ; %bb.0: ; %main_body
-; GFX9-NEXT:    image_gather4_lz v[0:1], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
+; GFX9-NEXT:    image_gather4_lz v[0:3], v[0:1], s[0:7], s[8:11] dmask:0x1 d16
 ; GFX9-NEXT:    s_waitcnt vmcnt(0)
 ; GFX9-NEXT:    ; return to shader part epilog
 ;
diff --git a/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll
index 932bd8930b20f..cdae06c1fb914 100644
--- a/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll
+++ b/llvm/test/CodeGen/AMDGPU/GlobalISel/llvm.amdgcn.image.gather4.d16.tfe.dim.ll
@@ -34,8 +34,8 @@ define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16_tfe(<8 x i32> inreg %rsr
 ; GFX81-NEXT:    v_mov_b32_e32 v6, v2
 ; GFX81-NEXT:    v_mov_b32_e32 v1, v0
 ; GFX81-NEXT:    v_mov_b32_e32 v2, v0
-; GFX81-NEXT:    image_gather4_lz v[0:2], v[4:5], s[0:7], s[8:11] dmask:0x1 tfe d16
 ; GFX81-NEXT:    v_mov_b32_e32 v7, v3
+; GFX81-NEXT:    image_gather4_lz v[0:4], v[4:5], s[0:7], s[8:11] dmask:0x1 tfe d16
 ; GFX81-NEXT:    s_waitcnt vmcnt(0)
 ; GFX81-NEXT:    flat_store_dword v[6:7], v2
 ; GFX81-NEXT:    s_waitcnt vmcnt(0)
@@ -49,8 +49,8 @@ define amdgpu_ps <2 x float> @image_gather4_lz_2d_v4f16_tfe(<8 x i32> inreg %rsr
 ; GFX9-NEXT:    v_mov_b32_e32 v6, v2
 ; GFX9-NEXT:    v_mov_b32_e32 v1, v0
 ; GFX9-NEXT:    v_mov_b32_e32 v2, v0
-; GFX9-NEXT:    image_gather4_lz v[0:2], v[4:5], s[0:7], s[8:11] dmask:0x1 tfe d16
 ; GFX9-NEXT:    v_mov_b32_e32 v7, v3
+; GFX9-NEXT:    image_gather4_lz v[0:4], v[4:5], s[0:7], s[8:11] dmask:0x1 tfe d16
 ; GFX9-NEXT:    s_waitcnt vmcnt(0)
 ; GFX9-NEXT:    global_store_dword v[6:7], v2, off
 ; GFX9-NEXT:    s_waitcnt vmcnt(0)



More information about the llvm-commits mailing list