This add experimental support for AMD Instinct MI300. It has been tested to support hello world, but not yet much beyond (to come).
OK for mainline? Tobias
gcn: Add experimental MI300 (gfx942) support As gfx942 and gfx950 belong to gfx9-4-generic, the latter two are also added. Note that there are no specific optimizations for MI300, yet. For none of the mentioned devices, any multilib is build by default; use '--with-multilib-list=' when configuring GCC to build them alongside. gfx942 was added in LLVM (and its mc assembler, used by GCC) in version 18, generic support in LLVM 19 and gfx950 in LLVM 20. gcc/ChangeLog: * config/gcn/gcn-devices.def: Add gfx942, gfx950 and gfx9-4-generic. * config/gcn/gcn-opts.h (TARGET_CDNA3, TARGET_CDNA3_PLUS, TARGET_GLC_NAME, TARGET_TARGET_SC_CACHE): Define. (TARGET_ARCHITECTED_FLAT_SCRATCH): Use also for CDNA3. * config/gcn/gcn.h (gcn_isa): Add ISA_CDNA3 to the enum. * config/gcn/gcn.cc (print_operand): Update 'g' to use TARGET_GLC_NAME; add 'G' to print TARGET_GLC_NAME unconditionally. * config/gcn/gcn-valu.md (scatter, gather): Use TARGET_GLC_NAME. * config/gcn/gcn.md: Use %G<num> instead of glc; use 'buffer_inv sc1' for TARGET_TARGET_SC_CACHE. * doc/invoke.texi (march): Add gfx942, gfx950 and gfx9-4-generic. * doc/install.texi (amdgcn*-*-*): Add gfx942, gfx950 and gfx9-4-generic. * config/gcn/gcn-tables.opt: Regenerate. libgomp/ChangeLog: * testsuite/libgomp.c/declare-variant-4.h (gfx942): New variant function. * testsuite/libgomp.c/declare-variant-4-gfx942.c: New test. gcc/config/gcn/gcn-devices.def | 33 ++++ gcc/config/gcn/gcn-opts.h | 13 +- gcc/config/gcn/gcn-tables.opt | 9 ++ gcc/config/gcn/gcn-valu.md | 8 +- gcc/config/gcn/gcn.cc | 8 +- gcc/config/gcn/gcn.h | 2 + gcc/config/gcn/gcn.md | 168 +++++++++++++-------- gcc/doc/install.texi | 17 ++- gcc/doc/invoke.texi | 10 ++ .../testsuite/libgomp.c/declare-variant-4-gfx942.c | 8 + libgomp/testsuite/libgomp.c/declare-variant-4.h | 8 + 11 files changed, 208 insertions(+), 76 deletions(-) diff --git a/gcc/config/gcn/gcn-devices.def b/gcc/config/gcn/gcn-devices.def index af1420382e2..426acf0cb7a 100644 --- a/gcc/config/gcn/gcn-devices.def +++ b/gcc/config/gcn/gcn-devices.def @@ -171,6 +171,28 @@ GCN_DEVICE(gfx90c, GFX90C, 0x32, ISA_GCN5, /* Generic Name */ GFX9_GENERIC ) +GCN_DEVICE(gfx942, GFX942, 0x4c, ISA_CDNA3, + /* XNACK default */ HSACO_ATTR_ANY, + /* SRAM_ECC default */ HSACO_ATTR_ANY, + /* WAVE64 mode */ HSACO_ATTR_UNSUPPORTED, + /* CU mode */ HSACO_ATTR_UNSUPPORTED, + /* Max ISA VGPRs */ 512, + /* Generic code obj version */ 0, /* non-generic */ + /* Architecture Family */ GFX9, + /* Generic Name */ NONE + ) + +GCN_DEVICE(gfx950, GFX950, 0x4f, ISA_CDNA3, + /* XNACK default */ HSACO_ATTR_ANY, + /* SRAM_ECC default */ HSACO_ATTR_ANY, + /* WAVE64 mode */ HSACO_ATTR_UNSUPPORTED, + /* CU mode */ HSACO_ATTR_UNSUPPORTED, + /* Max ISA VGPRs */ 512, + /* Generic code obj version */ 0, /* non-generic */ + /* Architecture Family */ GFX9, + /* Generic Name */ NONE + ) + GCN_DEVICE(gfx9-generic, GFX9_GENERIC, 0x051, ISA_GCN5, /* XNACK default */ HSACO_ATTR_ANY, /* SRAM_ECC default */ HSACO_ATTR_UNSUPPORTED, @@ -182,6 +204,17 @@ GCN_DEVICE(gfx9-generic, GFX9_GENERIC, 0x051, ISA_GCN5, /* Generic Name */ NONE ) +GCN_DEVICE(gfx9-4-generic, GFX9_4_GENERIC, 0x05f, ISA_CDNA3, + /* XNACK default */ HSACO_ATTR_ANY, + /* SRAM_ECC default */ HSACO_ATTR_UNSUPPORTED, + /* WAVE64 mode */ HSACO_ATTR_UNSUPPORTED, + /* CU mode */ HSACO_ATTR_UNSUPPORTED, + /* Max ISA VGPRs */ 256, + /* Generic code obj version */ 1, + /* Architecture Family */ GFX9, + /* Generic Name */ NONE + ) + /* GCN GFX10.3 (RDNA 2) */ GCN_DEVICE(gfx1030, GFX1030, 0x36, ISA_RDNA2, diff --git a/gcc/config/gcn/gcn-opts.h b/gcc/config/gcn/gcn-opts.h index 88f562dfc1e..bcea14f3fe7 100644 --- a/gcc/config/gcn/gcn-opts.h +++ b/gcc/config/gcn/gcn-opts.h @@ -33,7 +33,8 @@ extern enum gcn_isa { ISA_RDNA2, ISA_RDNA3, ISA_CDNA1, - ISA_CDNA2 + ISA_CDNA2, + ISA_CDNA3 } gcn_isa; #define TARGET_GCN5 (gcn_isa == ISA_GCN5) @@ -41,6 +42,8 @@ extern enum gcn_isa { #define TARGET_CDNA1_PLUS (gcn_isa >= ISA_CDNA1) #define TARGET_CDNA2 (gcn_isa == ISA_CDNA2) #define TARGET_CDNA2_PLUS (gcn_isa >= ISA_CDNA2) +#define TARGET_CDNA3 (gcn_isa == ISA_CDNA3) +#define TARGET_CDNA3_PLUS (gcn_isa >= ISA_CDNA3) #define TARGET_RDNA2 (gcn_isa == ISA_RDNA2) #define TARGET_RDNA2_PLUS (gcn_isa >= ISA_RDNA2 && gcn_isa < ISA_CDNA1) #define TARGET_RDNA3 (gcn_isa == ISA_RDNA3) @@ -81,18 +84,22 @@ enum hsaco_attr_type #define TARGET_DPP8 TARGET_RDNA2_PLUS /* Device requires CDNA1-style manually inserted wait states for AVGPRs. */ #define TARGET_AVGPR_CDNA1_NOPS TARGET_CDNA1 +/* Whether to use the 'globally coherent' (glc) or the 'scope' (sc0, sc1) flag + for scalar memory operations. The string starts on purpose with a space. */ +#define TARGET_GLC_NAME (TARGET_CDNA3 ? " sc0" : " glc") /* The metadata on different devices need different granularity. */ #define TARGET_VGPR_GRANULARITY \ (TARGET_RDNA3 ? 12 \ : TARGET_RDNA2_PLUS || TARGET_CDNA2_PLUS ? 8 \ : 4) /* This mostly affects the metadata. */ -#define TARGET_ARCHITECTED_FLAT_SCRATCH TARGET_RDNA3 +#define TARGET_ARCHITECTED_FLAT_SCRATCH (TARGET_RDNA3 || TARGET_CDNA3) /* Device has Sub-DWord Addressing instrucions. */ #define TARGET_SDWA (!TARGET_RDNA3) /* Different devices uses different cache control instructions. */ -#define TARGET_WBINVL1_CACHE (!TARGET_RDNA2_PLUS) +#define TARGET_WBINVL1_CACHE (!TARGET_RDNA2_PLUS && !TARGET_CDNA3) #define TARGET_GLn_CACHE TARGET_RDNA2_PLUS +#define TARGET_TARGET_SC_CACHE TARGET_CDNA3 /* Some devices have TGSPLIT, which needs at least metadata. */ #define TARGET_TGSPLIT TARGET_CDNA2_PLUS diff --git a/gcc/config/gcn/gcn-tables.opt b/gcc/config/gcn/gcn-tables.opt index 96ce9bd2df3..4a381b33b51 100644 --- a/gcc/config/gcn/gcn-tables.opt +++ b/gcc/config/gcn/gcn-tables.opt @@ -48,9 +48,18 @@ Enum(gpu_type) String(gfx90a) Value(PROCESSOR_GFX90A) EnumValue Enum(gpu_type) String(gfx90c) Value(PROCESSOR_GFX90C) +EnumValue +Enum(gpu_type) String(gfx942) Value(PROCESSOR_GFX942) + +EnumValue +Enum(gpu_type) String(gfx950) Value(PROCESSOR_GFX950) + EnumValue Enum(gpu_type) String(gfx9-generic) Value(PROCESSOR_GFX9_GENERIC) +EnumValue +Enum(gpu_type) String(gfx9-4-generic) Value(PROCESSOR_GFX9_4_GENERIC) + EnumValue Enum(gpu_type) String(gfx1030) Value(PROCESSOR_GFX1030) diff --git a/gcc/config/gcn/gcn-valu.md b/gcc/config/gcn/gcn-valu.md index 977ad886ef2..4b21302e82c 100644 --- a/gcc/config/gcn/gcn-valu.md +++ b/gcc/config/gcn/gcn-valu.md @@ -1161,7 +1161,7 @@ && (((unsigned HOST_WIDE_INT)INTVAL(operands[2]) + 0x1000) < 0x2000))" { addr_space_t as = INTVAL (operands[3]); - const char *glc = INTVAL (operands[4]) ? " glc" : ""; + const char *glc = INTVAL (operands[4]) ? TARGET_GLC_NAME : ""; static char buf[200]; if (AS_FLAT_P (as)) @@ -1221,7 +1221,7 @@ && (((unsigned HOST_WIDE_INT)INTVAL(operands[3]) + 0x1000) < 0x2000))" { addr_space_t as = INTVAL (operands[4]); - const char *glc = INTVAL (operands[5]) ? " glc" : ""; + const char *glc = INTVAL (operands[5]) ? TARGET_GLC_NAME : ""; static char buf[200]; if (AS_GLOBAL_P (as)) @@ -1288,7 +1288,7 @@ && (((unsigned HOST_WIDE_INT)INTVAL(operands[1]) + 0x1000) < 0x2000))" { addr_space_t as = INTVAL (operands[3]); - const char *glc = INTVAL (operands[4]) ? " glc" : ""; + const char *glc = INTVAL (operands[4]) ? TARGET_GLC_NAME : ""; static char buf[200]; if (AS_FLAT_P (as)) @@ -1345,7 +1345,7 @@ && (((unsigned HOST_WIDE_INT)INTVAL(operands[2]) + 0x1000) < 0x2000))" { addr_space_t as = INTVAL (operands[4]); - const char *glc = INTVAL (operands[5]) ? " glc" : ""; + const char *glc = INTVAL (operands[5]) ? TARGET_GLC_NAME : ""; static char buf[200]; if (AS_GLOBAL_P (as)) diff --git a/gcc/config/gcn/gcn.cc b/gcc/config/gcn/gcn.cc index f982dbd7bcf..31a59dd6f22 100644 --- a/gcc/config/gcn/gcn.cc +++ b/gcc/config/gcn/gcn.cc @@ -7102,7 +7102,8 @@ print_operand_address (FILE *file, rtx mem) E - print conditional code for v_cmp (eq_u64/ne_u64...) A - print address in formatting suitable for given address space. O - print offset:n for data share operations. - g - print "glc", if appropriate for given MEM + G - print "glc" (or for gfx94x: sc0) unconditionally [+ indep. of regnum] + g - print "glc" (or for gfx94x: sc0), if appropriate for given MEM L - print low-part of a multi-reg value H - print second part of a multi-reg value (high-part of 2-reg value) J - print third part of a multi-reg value @@ -7718,10 +7719,13 @@ print_operand (FILE *file, rtx x, int code) else output_addr_const (file, x); return; + case 'G': + fputs (TARGET_GLC_NAME, file); + return; case 'g': gcc_assert (xcode == MEM); if (MEM_VOLATILE_P (x)) - fputs (" glc", file); + fputs (TARGET_GLC_NAME, file); return; default: output_operand_lossage ("invalid %%xn code"); diff --git a/gcc/config/gcn/gcn.h b/gcc/config/gcn/gcn.h index 5198fbca207..3d42de3b2a8 100644 --- a/gcc/config/gcn/gcn.h +++ b/gcc/config/gcn/gcn.h @@ -43,6 +43,8 @@ extern const struct gcn_device_def { builtin_define ("__CDNA1__"); \ else if (TARGET_CDNA2) \ builtin_define ("__CDNA2__"); \ + else if (TARGET_CDNA3) \ + builtin_define ("__CDNA3__"); \ else if (TARGET_RDNA2) \ builtin_define ("__RDNA2__"); \ else if (TARGET_RDNA3) \ diff --git a/gcc/config/gcn/gcn.md b/gcc/config/gcn/gcn.md index e0fb735e5ec..1998931e052 100644 --- a/gcc/config/gcn/gcn.md +++ b/gcc/config/gcn/gcn.md @@ -206,7 +206,7 @@ ; vdata: vgpr0-255 ; srsrc: sgpr0-102 ; soffset: sgpr0-102 -; flags: offen, idxen, glc, lds, slc, tfe +; flags: offen, idxen, %G, lds, slc, tfe ; ; mtbuf - Typed memory buffer operation. Two words ; offset: 12-bit constant @@ -216,10 +216,10 @@ ; vdata: vgpr0-255 ; srsrc: sgpr0-102 ; soffset: sgpr0-102 -; flags: offen, idxen, glc, lds, slc, tfe +; flags: offen, idxen, %G, lds, slc, tfe ; ; flat - flat or global memory operations -; flags: glc, slc +; flags: %G, slc ; addr: vgpr0-255 ; data: vgpr0-255 ; vdst: vgpr0-255 @@ -1964,6 +1964,14 @@ [(set_attr "type" "mult") (set_attr "length" "8")]) +(define_insn "*memory_barrier" + [(set (match_operand:BLK 0) + (unspec:BLK [(match_dup 0)] UNSPEC_MEMORY_BARRIER))] + "TARGET_TARGET_SC_CACHE" + "buffer_inv sc1" + [(set_attr "type" "mubuf") + (set_attr "length" "4")]) + ; FIXME: These patterns have been disabled as they do not seem to work ; reliably - they can cause hangs or incorrect results. ; TODO: flush caches according to memory model @@ -1979,9 +1987,9 @@ (use (match_operand 3 "const_int_operand"))] "0 /* Disabled. */" "@ - s_atomic_<bare_mnemonic><X>\t%0, %1, %2 glc\;s_waitcnt\tlgkmcnt(0) - flat_atomic_<bare_mnemonic><X>\t%0, %1, %2 glc\;s_waitcnt\t0 - global_atomic_<bare_mnemonic><X>\t%0, %A1, %2%O1 glc\;s_waitcnt\tvmcnt(0)" + s_atomic_<bare_mnemonic><X>\t%0, %1, %2 %G2\;s_waitcnt\tlgkmcnt(0) + flat_atomic_<bare_mnemonic><X>\t%0, %1, %2 %G2\;s_waitcnt\t0 + global_atomic_<bare_mnemonic><X>\t%0, %A1, %2%O1 %G2\;s_waitcnt\tvmcnt(0)" [(set_attr "type" "smem,flat,flat") (set_attr "length" "12")]) @@ -2046,9 +2054,9 @@ UNSPECV_ATOMIC))] "" "@ - s_atomic_cmpswap<X>\t%0, %1, %2 glc\;s_waitcnt\tlgkmcnt(0) - flat_atomic_cmpswap<X>\t%0, %1, %2 glc\;s_waitcnt\t0 - global_atomic_cmpswap<X>\t%0, %A1, %2%O1 glc\;s_waitcnt\tvmcnt(0)" + s_atomic_cmpswap<X>\t%0, %1, %2 %G2\;s_waitcnt\tlgkmcnt(0) + flat_atomic_cmpswap<X>\t%0, %1, %2 %G2\;s_waitcnt\t0 + global_atomic_cmpswap<X>\t%0, %A1, %2%O1 %G2\;s_waitcnt\tvmcnt(0)" [(set_attr "type" "smem,flat,flat") (set_attr "length" "12") (set_attr "delayeduse" "*,yes,yes")]) @@ -2088,15 +2096,15 @@ switch (which_alternative) { case 0: - return "s_load%o0\t%0, %A1 glc\;s_waitcnt\tlgkmcnt(0)"; + return "s_load%o0\t%0, %A1 %G1\;s_waitcnt\tlgkmcnt(0)"; case 1: return (TARGET_RDNA2 /* Not GFX11. */ - ? "flat_load%o0\t%0, %A1%O1 glc dlc\;s_waitcnt\t0" - : "flat_load%o0\t%0, %A1%O1 glc\;s_waitcnt\t0"); + ? "flat_load%o0\t%0, %A1%O1 %G1 dlc\;s_waitcnt\t0" + : "flat_load%o0\t%0, %A1%O1 %G1\;s_waitcnt\t0"); case 2: return (TARGET_RDNA2 /* Not GFX11. */ - ? "global_load%o0\t%0, %A1%O1 glc dlc\;s_waitcnt\tvmcnt(0)" - : "global_load%o0\t%0, %A1%O1 glc\;s_waitcnt\tvmcnt(0)"); + ? "global_load%o0\t%0, %A1%O1 %G1 dlc\;s_waitcnt\tvmcnt(0)" + : "global_load%o0\t%0, %A1%O1 %G1\;s_waitcnt\tvmcnt(0)"); } break; case MEMMODEL_CONSUME: @@ -2105,25 +2113,31 @@ switch (which_alternative) { case 0: - return "s_load%o0\t%0, %A1 glc\;s_waitcnt\tlgkmcnt(0)\;" + return "s_load%o0\t%0, %A1 %G1\;s_waitcnt\tlgkmcnt(0)\;" "s_dcache_wb_vol"; case 1: return (TARGET_RDNA2 - ? "flat_load%o0\t%0, %A1%O1 glc dlc\;s_waitcnt\t0\;" + ? "flat_load%o0\t%0, %A1%O1 %G1 dlc\;s_waitcnt\t0\;" "buffer_gl1_inv\;buffer_gl0_inv" : TARGET_RDNA3 - ? "flat_load%o0\t%0, %A1%O1 glc\;s_waitcnt\t0\;" + ? "flat_load%o0\t%0, %A1%O1 %G1\;s_waitcnt\t0\;" "buffer_gl1_inv\;buffer_gl0_inv" - : "flat_load%o0\t%0, %A1%O1 glc\;s_waitcnt\t0\;" + : TARGET_TARGET_SC_CACHE + ? "flat_load%o0\t%0, %A1%O1 %G1\;s_waitcnt\t0\;" + "buffer_inv sc1" + : "flat_load%o0\t%0, %A1%O1 %G1\;s_waitcnt\t0\;" "buffer_wbinvl1_vol"); case 2: return (TARGET_RDNA2 - ? "global_load%o0\t%0, %A1%O1 glc dlc\;s_waitcnt\tvmcnt(0)\;" + ? "global_load%o0\t%0, %A1%O1 %G1 dlc\;s_waitcnt\tvmcnt(0)\;" "buffer_gl1_inv\;buffer_gl0_inv" : TARGET_RDNA3 - ? "global_load%o0\t%0, %A1%O1 glc\;s_waitcnt\tvmcnt(0)\;" + ? "global_load%o0\t%0, %A1%O1 %G1\;s_waitcnt\tvmcnt(0)\;" "buffer_gl1_inv\;buffer_gl0_inv" - : "global_load%o0\t%0, %A1%O1 glc\;s_waitcnt\tvmcnt(0)\;" + : TARGET_TARGET_SC_CACHE + ? "global_load%o0\t%0, %A1%O1 %G1\;s_waitcnt\tvmcnt(0)\;" + "buffer_inv sc1" + : "global_load%o0\t%0, %A1%O1 %G1\;s_waitcnt\tvmcnt(0)\;" "buffer_wbinvl1_vol"); } break; @@ -2133,25 +2147,31 @@ switch (which_alternative) { case 0: - return "s_dcache_wb_vol\;s_load%o0\t%0, %A1 glc\;" + return "s_dcache_wb_vol\;s_load%o0\t%0, %A1 %G1\;" "s_waitcnt\tlgkmcnt(0)\;s_dcache_inv_vol"; case 1: return (TARGET_RDNA2 - ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_load%o0\t%0, %A1%O1 glc dlc\;" + ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_load%o0\t%0, %A1%O1 %G1 dlc\;" "s_waitcnt\t0\;buffer_gl1_inv\;buffer_gl0_inv" : TARGET_RDNA3 - ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_load%o0\t%0, %A1%O1 glc\;" + ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_load%o0\t%0, %A1%O1 %G1\;" "s_waitcnt\t0\;buffer_gl1_inv\;buffer_gl0_inv" - : "buffer_wbinvl1_vol\;flat_load%o0\t%0, %A1%O1 glc\;" + : TARGET_TARGET_SC_CACHE + ? "buffer_inv sc1\;flat_load%o0\t%0, %A1%O1 %G1\;" + "s_waitcnt\t0\;buffer_inv sc1" + : "buffer_wbinvl1_vol\;flat_load%o0\t%0, %A1%O1 %G1\;" "s_waitcnt\t0\;buffer_wbinvl1_vol"); case 2: return (TARGET_RDNA2 - ? "buffer_gl1_inv\;buffer_gl0_inv\;global_load%o0\t%0, %A1%O1 glc dlc\;" + ? "buffer_gl1_inv\;buffer_gl0_inv\;global_load%o0\t%0, %A1%O1 %G1 dlc\;" "s_waitcnt\tvmcnt(0)\;buffer_gl1_inv\;buffer_gl0_inv" : TARGET_RDNA3 - ? "buffer_gl1_inv\;buffer_gl0_inv\;global_load%o0\t%0, %A1%O1 glc\;" + ? "buffer_gl1_inv\;buffer_gl0_inv\;global_load%o0\t%0, %A1%O1 %G1\;" "s_waitcnt\tvmcnt(0)\;buffer_gl1_inv\;buffer_gl0_inv" - : "buffer_wbinvl1_vol\;global_load%o0\t%0, %A1%O1 glc\;" + : TARGET_TARGET_SC_CACHE + ? "buffer_inv sc1\;global_load%o0\t%0, %A1%O1 %G1\;" + "s_waitcnt\tvmcnt(0)\;buffer_inv sc1" + : "buffer_wbinvl1_vol\;global_load%o0\t%0, %A1%O1 %G1\;" "s_waitcnt\tvmcnt(0)\;buffer_wbinvl1_vol"); } break; @@ -2176,11 +2196,11 @@ switch (which_alternative) { case 0: - return "s_store%o1\t%1, %A0 glc\;s_waitcnt\tlgkmcnt(0)"; + return "s_store%o1\t%1, %A0 %G1\;s_waitcnt\tlgkmcnt(0)"; case 1: - return "flat_store%o1\t%A0, %1%O0 glc\;s_waitcnt\t0"; + return "flat_store%o1\t%A0, %1%O0 %G1\;s_waitcnt\t0"; case 2: - return "global_store%o1\t%A0, %1%O0 glc\;s_waitcnt\tvmcnt(0)"; + return "global_store%o1\t%A0, %1%O0 %G1\;s_waitcnt\tvmcnt(0)"; } break; case MEMMODEL_RELEASE: @@ -2188,18 +2208,22 @@ switch (which_alternative) { case 0: - return "s_dcache_wb_vol\;s_store%o1\t%1, %A0 glc"; + return "s_dcache_wb_vol\;s_store%o1\t%1, %A0 %G1"; case 1: return (TARGET_GLn_CACHE - ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_store%o1\t%A0, %1%O0 glc" + ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_store%o1\t%A0, %1%O0 %G1" : TARGET_WBINVL1_CACHE - ? "buffer_wbinvl1_vol\;flat_store%o1\t%A0, %1%O0 glc" + ? "buffer_wbinvl1_vol\;flat_store%o1\t%A0, %1%O0 %G1" + : TARGET_TARGET_SC_CACHE + ? "buffer_inv sc1\;flat_store%o1\t%A0, %1%O0 %G1" : "error: cache architectire unspecified"); case 2: return (TARGET_GLn_CACHE - ? "buffer_gl1_inv\;buffer_gl0_inv\;global_store%o1\t%A0, %1%O0 glc" + ? "buffer_gl1_inv\;buffer_gl0_inv\;global_store%o1\t%A0, %1%O0 %G1" : TARGET_WBINVL1_CACHE - ? "buffer_wbinvl1_vol\;global_store%o1\t%A0, %1%O0 glc" + ? "buffer_wbinvl1_vol\;global_store%o1\t%A0, %1%O0 %G1" + : TARGET_TARGET_SC_CACHE + ? "buffer_inv sc1\;global_store%o1\t%A0, %1%O0 %G1" : "error: cache architecture unspecified"); } break; @@ -2209,23 +2233,29 @@ switch (which_alternative) { case 0: - return "s_dcache_wb_vol\;s_store%o1\t%1, %A0 glc\;" + return "s_dcache_wb_vol\;s_store%o1\t%1, %A0 %G1\;" "s_waitcnt\tlgkmcnt(0)\;s_dcache_inv_vol"; case 1: return (TARGET_GLn_CACHE - ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_store%o1\t%A0, %1%O0 glc\;" + ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_store%o1\t%A0, %1%O0 %G1\;" "s_waitcnt\t0\;buffer_gl1_inv\;buffer_gl0_inv" : TARGET_WBINVL1_CACHE - ? "buffer_wbinvl1_vol\;flat_store%o1\t%A0, %1%O0 glc\;" + ? "buffer_wbinvl1_vol\;flat_store%o1\t%A0, %1%O0 %G1\;" "s_waitcnt\t0\;buffer_wbinvl1_vol" + : TARGET_TARGET_SC_CACHE + ? "buffer_inv sc1\;flat_store%o1\t%A0, %1%O0 %G1\;" + "s_waitcnt\t0\;buffer_inv sc1" : "error: cache architecture unspecified"); case 2: return (TARGET_GLn_CACHE - ? "buffer_gl1_inv\;buffer_gl0_inv\;global_store%o1\t%A0, %1%O0 glc\;" + ? "buffer_gl1_inv\;buffer_gl0_inv\;global_store%o1\t%A0, %1%O0 %G1\;" "s_waitcnt\tvmcnt(0)\;buffer_gl1_inv\;buffer_gl0_inv" : TARGET_WBINVL1_CACHE - ? "buffer_wbinvl1_vol\;global_store%o1\t%A0, %1%O0 glc\;" + ? "buffer_wbinvl1_vol\;global_store%o1\t%A0, %1%O0 %G1\;" "s_waitcnt\tvmcnt(0)\;buffer_wbinvl1_vol" + : TARGET_TARGET_SC_CACHE + ? "buffer_inv sc1\;global_store%o1\t%A0, %1%O0 %G1\;" + "s_waitcnt\tvmcnt(0)\;buffer_inv sc1" : "error: cache architecture unspecified"); } break; @@ -2252,11 +2282,11 @@ switch (which_alternative) { case 0: - return "s_atomic_swap<X>\t%0, %1, %2 glc\;s_waitcnt\tlgkmcnt(0)"; + return "s_atomic_swap<X>\t%0, %1, %2 %G1\;s_waitcnt\tlgkmcnt(0)"; case 1: - return "flat_atomic_swap<X>\t%0, %1, %2 glc\;s_waitcnt\t0"; + return "flat_atomic_swap<X>\t%0, %1, %2 %G1\;s_waitcnt\t0"; case 2: - return "global_atomic_swap<X>\t%0, %A1, %2%O1 glc\;" + return "global_atomic_swap<X>\t%0, %A1, %2%O1 %G1\;" "s_waitcnt\tvmcnt(0)"; } break; @@ -2266,23 +2296,29 @@ switch (which_alternative) { case 0: - return "s_atomic_swap<X>\t%0, %1, %2 glc\;s_waitcnt\tlgkmcnt(0)\;" + return "s_atomic_swap<X>\t%0, %1, %2 %G1\;s_waitcnt\tlgkmcnt(0)\;" "s_dcache_wb_vol\;s_dcache_inv_vol"; case 1: return (TARGET_GLn_CACHE - ? "flat_atomic_swap<X>\t%0, %1, %2 glc\;s_waitcnt\t0\;" + ? "flat_atomic_swap<X>\t%0, %1, %2 %G1\;s_waitcnt\t0\;" "buffer_gl1_inv\;buffer_gl0_inv" : TARGET_WBINVL1_CACHE - ? "flat_atomic_swap<X>\t%0, %1, %2 glc\;s_waitcnt\t0\;" + ? "flat_atomic_swap<X>\t%0, %1, %2 %G1\;s_waitcnt\t0\;" "buffer_wbinvl1_vol" + : TARGET_TARGET_SC_CACHE + ? "flat_atomic_swap<X>\t%0, %1, %2 %G1\;s_waitcnt\t0\;" + "buffer_inv sc1" : "error: cache architecture unspecified"); case 2: return (TARGET_GLn_CACHE - ? "global_atomic_swap<X>\t%0, %A1, %2%O1 glc\;" + ? "global_atomic_swap<X>\t%0, %A1, %2%O1 %G1\;" "s_waitcnt\tvmcnt(0)\;buffer_gl1_inv\;buffer_gl0_inv" : TARGET_WBINVL1_CACHE - ? "global_atomic_swap<X>\t%0, %A1, %2%O1 glc\;" + ? "global_atomic_swap<X>\t%0, %A1, %2%O1 %G1\;" "s_waitcnt\tvmcnt(0)\;buffer_wbinvl1_vol" + : TARGET_TARGET_SC_CACHE + ? "global_atomic_swap<X>\t%0, %A1, %2%O1 %G1\;" + "s_waitcnt\tvmcnt(0)\;buffer_inv sc1" : "error: cache architecture unspecified"); } break; @@ -2291,24 +2327,31 @@ switch (which_alternative) { case 0: - return "s_dcache_wb_vol\;s_atomic_swap<X>\t%0, %1, %2 glc\;" + return "s_dcache_wb_vol\;s_atomic_swap<X>\t%0, %1, %2 %G1\;" "s_waitcnt\tlgkmcnt(0)"; case 1: return (TARGET_GLn_CACHE - ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_atomic_swap<X>\t%0, %1, %2 glc\;" + ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_atomic_swap<X>\t%0, %1, %2 %G1\;" "s_waitcnt\t0" : TARGET_WBINVL1_CACHE - ? "buffer_wbinvl1_vol\;flat_atomic_swap<X>\t%0, %1, %2 glc\;" + ? "buffer_wbinvl1_vol\;flat_atomic_swap<X>\t%0, %1, %2 %G1\;" + "s_waitcnt\t0" + : TARGET_TARGET_SC_CACHE + ? "buffer_inv sc1\;flat_atomic_swap<X>\t%0, %1, %2 %G1\;" "s_waitcnt\t0" : "error: cache architecture unspecified"); case 2: return (TARGET_GLn_CACHE ? "buffer_gl1_inv\;buffer_gl0_inv\;" - "global_atomic_swap<X>\t%0, %A1, %2%O1 glc\;" + "global_atomic_swap<X>\t%0, %A1, %2%O1 %G1\;" "s_waitcnt\tvmcnt(0)" : TARGET_WBINVL1_CACHE ? "buffer_wbinvl1_vol\;" - "global_atomic_swap<X>\t%0, %A1, %2%O1 glc\;" + "global_atomic_swap<X>\t%0, %A1, %2%O1 %G1\;" + "s_waitcnt\tvmcnt(0)" + : TARGET_TARGET_SC_CACHE + ? "buffer_inv sc1\;" + "global_atomic_swap<X>\t%0, %A1, %2%O1 %G1\;" "s_waitcnt\tvmcnt(0)" : "error: cache architecture unspecified"); } @@ -2319,25 +2362,32 @@ switch (which_alternative) { case 0: - return "s_dcache_wb_vol\;s_atomic_swap<X>\t%0, %1, %2 glc\;" + return "s_dcache_wb_vol\;s_atomic_swap<X>\t%0, %1, %2 %G1\;" "s_waitcnt\tlgkmcnt(0)\;s_dcache_inv_vol"; case 1: return (TARGET_GLn_CACHE - ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_atomic_swap<X>\t%0, %1, %2 glc\;" + ? "buffer_gl1_inv\;buffer_gl0_inv\;flat_atomic_swap<X>\t%0, %1, %2 %G1\;" "s_waitcnt\t0\;buffer_gl1_inv\;buffer_gl0_inv" : TARGET_WBINVL1_CACHE - ? "buffer_wbinvl1_vol\;flat_atomic_swap<X>\t%0, %1, %2 glc\;" + ? "buffer_wbinvl1_vol\;flat_atomic_swap<X>\t%0, %1, %2 %G1\;" "s_waitcnt\t0\;buffer_wbinvl1_vol" + : TARGET_TARGET_SC_CACHE + ? "buffer_inv sc1\;flat_atomic_swap<X>\t%0, %1, %2 %G1\;" + "s_waitcnt\t0\;buffer_inv sc1" : "error: cache architecture unspecified"); case 2: return (TARGET_GLn_CACHE ? "buffer_gl1_inv\;buffer_gl0_inv\;" - "global_atomic_swap<X>\t%0, %A1, %2%O1 glc\;" + "global_atomic_swap<X>\t%0, %A1, %2%O1 %G1\;" "s_waitcnt\tvmcnt(0)\;buffer_gl1_inv\;buffer_gl0_inv" : TARGET_WBINVL1_CACHE ? "buffer_wbinvl1_vol\;" - "global_atomic_swap<X>\t%0, %A1, %2%O1 glc\;" + "global_atomic_swap<X>\t%0, %A1, %2%O1 %G1\;" "s_waitcnt\tvmcnt(0)\;buffer_wbinvl1_vol" + : TARGET_TARGET_SC_CACHE + ? "buffer_inv sc1\;" + "global_atomic_swap<X>\t%0, %A1, %2%O1 %G1\;" + "s_waitcnt\tvmcnt(0)\;buffer_inv sc1" : "error: cache architecture unspecified"); } break; diff --git a/gcc/doc/install.texi b/gcc/doc/install.texi index fb921b326f1..34e35a2dd52 100644 --- a/gcc/doc/install.texi +++ b/gcc/doc/install.texi @@ -1343,11 +1343,11 @@ default set of libraries is selected based on the value of @item amdgcn*-*-* @var{list} is a comma separated list of ISA names (allowed values: @code{gfx900}, @code{gfx902}, @code{gfx904}, @code{gfx906}, @code{gfx908}, -@code{gfx909}, @code{gfx90a}, @code{gfx90c}, @code{gfx9-generic}, -@code{gfx1030}, @code{gfx1031}, @code{gfx1032}, @code{gfx1033}, -@code{gfx1034}, @code{gfx1035}, @code{gfx1036}, @code{gfx10-3-generic}, -@code{gfx1100}, @code{gfx1101}, @code{gfx1102}, @code{gfx1103}, -@code{gfx1150}, @code{gfx1151}, @code{gfx1152}, @code{gfx1153}, +@code{gfx909}, @code{gfx90a}, @code{gfx90c}, @code{gfx942}, @code{gfx950}, +@code{gfx9-generic}, @code{gfx9-4-generic}, @code{gfx1030}, @code{gfx1031}, +@code{gfx1032}, @code{gfx1033}, @code{gfx1034}, @code{gfx1035}, @code{gfx1036}, +@code{gfx10-3-generic}, @code{gfx1100}, @code{gfx1101}, @code{gfx1102}, +@code{gfx1103}, @code{gfx1150}, @code{gfx1151}, @code{gfx1152}, @code{gfx1153}, @code{gfx11-generic}). It ought not include the name of the default ISA, specified via @option{--with-arch}. If @var{list} is empty, then there will be no multilibs and only the default run-time library will be built. If @@ -4064,9 +4064,10 @@ By default, multilib support is built for @code{gfx900}, @code{gfx906}, requires LLVM 15 or newer. LLVM 13.0.1 or LLVM 14 can be used by specifying a @code{--with-multilib-list=} that does not list any GFX 11 device nor @code{gfx1036}. At least LLVM 16 is required for @code{gfx1150} and -@code{gfx1151}, LLVM 19 for the generic @code{gfx9-generic}, -@code{gfx10-3-generic}, and @code{gfx11-generic} targets and for -@code{gfx1152}, while LLVM 20 is required for @code{gfx1153}. +@code{gfx1151}, LLVM 18 for @code{gfx942}, LLVM 19 for the generic +@code{gfx9-generic}, @code{gfx9-4-generic}, @code{gfx10-3-generic}, and +@code{gfx11-generic} targets and for @code{gfx1152}, while LLVM 20 is required +for @code{gfx950} and @code{gfx1153}. The supported ISA architectures are listed in the GCC manual. The generic ISA targets @code{gfx9-generic}, @code{gfx10-3-generic}, and diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi index 17929b3cf15..382cc9fa7a8 100644 --- a/gcc/doc/invoke.texi +++ b/gcc/doc/invoke.texi @@ -22673,10 +22673,20 @@ Compile for CDNA2 Instinct MI200 series devices (gfx90a). @item gfx90c Compile for GCN5 Vega 7 devices (gfx90c). +@item gfx942 +Compile for CDNA3 Instinct MI300 series devices (gfx942). (Experimental) + +@item gfx950 +Compile for the CDNA3 gfx950 devices. (Experimental) + @item gfx9-generic Compile generic code for Vega devices, executable on the following subset of GFX9 devices: gfx900, gfx902, gfx904, gfx906, gfx909 and gfx90c. (Experimental) +@item gfx9-4-generic +Compile generic code for CDNA3 devices, executable on the following subset of +GFX9 devices: gfx942 and gfx950. (Experimental) + @item gfx1030 Compile for RDNA2 gfx1030 devices (GFX10 series). diff --git a/libgomp/testsuite/libgomp.c/declare-variant-4-gfx942.c b/libgomp/testsuite/libgomp.c/declare-variant-4-gfx942.c new file mode 100644 index 00000000000..d1df5500d5f --- /dev/null +++ b/libgomp/testsuite/libgomp.c/declare-variant-4-gfx942.c @@ -0,0 +1,8 @@ +/* { dg-do link { target { offload_target_amdgcn } } } */ +/* { dg-additional-options -foffload=amdgcn-amdhsa } */ +/* { dg-additional-options -foffload=-march=gfx942 } */ +/* { dg-additional-options "-foffload=-fdump-tree-optimized" } */ + +#include "declare-variant-4.h" + +/* { dg-final { only_for_offload_target amdgcn-amdhsa scan-offload-tree-dump "= gfx942 \\(\\);" "optimized" } } */ diff --git a/libgomp/testsuite/libgomp.c/declare-variant-4.h b/libgomp/testsuite/libgomp.c/declare-variant-4.h index 53788d2f922..2257f4c5508 100644 --- a/libgomp/testsuite/libgomp.c/declare-variant-4.h +++ b/libgomp/testsuite/libgomp.c/declare-variant-4.h @@ -35,6 +35,13 @@ gfx90c (void) return 0x90c; } +__attribute__ ((noipa)) +int +gfx942 (void) +{ + return 0x942; +} + __attribute__ ((noipa)) int gfx1030 (void) @@ -68,6 +75,7 @@ gfx1103 (void) #pragma omp declare variant(gfx908) match(device = {isa("gfx908")}) #pragma omp declare variant(gfx90a) match(device = {isa("gfx90a")}) #pragma omp declare variant(gfx90c) match(device = {isa("gfx90c")}) +#pragma omp declare variant(gfx942) match(device = {isa("gfx942")}) #pragma omp declare variant(gfx1030) match(device = {isa("gfx1030")}) #pragma omp declare variant(gfx1036) match(device = {isa("gfx1036")}) #pragma omp declare variant(gfx1100) match(device = {isa("gfx1100")})
gcc-16/changes.html: Update GCN for gfx942 diff --git a/htdocs/gcc-16/changes.html b/htdocs/gcc-16/changes.html index bec41705..ebd3d867 100644 --- a/htdocs/gcc-16/changes.html +++ b/htdocs/gcc-16/changes.html @@ -98,6 +98,17 @@ for general information.</p> <!-- <h3 id="x86">IA-32/x86-64</h3> --> +<h3 id="amdgcn">AMD GPU (GCN)</h3> + +<ul> + <li>Experimental support for AMD Instinct MI300 (<code>gfx942</code>) devices + has been added, including the generic <code>gfx9-4-generic</code> and + mostly compatible <code>gfx950</code>. Consult GCC's + <a href="https://gcc.gnu.org/install/specific.html#amdgcn-x-amdhsa"> + installation notes</a> on how to enable multilib support for them.</li> +.</li> +</ul> + <!-- <h3 id="mips">MIPS</h3> --> <!-- <h3 id="mep">MeP</h3> -->