Skip to content

Commit 6c8fd97

Browse files
committed
AMDGPU: Add first gfx950 mfma instructions
Scheduling info and hazards are wrong and TBD.
1 parent f2f273d commit 6c8fd97

File tree

16 files changed

+592
-3
lines changed

16 files changed

+592
-3
lines changed

clang/include/clang/Basic/BuiltinsAMDGPU.def

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -431,6 +431,12 @@ TARGET_BUILTIN(__builtin_amdgcn_cvt_pk_fp8_f32, "iffiIb", "nc", "fp8-conversion-
431431
TARGET_BUILTIN(__builtin_amdgcn_cvt_sr_bf8_f32, "ifiiIi", "nc", "fp8-conversion-insts")
432432
TARGET_BUILTIN(__builtin_amdgcn_cvt_sr_fp8_f32, "ifiiIi", "nc", "fp8-conversion-insts")
433433

434+
//===----------------------------------------------------------------------===//
435+
// GFX950 only builtins.
436+
//===----------------------------------------------------------------------===//
437+
TARGET_BUILTIN(__builtin_amdgcn_mfma_f32_16x16x32_f16, "V4fV8hV8hV4fIiIiIi", "nc", "gfx950-insts")
438+
TARGET_BUILTIN(__builtin_amdgcn_mfma_f32_32x32x16_f16, "V16fV8hV8hV16fIiIiIi", "nc", "gfx950-insts")
439+
434440
//===----------------------------------------------------------------------===//
435441
// GFX12+ only builtins.
436442
//===----------------------------------------------------------------------===//

clang/test/CodeGenOpenCL/builtins-amdgcn-mfma.cl

Lines changed: 23 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
// RUN: %clang_cc1 -triple amdgcn-unknown-unknown -target-cpu gfx908 -DMFMA_GFX908_TESTS -emit-llvm -o - %s | FileCheck %s --check-prefix=CHECK-GFX908
33
// RUN: %clang_cc1 -triple amdgcn-unknown-unknown -target-cpu gfx90a -DMFMA_GFX90A_TESTS -emit-llvm -o - %s | FileCheck %s --check-prefix=CHECK-GFX90A
44
// RUN: %clang_cc1 -triple amdgcn-unknown-unknown -target-cpu gfx940 -DMFMA_GFX940_TESTS -emit-llvm -o - %s | FileCheck %s --check-prefix=CHECK-GFX940
5+
// RUN: %clang_cc1 -triple amdgcn-unknown-unknown -target-cpu gfx950 -DMFMA_GFX950_TESTS -emit-llvm -o - %s | FileCheck %s --check-prefix=CHECK-GFX950
56

67
#pragma OPENCL EXTENSION cl_khr_fp64:enable
78

@@ -222,7 +223,7 @@ void test_mfma_f64_4x4x4f64(global double* out, double a, double b, double c)
222223

223224
#endif // MFMA_GFX90A_TESTS
224225

225-
#ifdef MFMA_GFX940_TESTS
226+
#if defined(MFMA_GFX940_TESTS) || defined(MFMA_GFX950_TESTS)
226227
// CHECK-GFX940-LABEL: @test_mfma_i32_16x16x32_i8
227228
// CHECK-GFX940: call <4 x i32> @llvm.amdgcn.mfma.i32.16x16x32.i8(i64 %a, i64 %b, <4 x i32> %c, i32 0, i32 0, i32 0)
228229
void test_mfma_i32_16x16x32_i8(global v4i* out, long a, long b, v4i c)
@@ -404,4 +405,24 @@ void test_smfmac_f32_32x32x32_fp8_fp8(global v16f* out, v2i a, v4i b, v16f c, in
404405
{
405406
*out = __builtin_amdgcn_smfmac_f32_32x32x32_fp8_fp8(a, b, c, idx, 0, 0);
406407
}
407-
#endif // MFMA_GFX940_TESTS
408+
#endif // defined(MFMA_GFX940_TESTS) || defined(MFMA_GFX950_TESTS)
409+
410+
#ifdef MFMA_GFX950_TESTS
411+
412+
// CHECK-GFX950-LABEL: @test_mfma_f32_16x16x32_f16(
413+
// CHECK-GFX950: tail call <4 x float> @llvm.amdgcn.mfma.f32.16x16x32.f16(<8 x half> %a, <8 x half> %b, <4 x float> %c, i32 1, i32 2, i32 3)
414+
415+
v4f test_mfma_f32_16x16x32_f16(v8h a, v8h b, v4f c)
416+
{
417+
return __builtin_amdgcn_mfma_f32_16x16x32_f16(a, b, c, 1, 2, 3);
418+
}
419+
420+
// CHECK-GFX950-LABEL: @test_mfma_f32_32x32x16_f16
421+
// CHECK-GFX950: tail call <16 x float> @llvm.amdgcn.mfma.f32.32x32x16.f16(<8 x half> %a, <8 x half> %b, <16 x float> %c, i32 1, i32 2, i32 3)
422+
v16f test_mfma_f32_32x32x16_f16(v8h a, v8h b, v16f c)
423+
{
424+
return __builtin_amdgcn_mfma_f32_32x32x16_f16(a, b, c, 1, 2, 3);
425+
}
426+
427+
428+
#endif
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
// REQUIRES: amdgpu-registered-target
2+
// RUN: %clang_cc1 -triple amdgcn-- -target-cpu gfx950 -verify -S -o - %s
3+
4+
typedef float float4 __attribute__((ext_vector_type(4)));
5+
typedef float float16 __attribute__((ext_vector_type(16)));
6+
typedef half half8 __attribute__((ext_vector_type(8)));
7+
8+
9+
void test_mfma_f32_16x16x32_f16(__global float4* out, half8 a, half8 b, float4 c, int X) {
10+
11+
*out = __builtin_amdgcn_mfma_f32_16x16x32_f16(a, b, c, X, 0, 0); // expected-error{{argument to '__builtin_amdgcn_mfma_f32_16x16x32_f16' must be a constant integer}}
12+
*out = __builtin_amdgcn_mfma_f32_16x16x32_f16(a, b, c, 0, X, 0); // expected-error{{argument to '__builtin_amdgcn_mfma_f32_16x16x32_f16' must be a constant integer}}
13+
*out = __builtin_amdgcn_mfma_f32_16x16x32_f16(a, b, c, 0, 0, X); // expected-error{{argument to '__builtin_amdgcn_mfma_f32_16x16x32_f16' must be a constant integer}}
14+
}
15+
16+
17+
void test_mfma_f32_32x32x16_f16(__global float16* out, half8 a, half8 b, float16 c, int X) {
18+
*out = __builtin_amdgcn_mfma_f32_32x32x16_f16(a, b, c, X, 0, 0); // expected-error{{argument to '__builtin_amdgcn_mfma_f32_32x32x16_f16' must be a constant integer}}
19+
*out = __builtin_amdgcn_mfma_f32_32x32x16_f16(a, b, c, 0, X, 0); // expected-error{{argument to '__builtin_amdgcn_mfma_f32_32x32x16_f16' must be a constant integer}}
20+
*out = __builtin_amdgcn_mfma_f32_32x32x16_f16(a, b, c, 0, 0, X); // expected-error{{argument to '__builtin_amdgcn_mfma_f32_32x32x16_f16' must be a constant integer}}
21+
}
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
// REQUIRES: amdgpu-registered-target
2+
// RUN: %clang_cc1 -triple amdgcn-- -target-cpu gfx940 -verify -S -o - %s
3+
4+
typedef float float4 __attribute__((ext_vector_type(4)));
5+
typedef float float16 __attribute__((ext_vector_type(16)));
6+
typedef half half8 __attribute__((ext_vector_type(8)));
7+
8+
void test(__global float4* out0, half8 a0, half8 b0, float4 c0,
9+
__global float16* out1, half8 a1, half8 b1, float16 c1) {
10+
*out0 = __builtin_amdgcn_mfma_f32_16x16x32_f16(a0, b0, c0, 0, 0, 0); // expected-error{{'__builtin_amdgcn_mfma_f32_16x16x32_f16' needs target feature gfx950-insts}}
11+
*out1 = __builtin_amdgcn_mfma_f32_32x32x16_f16(a1, b1, c1, 0, 0, 0); // expected-error{{'__builtin_amdgcn_mfma_f32_32x32x16_f16' needs target feature gfx950-insts}}
12+
}

llvm/include/llvm/IR/IntrinsicsAMDGPU.td

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3110,6 +3110,15 @@ def int_amdgcn_cvt_sr_fp8_f32 : ClangBuiltin<"__builtin_amdgcn_cvt_sr_fp8_f32">,
31103110
[llvm_float_ty, llvm_i32_ty, llvm_i32_ty, llvm_i32_ty],
31113111
[IntrNoMem, ImmArg<ArgIndex<3>>]>;
31123112

3113+
//===----------------------------------------------------------------------===//
3114+
// gfx950 intrinsics
3115+
//===----------------------------------------------------------------------===//
3116+
3117+
defset list<Intrinsic> AMDGPUMFMAIntrinsics950 = {
3118+
def int_amdgcn_mfma_f32_16x16x32_f16 : AMDGPUMfmaIntrinsic<llvm_v4f32_ty, llvm_v8f16_ty>;
3119+
def int_amdgcn_mfma_f32_32x32x16_f16 : AMDGPUMfmaIntrinsic<llvm_v16f32_ty, llvm_v8f16_ty>;
3120+
}
3121+
31133122
//===----------------------------------------------------------------------===//
31143123
// Special Intrinsics for backend internal use only. No frontend
31153124
// should emit calls to these.

llvm/lib/Target/AMDGPU/AMDGPU.td

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1983,6 +1983,10 @@ def isNotGFX940Plus :
19831983
Predicate<"!Subtarget->hasGFX940Insts()">,
19841984
AssemblerPredicate<(all_of (not FeatureGFX940Insts))>;
19851985

1986+
def HasGFX950Insts :
1987+
Predicate<"Subtarget->hasGFX950Insts()">,
1988+
AssemblerPredicate<(all_of FeatureGFX950Insts)>;
1989+
19861990
def isGFX8GFX9NotGFX940 :
19871991
Predicate<"!Subtarget->hasGFX940Insts() &&"
19881992
"(Subtarget->getGeneration() == AMDGPUSubtarget::VOLCANIC_ISLANDS ||"

llvm/lib/Target/AMDGPU/AMDGPURegisterBankInfo.cpp

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4747,7 +4747,9 @@ AMDGPURegisterBankInfo::getInstrMapping(const MachineInstr &MI) const {
47474747
case Intrinsic::amdgcn_mfma_f32_32x32x16_bf8_bf8:
47484748
case Intrinsic::amdgcn_mfma_f32_32x32x16_bf8_fp8:
47494749
case Intrinsic::amdgcn_mfma_f32_32x32x16_fp8_bf8:
4750-
case Intrinsic::amdgcn_mfma_f32_32x32x16_fp8_fp8: {
4750+
case Intrinsic::amdgcn_mfma_f32_32x32x16_fp8_fp8:
4751+
case Intrinsic::amdgcn_mfma_f32_16x16x32_f16:
4752+
case Intrinsic::amdgcn_mfma_f32_32x32x16_f16: {
47514753
// Default for MAI intrinsics.
47524754
// srcC can also be an immediate which can be folded later.
47534755
// FIXME: Should we eventually add an alternative mapping with AGPR src

llvm/lib/Target/AMDGPU/AMDGPUSearchableTables.td

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -333,6 +333,8 @@ foreach intr = AMDGPUMFMAIntrinsics90A in
333333
def : SourceOfDivergence<intr>;
334334
foreach intr = AMDGPUMFMAIntrinsics940 in
335335
def : SourceOfDivergence<intr>;
336+
foreach intr = AMDGPUMFMAIntrinsics950 in
337+
def : SourceOfDivergence<intr>;
336338
foreach intr = AMDGPUWMMAIntrinsicsGFX11 in
337339
def : SourceOfDivergence<intr>;
338340
foreach intr = AMDGPUWMMAIntrinsicsGFX12 in

llvm/lib/Target/AMDGPU/GCNSubtarget.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1285,6 +1285,10 @@ class GCNSubtarget final : public AMDGPUGenSubtargetInfo,
12851285
// hasGFX90AInsts is also true.
12861286
bool hasGFX940Insts() const { return GFX940Insts; }
12871287

1288+
// GFX950 is a derivation to GFX940. hasGFX950Insts() implies that
1289+
// hasGFX940Insts and hasGFX90AInsts are also true.
1290+
bool hasGFX950Insts() const { return GFX950Insts; }
1291+
12881292
bool hasSALUFloatInsts() const { return HasSALUFloatInsts; }
12891293

12901294
bool hasPseudoScalarTrans() const { return HasPseudoScalarTrans; }

llvm/lib/Target/AMDGPU/SIInstrInfo.td

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2845,6 +2845,10 @@ def VOP_V16I32_V2I32_V4I32_I32 : VOPProfile <[v16i32, v2i32, v4i32, i32]>;
28452845
def VOP_V4F32_V2I32_V4I32_I32 : VOPProfile <[v4f32, v2i32, v4i32, i32]>;
28462846
def VOP_V16F32_V2I32_V4I32_I32 : VOPProfile <[v16f32, v2i32, v4i32, i32]>;
28472847

2848+
def VOP_V4F32_V8F16_V8F16_V4F32 : VOPProfile <[v4f32, v8f16, v8f16, v4f32]>;
2849+
def VOP_V16F32_V8F16_V8F16_V16F32 : VOPProfile <[v16f32, v8f16, v8f16, v16f32]>;
2850+
2851+
28482852
class Commutable_REV <string revOp, bit isOrig> {
28492853
string RevOp = revOp;
28502854
bit IsOrig = isOrig;

llvm/lib/Target/AMDGPU/VOP3PInstructions.td

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -626,6 +626,11 @@ def VOPProfileSMFMAC_I32_32X32X32_I8 : VOPProfileSMFMAC<VOP_V16I32_V2I32_V4I32_
626626
def VOPProfileSMFMAC_F32_16X16X64_F8 : VOPProfileSMFMAC<VOP_V4F32_V2I32_V4I32_I32, AVDst_128, AVSrc_64, AVSrc_128>;
627627
def VOPProfileSMFMAC_F32_32X32X32_F8 : VOPProfileSMFMAC<VOP_V16F32_V2I32_V4I32_I32, AVDst_512, AVSrc_64, AVSrc_128>;
628628

629+
def VOPProfileMAI_F32_V8F16_X32 : VOPProfileMAI<VOP_V4F32_V8F16_V8F16_V4F32, AISrc_128_f32, ADst_128, AVSrc_128>;
630+
def VOPProfileMAI_F32_V8F16_X32_VCD : VOPProfileMAI<VOP_V4F32_V8F16_V8F16_V4F32, VISrc_128_f32, VDst_128, AVSrc_128>;
631+
def VOPProfileMAI_F32_V8F16_X16 : VOPProfileMAI<VOP_V16F32_V8F16_V8F16_V16F32, AISrc_512_f32, ADst_512, AVSrc_128>;
632+
def VOPProfileMAI_F32_V8F16_X16_VCD : VOPProfileMAI<VOP_V16F32_V8F16_V8F16_V16F32, VISrc_512_f32, VDst_512, AVSrc_128>;
633+
629634
class MFMATable <bit is_mac, string Name> {
630635
bit IsMac = is_mac;
631636
string FMAOp = Name;
@@ -739,6 +744,11 @@ defm V_MFMA_F32_32X32X4BF16 : MAIInst<"v_mfma_f32_32x32x4bf16", "F32_V2I16_X16",
739744

740745
} // End SubtargetPredicate = HasMAIInsts
741746

747+
let SubtargetPredicate = HasGFX950Insts, is_gfx940_xdl = 1 in {
748+
defm V_MFMA_F32_16X16X32_F16 : MAIInst<"v_mfma_f32_16x16x32f16", "F32_V8F16_X32", int_amdgcn_mfma_f32_16x16x32_f16>;
749+
defm V_MFMA_F32_32X32X16_F16 : MAIInst<"v_mfma_f32_32x32x16f16", "F32_V8F16_X16", int_amdgcn_mfma_f32_32x32x16_f16>;
750+
}
751+
742752
let Predicates = [isGFX90APlus] in {
743753
let is_gfx940_xdl = 1 in {
744754
defm V_MFMA_F32_32X32X4BF16_1K : MAIInst<"v_mfma_f32_32x32x4bf16_1k", "F32_V4I16_X32", int_amdgcn_mfma_f32_32x32x4bf16_1k>;
@@ -1650,6 +1660,16 @@ multiclass VOP3P_Real_MFMA_gfx940<bits<7> op, string Name = !cast<VOP3_Pseudo>(N
16501660
}
16511661
}
16521662

1663+
multiclass VOP3P_Real_MFMA_gfx950<bits<7> op, string Name = !cast<VOP3_Pseudo>(NAME#"_e64").Mnemonic,
1664+
VOP3_Pseudo PS_ACD = !cast<VOP3_Pseudo>(NAME # "_e64"),
1665+
VOP3_Pseudo PS_VCD = !cast<VOP3_Pseudo>(NAME # "_vgprcd" # "_e64")> {
1666+
let SubtargetPredicate = HasGFX950Insts,
1667+
AssemblerPredicate = HasGFX950Insts in {
1668+
defm "" : VOP3P_Real_MFMA_gfx940<op, Name, PS_ACD, PS_VCD>;
1669+
}
1670+
}
1671+
1672+
16531673
multiclass VOP3P_Real_MFMA_vi<bits<7> op> {
16541674
def _vi : VOP3P_Real<!cast<VOP3_Pseudo>(NAME#"_e64"), SIEncodingFamily.VI>,
16551675
VOP3Pe_MAI <op, !cast<VOP3_Pseudo>(NAME#"_e64").Pfl, ?> {
@@ -1764,6 +1784,8 @@ defm V_MFMA_F32_16X16X16BF16_1K : VOP3P_Real_MFMA_gfx90a <0x67>;
17641784
defm V_MFMA_F64_16X16X4F64 : VOP3P_Real_MFMA_gfx90a <0x6e>;
17651785
defm V_MFMA_F64_4X4X4F64 : VOP3P_Real_MFMA_gfx90a <0x6f>;
17661786

1787+
defm V_MFMA_F32_16X16X32_F16 : VOP3P_Real_MFMA_gfx950 <0x54, "v_mfma_f32_16x16x32_f16">;
1788+
defm V_MFMA_F32_32X32X16_F16 : VOP3P_Real_MFMA_gfx950 <0x55, "v_mfma_f32_32x32x16_f16">;
17671789
defm V_MFMA_I32_32X32X16I8 : VOP3P_Real_MFMA_gfx940 <0x56, "v_mfma_i32_32x32x16_i8">;
17681790
defm V_MFMA_I32_16X16X32I8 : VOP3P_Real_MFMA_gfx940 <0x57, "v_mfma_i32_16x16x32_i8">;
17691791
let SubtargetPredicate = HasXF32Insts in {

llvm/test/Analysis/UniformityAnalysis/AMDGPU/intrinsics.ll

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -261,6 +261,23 @@ bb:
261261
ret void
262262
}
263263

264+
declare <4 x float> @llvm.amdgcn.mfma.f32.16x16x32.f16(<8 x half>, <8 x half>, <4 x float>, i32 immarg, i32 immarg, i32 immarg)
265+
declare <16 x float> @llvm.amdgcn.mfma.f32.32x32x16.f16(<8 x half>, <8 x half>, <16 x float>, i32 immarg, i32 immarg, i32 immarg)
266+
267+
; CHECK: DIVERGENT: %result = call <4 x float> @llvm.amdgcn.mfma.f32.16x16x32.f16(<8 x half> %arg0, <8 x half> %arg1, <4 x float> %arg2, i32 immarg 0, i32 immarg 0, i32 immarg 0)
268+
define amdgpu_kernel void @mfma_f32_16x16x32_f16(<8 x half> %arg0, <8 x half> %arg1, <4 x float> %arg2, ptr addrspace(1) %out) {
269+
%result = call <4 x float> @llvm.amdgcn.mfma.f32.16x16x32.f16(<8 x half> %arg0, <8 x half> %arg1, <4 x float> %arg2, i32 immarg 0, i32 immarg 0, i32 immarg 0)
270+
store <4 x float> %result, ptr addrspace(1) %out
271+
ret void
272+
}
273+
274+
; CHECK: DIVERGENT: %result = call <16 x float> @llvm.amdgcn.mfma.f32.32x32x16.f16(<8 x half> %arg0, <8 x half> %arg1, <16 x float> %arg2, i32 immarg 0, i32 immarg 0, i32 immarg 0)
275+
define amdgpu_kernel void @mfma_f32_32x32x16_f16(<8 x half> %arg0, <8 x half> %arg1, <16 x float> %arg2, ptr addrspace(1) %out) {
276+
%result = call <16 x float> @llvm.amdgcn.mfma.f32.32x32x16.f16(<8 x half> %arg0, <8 x half> %arg1, <16 x float> %arg2, i32 immarg 0, i32 immarg 0, i32 immarg 0)
277+
store <16 x float> %result, ptr addrspace(1) %out
278+
ret void
279+
}
280+
264281
declare i32 @llvm.amdgcn.ds.swizzle(i32, i32) #1
265282
declare i32 @llvm.amdgcn.permlane16.i32(i32, i32, i32, i32, i1, i1) #1
266283
declare i32 @llvm.amdgcn.permlanex16.i32(i32, i32, i32, i32, i1, i1) #1

0 commit comments

Comments
 (0)