[llvm] 242647e - AMDGPU: Only disassemble .amdhsa_reserve_xnack_mask on xnack targets (#212789)
via llvm-commits
llvm-commits at lists.llvm.org
Thu Aug 20 09:01:30 PDT 2026
Author: Matt Arsenault
Date: 2026-08-20T18:01:23+02:00
New Revision: 242647e188e8cfa410fa9604b97c748b47210d3b
URL: https://github.com/llvm/llvm-project/commit/242647e188e8cfa410fa9604b97c748b47210d3b
DIFF: https://github.com/llvm/llvm-project/commit/242647e188e8cfa410fa9604b97c748b47210d3b.diff
LOG: AMDGPU: Only disassemble .amdhsa_reserve_xnack_mask on xnack targets (#212789)
The disassembler unconditionally printed .amdhsa_reserve_xnack_mask when
emitting a kernel descriptor. Targets that do not support xnack have no
xnack mask to reserve, and the assembler streamer already only emits the
directive when the subtarget supports xnack. Match that behavior in the
disassembler so the round-trip is consistent and gfx11/gfx12 descriptors
no longer carry a spurious directive.
As a guard against a malformed binary, if the object's ELF e_flags
erroneously select xnack "on" for a target that does not support xnack,
still print the directive so the invalid state remains visible in the
disassembly rather than being silently dropped.
Co-authored-by: Claude (Opus 4.8) <noreply at anthropic.com>
Added:
llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-xnack-unsupported-eflags.yaml
Modified:
llvm/lib/Target/AMDGPU/Disassembler/AMDGPUDisassembler.cpp
llvm/lib/Target/AMDGPU/Disassembler/AMDGPUDisassembler.h
llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-gfx11.s
llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-gfx12.s
Removed:
################################################################################
diff --git a/llvm/lib/Target/AMDGPU/Disassembler/AMDGPUDisassembler.cpp b/llvm/lib/Target/AMDGPU/Disassembler/AMDGPUDisassembler.cpp
index 40e8c58839879..45c1350c146da 100644
--- a/llvm/lib/Target/AMDGPU/Disassembler/AMDGPUDisassembler.cpp
+++ b/llvm/lib/Target/AMDGPU/Disassembler/AMDGPUDisassembler.cpp
@@ -123,6 +123,7 @@ void AMDGPUDisassembler::emitTargetIDIfSupported(raw_ostream &OS,
break;
case ELF::EF_AMDGPU_FEATURE_XNACK_ON_V4:
OS << ":xnack+";
+ XnackOnFromEFlags = true;
break;
}
}
@@ -2572,10 +2573,15 @@ Expected<bool> AMDGPUDisassembler::decodeCOMPUTE_PGM_RSRC1(
KdStream << Indent << ".amdhsa_reserve_vcc " << 0 << '\n';
if (!hasArchitectedFlatScratch())
KdStream << Indent << ".amdhsa_reserve_flat_scratch " << 0 << '\n';
- bool ReservedXnackMask = STI.hasFeature(AMDGPU::FeatureXNACK);
- assert(!ReservedXnackMask || STI.hasFeature(AMDGPU::FeatureSupportsXNACK));
- KdStream << Indent << ".amdhsa_reserve_xnack_mask " << ReservedXnackMask
- << '\n';
+ // Only print the directive on xnack-supporting targets (matching the
+ // asmprinter), unless the binary erronously set xnack on an unsupported
+ // target
+ bool ReservedXnackMask =
+ STI.hasFeature(AMDGPU::FeatureXNACK) || XnackOnFromEFlags;
+ if (STI.hasFeature(AMDGPU::FeatureSupportsXNACK) || ReservedXnackMask) {
+ KdStream << Indent << ".amdhsa_reserve_xnack_mask " << ReservedXnackMask
+ << '\n';
+ }
KdStream << Indent << ".amdhsa_next_free_sgpr " << NextFreeSGPR << "\n";
CHECK_RESERVED_BITS(COMPUTE_PGM_RSRC1_PRIORITY);
diff --git a/llvm/lib/Target/AMDGPU/Disassembler/AMDGPUDisassembler.h b/llvm/lib/Target/AMDGPU/Disassembler/AMDGPUDisassembler.h
index da6bd45485606..8cdd1dec844e1 100644
--- a/llvm/lib/Target/AMDGPU/Disassembler/AMDGPUDisassembler.h
+++ b/llvm/lib/Target/AMDGPU/Disassembler/AMDGPUDisassembler.h
@@ -47,6 +47,9 @@ class AMDGPUDisassembler : public MCDisassembler {
mutable uint64_t Literal;
mutable bool HasLiteral;
mutable std::optional<bool> EnableWavefrontSize32;
+
+ // If the object's ELF e_flags enable xnack. TODO: Replace with TargetID
+ mutable bool XnackOnFromEFlags = false;
unsigned CodeObjectVersion;
const MCExpr *UCVersionW64Expr;
const MCExpr *UCVersionW32Expr;
diff --git a/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-gfx11.s b/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-gfx11.s
index 8e81fb41e6869..a7a04fbc8cf89 100644
--- a/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-gfx11.s
+++ b/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-gfx11.s
@@ -19,7 +19,6 @@
; CHECK-NEXT: ; IMAGE_OP 0
; CHECK-NEXT: .amdhsa_next_free_vgpr 32
; CHECK-NEXT: .amdhsa_reserve_vcc 0
-; CHECK-NEXT: .amdhsa_reserve_xnack_mask 0
; CHECK-NEXT: .amdhsa_next_free_sgpr 8
; CHECK-NEXT: .amdhsa_float_round_mode_32 0
; CHECK-NEXT: .amdhsa_float_round_mode_16_64 0
@@ -76,7 +75,6 @@
; CHECK-NEXT: ; IMAGE_OP 0
; CHECK-NEXT: .amdhsa_next_free_vgpr 32
; CHECK-NEXT: .amdhsa_reserve_vcc 0
-; CHECK-NEXT: .amdhsa_reserve_xnack_mask 0
; CHECK-NEXT: .amdhsa_next_free_sgpr 8
; CHECK-NEXT: .amdhsa_float_round_mode_32 0
; CHECK-NEXT: .amdhsa_float_round_mode_16_64 0
@@ -134,7 +132,6 @@
; CHECK-NEXT: ; IMAGE_OP 0
; CHECK-NEXT: .amdhsa_next_free_vgpr 32
; CHECK-NEXT: .amdhsa_reserve_vcc 0
-; CHECK-NEXT: .amdhsa_reserve_xnack_mask 0
; CHECK-NEXT: .amdhsa_next_free_sgpr 8
; CHECK-NEXT: .amdhsa_float_round_mode_32 0
; CHECK-NEXT: .amdhsa_float_round_mode_16_64 0
@@ -192,7 +189,6 @@
; CHECK-NEXT: ; IMAGE_OP 0
; CHECK-NEXT: .amdhsa_next_free_vgpr 32
; CHECK-NEXT: .amdhsa_reserve_vcc 0
-; CHECK-NEXT: .amdhsa_reserve_xnack_mask 0
; CHECK-NEXT: .amdhsa_next_free_sgpr 8
; CHECK-NEXT: .amdhsa_float_round_mode_32 0
; CHECK-NEXT: .amdhsa_float_round_mode_16_64 0
diff --git a/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-gfx12.s b/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-gfx12.s
index 71d74d0813fad..42f905cf49cf7 100644
--- a/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-gfx12.s
+++ b/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-gfx12.s
@@ -17,7 +17,6 @@
; CHECK-NEXT: ; IMAGE_OP 0
; CHECK-NEXT: .amdhsa_next_free_vgpr 32
; CHECK-NEXT: .amdhsa_reserve_vcc 0
-; CHECK-NEXT: .amdhsa_reserve_xnack_mask 0
; CHECK-NEXT: .amdhsa_next_free_sgpr 8
; CHECK-NEXT: .amdhsa_float_round_mode_32 0
; CHECK-NEXT: .amdhsa_float_round_mode_16_64 0
@@ -71,7 +70,6 @@
; CHECK-NEXT: ; IMAGE_OP 0
; CHECK-NEXT: .amdhsa_next_free_vgpr 32
; CHECK-NEXT: .amdhsa_reserve_vcc 0
-; CHECK-NEXT: .amdhsa_reserve_xnack_mask 0
; CHECK-NEXT: .amdhsa_next_free_sgpr 8
; CHECK-NEXT: .amdhsa_float_round_mode_32 0
; CHECK-NEXT: .amdhsa_float_round_mode_16_64 0
diff --git a/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-xnack-unsupported-eflags.yaml b/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-xnack-unsupported-eflags.yaml
new file mode 100644
index 0000000000000..311daa0ffc255
--- /dev/null
+++ b/llvm/test/tools/llvm-objdump/ELF/AMDGPU/kd-xnack-unsupported-eflags.yaml
@@ -0,0 +1,55 @@
+# Test that the disassembler surfaces .amdhsa_reserve_xnack_mask when an
+# object's ELF e_flags erroneously select xnack "on" for a target that does not
+# support xnack (gfx1200). The directive is normally suppressed for such
+# targets, but must be printed here so the invalid state remains visible.
+
+# RUN: yaml2obj %s -o %t.o
+# RUN: llvm-objdump --disassemble-symbols=kernel.kd %t.o | FileCheck %s
+
+# CHECK: .amdgcn_target "amdgpu-amd-amdhsa-unknown-gfx1200:xnack+"
+# CHECK: .amdhsa_kernel kernel
+# CHECK: .amdhsa_reserve_xnack_mask 1
+
+--- !ELF
+FileHeader:
+ Class: ELFCLASS64
+ Data: ELFDATA2LSB
+ OSABI: ELFOSABI_AMDGPU_HSA
+ ABIVersion: 0x3
+ Type: ET_REL
+ Machine: EM_AMDGPU
+ Flags: [ EF_AMDGPU_MACH_AMDGCN_GFX1200, EF_AMDGPU_FEATURE_XNACK_ON_V4, EF_AMDGPU_FEATURE_SRAMECC_UNSUPPORTED_V4 ]
+ SectionHeaderStringTable: .strtab
+Sections:
+ - Name: .text
+ Type: SHT_PROGBITS
+ Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
+ AddressAlign: 0x4
+ Content: 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000CE0800000000004000000000000
+ - Name: .rela.text
+ Type: SHT_RELA
+ Flags: [ SHF_INFO_LINK ]
+ Link: .symtab
+ AddressAlign: 0x8
+ Info: .text
+ Relocations:
+ - Offset: 0x10
+ Symbol: kernel
+ Type: R_AMDGPU_REL64
+ Addend: 16
+ - Type: SectionHeaderTable
+ Sections:
+ - Name: .strtab
+ - Name: .text
+ - Name: .rela.text
+ - Name: .symtab
+Symbols:
+ - Name: kernel.kd
+ Type: STT_OBJECT
+ Section: .text
+ Binding: STB_GLOBAL
+ Size: 0x40
+ - Name: kernel
+ Binding: STB_GLOBAL
+ Other: [ STV_PROTECTED ]
+...
More information about the llvm-commits
mailing list