diff --git a/clang/test/Preprocessor/riscv-target-features.c b/clang/test/Preprocessor/riscv-target-features.c --- a/clang/test/Preprocessor/riscv-target-features.c +++ b/clang/test/Preprocessor/riscv-target-features.c @@ -69,6 +69,7 @@ // CHECK-NOT: __riscv_ssaia {{.*$}} // CHECK-NOT: __riscv_zfbfmin {{.*$}} // CHECK-NOT: __riscv_zvfbfmin {{.*$}} +// CHECK-NOT: __riscv_zvfbfwma {{.*$}} // RUN: %clang -target riscv32-unknown-linux-gnu -march=rv32i -x c -E -dM %s \ // RUN: -o - | FileCheck %s @@ -692,3 +693,11 @@ // RUN: -march=rv64ifzvfbfmin0p6 -x c -E -dM %s \ // RUN: -o - | FileCheck --check-prefix=CHECK-ZVFBFMIN-EXT %s // CHECK-ZVFBFMIN-EXT: __riscv_zvfbfmin 6000{{$}} + +// RUN: %clang -target riscv32 -menable-experimental-extensions \ +// RUN: -march=rv32ifzvfbfwma0p6 -x c -E -dM %s \ +// RUN: -o - | FileCheck --check-prefix=CHECK-ZVFBFWMA-EXT %s +// RUN: %clang -target riscv64 -menable-experimental-extensions \ +// RUN: -march=rv64ifzvfbfwma0p6 -x c -E -dM %s \ +// RUN: -o - | FileCheck --check-prefix=CHECK-ZVFBFWMA-EXT %s +// CHECK-ZVFBFWMA-EXT: __riscv_zvfbfwma 6000{{$}} diff --git a/llvm/docs/RISCVUsage.rst b/llvm/docs/RISCVUsage.rst --- a/llvm/docs/RISCVUsage.rst +++ b/llvm/docs/RISCVUsage.rst @@ -219,6 +219,9 @@ ``experimental-zvfbfmin`` LLVM implements assembler support for the `0.6 draft specification `_. +``experimental-zvfbfwma`` + LLVM implements assembler support for the `0.6 draft specification `_. + ``experimental-zvfh`` LLVM implements `this draft text `__. diff --git a/llvm/docs/ReleaseNotes.rst b/llvm/docs/ReleaseNotes.rst --- a/llvm/docs/ReleaseNotes.rst +++ b/llvm/docs/ReleaseNotes.rst @@ -181,7 +181,8 @@ * Zve32f is no longer allowed with Zfinx. Zve64d is no longer allowed with Zdinx. * Assembly support was added for the experimental Zfbfmin (scalar BF16 - conversions) and Zvfbfmin (vector BF16 conversions) extensions. + conversions), Zvfbfmin (vector BF16 conversions), and Zvfbfwma (vector BF16 + widening mul-add) extensions. Changes to the WebAssembly Backend ---------------------------------- diff --git a/llvm/lib/Support/RISCVISAInfo.cpp b/llvm/lib/Support/RISCVISAInfo.cpp --- a/llvm/lib/Support/RISCVISAInfo.cpp +++ b/llvm/lib/Support/RISCVISAInfo.cpp @@ -150,6 +150,7 @@ {"zfbfmin", RISCVExtensionVersion{0, 6}}, {"zicond", RISCVExtensionVersion{1, 0}}, {"zvfbfmin", RISCVExtensionVersion{0, 6}}, + {"zvfbfwma", RISCVExtensionVersion{0, 6}}, {"zvfh", RISCVExtensionVersion{0, 1}}, {"ztso", RISCVExtensionVersion{0, 1}}, @@ -939,6 +940,7 @@ static const char *ImpliedExtsZve64f[] = {"zve64x", "zve32f"}; static const char *ImpliedExtsZve64x[] = {"zve32x", "zvl64b"}; static const char *ImpliedExtsZvfbfmin[] = {"zve32f"}; +static const char *ImpliedExtsZvfbfwma[] = {"zve32f"}; static const char *ImpliedExtsZvfh[] = {"zve32f", "zfhmin"}; static const char *ImpliedExtsZvkn[] = {"zvbb", "zvbc", "zvkned", "zvknhb", "zvkt"}; @@ -998,6 +1000,7 @@ {{"zve64f"}, {ImpliedExtsZve64f}}, {{"zve64x"}, {ImpliedExtsZve64x}}, {{"zvfbfmin"}, {ImpliedExtsZvfbfmin}}, + {{"zvfbfwma"}, {ImpliedExtsZvfbfwma}}, {{"zvfh"}, {ImpliedExtsZvfh}}, {{"zvkn"}, {ImpliedExtsZvkn}}, {{"zvkng"}, {ImpliedExtsZvkng}}, diff --git a/llvm/lib/Target/RISCV/RISCVFeatures.td b/llvm/lib/Target/RISCV/RISCVFeatures.td --- a/llvm/lib/Target/RISCV/RISCVFeatures.td +++ b/llvm/lib/Target/RISCV/RISCVFeatures.td @@ -459,6 +459,14 @@ AssemblerPredicate<(all_of FeatureStdExtZvfbfmin), "'Zvfbfmin' (Vector BF16 Converts)">; +def FeatureStdExtZvfbfwma + : SubtargetFeature<"experimental-zvfbfwma", "HasStdExtZvfbfwma", "true", + "'Zvfbfwma' (Vector BF16 widening mul-add)", + [FeatureStdExtZve32f]>; +def HasStdExtZvfbfwma : Predicate<"Subtarget->hasStdExtZvfbfwma()">, + AssemblerPredicate<(all_of FeatureStdExtZvfbfwma), + "'Zvfbfwma' (Vector BF16 widening mul-add)">; + def FeatureStdExtZvfh : SubtargetFeature<"experimental-zvfh", "HasStdExtZvfh", "true", "'Zvfh' (Vector Half-Precision Floating-Point)", @@ -629,10 +637,12 @@ def HasHalfFPLoadStoreMove : Predicate<"Subtarget->hasHalfFPLoadStoreMove()">, - AssemblerPredicate<(any_of FeatureStdExtZfh, FeatureStdExtZfhmin, FeatureStdExtZfbfmin), + AssemblerPredicate<(any_of FeatureStdExtZfh, FeatureStdExtZfhmin, + FeatureStdExtZfbfmin, FeatureStdExtZvfbfwma), "'Zfh' (Half-Precision Floating-Point) or " "'Zfhmin' (Half-Precision Floating-Point Minimal) or " - "'Zfbfmin' (Scalar BF16 Converts)">; + "'Zfbfmin' (Scalar BF16 Converts) or " + "'Zvfbfwma' (Vector BF16 widening mul-add)">; //===----------------------------------------------------------------------===// // Vendor extensions diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoZvfbf.td b/llvm/lib/Target/RISCV/RISCVInstrInfoZvfbf.td --- a/llvm/lib/Target/RISCV/RISCVInstrInfoZvfbf.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfoZvfbf.td @@ -24,3 +24,8 @@ let Uses = [FRM] in defm VFNCVTBF16_F_F_W : VNCVTF_FV_VS2<"vfncvtbf16.f.f.w", 0b010010, 0b11101>; } + +let Predicates = [HasStdExtZvfbfwma], Constraints = "@earlyclobber $vd", + RVVConstraint = WidenV, Uses = [FRM], mayRaiseFPException = true in { +defm VFWMACCBF16_V : VWMAC_FV_V_F<"vfwmaccbf16", 0b100011>; +} diff --git a/llvm/lib/Target/RISCV/RISCVSubtarget.h b/llvm/lib/Target/RISCV/RISCVSubtarget.h --- a/llvm/lib/Target/RISCV/RISCVSubtarget.h +++ b/llvm/lib/Target/RISCV/RISCVSubtarget.h @@ -124,7 +124,8 @@ return hasStdExtZfhOrZfhmin() || hasStdExtZhinxOrZhinxmin(); } bool hasHalfFPLoadStoreMove() const { - return HasStdExtZfh || HasStdExtZfhmin || HasStdExtZfbfmin; + return HasStdExtZfh || HasStdExtZfhmin || HasStdExtZfbfmin || + HasStdExtZvfbfwma; } bool is64Bit() const { return IsRV64; } MVT getXLenVT() const { return XLenVT; } diff --git a/llvm/test/CodeGen/RISCV/attributes.ll b/llvm/test/CodeGen/RISCV/attributes.ll --- a/llvm/test/CodeGen/RISCV/attributes.ll +++ b/llvm/test/CodeGen/RISCV/attributes.ll @@ -76,6 +76,7 @@ ; RUN: llc -mtriple=riscv32 -mattr=+experimental-ssaia %s -o - | FileCheck --check-prefixes=CHECK,RV32SSAIA %s ; RUN: llc -mtriple=riscv32 -mattr=+experimental-zfbfmin %s -o - | FileCheck --check-prefixes=CHECK,RV32ZFBFMIN %s ; RUN: llc -mtriple=riscv32 -mattr=+f,+experimental-zvfbfmin %s -o - | FileCheck --check-prefixes=CHECK,RV32ZVFBFMIN %s +; RUN: llc -mtriple=riscv32 -mattr=+f,+experimental-zvfbfwma %s -o - | FileCheck --check-prefixes=CHECK,RV32ZVFBFWMA %s ; RUN: llc -mtriple=riscv64 %s -o - | FileCheck %s ; RUN: llc -mtriple=riscv64 -mattr=+m %s -o - | FileCheck --check-prefixes=CHECK,RV64M %s @@ -159,6 +160,7 @@ ; RUN: llc -mtriple=riscv64 -mattr=+experimental-ssaia %s -o - | FileCheck --check-prefixes=CHECK,RV64SSAIA %s ; RUN: llc -mtriple=riscv64 -mattr=+experimental-zfbfmin %s -o - | FileCheck --check-prefixes=CHECK,RV64ZFBFMIN %s ; RUN: llc -mtriple=riscv64 -mattr=+f,+experimental-zvfbfmin %s -o - | FileCheck --check-prefixes=CHECK,RV64ZVFBFMIN %s +; RUN: llc -mtriple=riscv64 -mattr=+f,+experimental-zvfbfwma %s -o - | FileCheck --check-prefixes=CHECK,RV64ZVFBFWMA %s ; CHECK: .attribute 4, 16 @@ -237,6 +239,7 @@ ; RV32SSAIA: .attribute 5, "rv32i2p1_ssaia1p0" ; RV32ZFBFMIN: .attribute 5, "rv32i2p1_f2p2_zicsr2p0_zfbfmin0p6" ; RV32ZVFBFMIN: .attribute 5, "rv32i2p1_f2p2_zicsr2p0_zve32f1p0_zve32x1p0_zvfbfmin0p6_zvl32b1p0" +; RV32ZVFBFWMA: .attribute 5, "rv32i2p1_f2p2_zicsr2p0_zve32f1p0_zve32x1p0_zvfbfwma0p6_zvl32b1p0" ; RV64M: .attribute 5, "rv64i2p1_m2p0" ; RV64ZMMUL: .attribute 5, "rv64i2p1_zmmul1p0" @@ -319,6 +322,7 @@ ; RV64SSAIA: .attribute 5, "rv64i2p1_ssaia1p0" ; RV64ZFBFMIN: .attribute 5, "rv64i2p1_f2p2_zicsr2p0_zfbfmin0p6" ; RV64ZVFBFMIN: .attribute 5, "rv64i2p1_f2p2_zicsr2p0_zve32f1p0_zve32x1p0_zvfbfmin0p6_zvl32b1p0" +; RV64ZVFBFWMA: .attribute 5, "rv64i2p1_f2p2_zicsr2p0_zve32f1p0_zve32x1p0_zvfbfwma0p6_zvl32b1p0" define i32 @addi(i32 %a) { %1 = add i32 %a, 1 diff --git a/llvm/test/MC/RISCV/attribute-arch.s b/llvm/test/MC/RISCV/attribute-arch.s --- a/llvm/test/MC/RISCV/attribute-arch.s +++ b/llvm/test/MC/RISCV/attribute-arch.s @@ -269,3 +269,6 @@ .attribute arch, "rv32if_zvfbfmin0p6" # CHECK: .attribute 5, "rv32i2p1_f2p2_zicsr2p0_zve32f1p0_zve32x1p0_zvfbfmin0p6_zvl32b1p0" + +.attribute arch, "rv32if_zvfbfwma0p6" +# CHECK: .attribute 5, "rv32i2p1_f2p2_zicsr2p0_zve32f1p0_zve32x1p0_zvfbfwma0p6_zvl32b1p0" diff --git a/llvm/test/MC/RISCV/rv64zhinx-invalid.s b/llvm/test/MC/RISCV/rv64zhinx-invalid.s --- a/llvm/test/MC/RISCV/rv64zhinx-invalid.s +++ b/llvm/test/MC/RISCV/rv64zhinx-invalid.s @@ -1,7 +1,7 @@ # RUN: not llvm-mc -triple riscv64 -mattr=+zhinx %s 2>&1 | FileCheck %s # Not support float registers -flh fa4, 12(sp) # CHECK: :[[@LINE]]:1: error: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) or 'Zfbfmin' (Scalar BF16 Converts){{$}} +flh fa4, 12(sp) # CHECK: :[[@LINE]]:1: error: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) or 'Zfbfmin' (Scalar BF16 Converts) or 'Zvfbfwma' (Vector BF16 widening mul-add){{$}} # Invalid instructions fsh a5, 12(sp) # CHECK: :[[@LINE]]:5: error: invalid operand for instruction diff --git a/llvm/test/MC/RISCV/rv64zhinxmin-invalid.s b/llvm/test/MC/RISCV/rv64zhinxmin-invalid.s --- a/llvm/test/MC/RISCV/rv64zhinxmin-invalid.s +++ b/llvm/test/MC/RISCV/rv64zhinxmin-invalid.s @@ -1,7 +1,7 @@ # RUN: not llvm-mc -triple riscv64 -mattr=+zhinxmin %s 2>&1 | FileCheck %s # Not support float registers -flh fa4, 12(sp) # CHECK: :[[@LINE]]:1: error: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) or 'Zfbfmin' (Scalar BF16 Converts){{$}} +flh fa4, 12(sp) # CHECK: :[[@LINE]]:1: error: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) or 'Zfbfmin' (Scalar BF16 Converts) or 'Zvfbfwma' (Vector BF16 widening mul-add){{$}} # Invalid instructions fsh a5, 12(sp) # CHECK: :[[@LINE]]:5: error: invalid operand for instruction diff --git a/llvm/test/MC/RISCV/rvv/zvfbfwma-invalid.s b/llvm/test/MC/RISCV/rvv/zvfbfwma-invalid.s new file mode 100644 --- /dev/null +++ b/llvm/test/MC/RISCV/rvv/zvfbfwma-invalid.s @@ -0,0 +1,10 @@ +# RUN: not llvm-mc -triple riscv32 -mattr=+experimental-zvfbfwma,+d < %s 2>&1 | \ +# RUN: FileCheck %s +# RUN: not llvm-mc -triple riscv64 -mattr=+experimental-zvfbfwma,+d < %s 2>&1 | \ +# RUN: FileCheck %s + +# Attempting to use fcvt instructions from zfhmin +fcvt.s.h fa0, ft0 # CHECK: [[@LINE]]:1: error: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) +fcvt.h.s ft2, fa2 # CHECK: [[@LINE]]:1: error: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) +fcvt.d.h fa0, ft0 # CHECK: [[@LINE]]:1: error: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) +fcvt.h.d ft2, fa2 # CHECK: [[@LINE]]:1: error: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) diff --git a/llvm/test/MC/RISCV/rvv/zvfbfwma.s b/llvm/test/MC/RISCV/rvv/zvfbfwma.s new file mode 100644 --- /dev/null +++ b/llvm/test/MC/RISCV/rvv/zvfbfwma.s @@ -0,0 +1,68 @@ +# RUN: llvm-mc -triple=riscv32 -show-encoding -mattr=+f,+experimental-zvfbfwma %s \ +# RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST +# RUN: not llvm-mc -triple=riscv32 -show-encoding -mattr=+v,+f %s 2>&1 \ +# RUN: | FileCheck %s --check-prefix=CHECK-ERROR +# RUN: llvm-mc -triple=riscv32 -filetype=obj -mattr=+f,+experimental-zvfbfwma %s \ +# RUN: | llvm-objdump -d --mattr=+f,+experimental-zvfbfwma - \ +# RUN: | FileCheck %s --check-prefix=CHECK-INST +# RUN: llvm-mc -triple=riscv32 -filetype=obj -mattr=+f,+experimental-zvfbfwma %s \ +# RUN: | llvm-objdump -d - | FileCheck %s --check-prefix=CHECK-UNKNOWN +# RUN: llvm-mc -triple=riscv64 -show-encoding -mattr=+f,+experimental-zvfbfwma %s \ +# RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST +# RUN: not llvm-mc -triple=riscv64 -show-encoding -mattr=+v,+f %s 2>&1 \ +# RUN: | FileCheck %s --check-prefix=CHECK-ERROR +# RUN: llvm-mc -triple=riscv64 -filetype=obj -mattr=+f,+experimental-zvfbfwma %s \ +# RUN: | llvm-objdump -d --mattr=+f,+experimental-zvfbfwma - \ +# RUN: | FileCheck %s --check-prefix=CHECK-INST +# RUN: llvm-mc -triple=riscv64 -filetype=obj -mattr=+f,+experimental-zvfbfwma %s \ +# RUN: | llvm-objdump -d - | FileCheck %s --check-prefix=CHECK-UNKNOWN + +# CHECK-INST: vfwmaccbf16.vv v8, v20, v4, v0.t +# CHECK-ENCODING: [0x57,0x14,0x4a,0x8c] +# CHECK-ERROR: instruction requires the following: 'Zvfbfwma' (Vector BF16 widening mul-add){{$}} +# CHECK-UNKNOWN: 57 14 4a 8c +vfwmaccbf16.vv v8, v20, v4, v0.t + +# CHECK-INST: vfwmaccbf16.vv v8, v20, v4 +# CHECK-ENCODING: [0x57,0x14,0x4a,0x8e] +# CHECK-ERROR: instruction requires the following: 'Zvfbfwma' (Vector BF16 widening mul-add){{$}} +# CHECK-UNKNOWN: 57 14 4a 8e +vfwmaccbf16.vv v8, v20, v4 + +# CHECK-INST: vfwmaccbf16.vf v8, fa0, v4, v0.t +# CHECK-ENCODING: [0x57,0x54,0x45,0x8c] +# CHECK-ERROR: instruction requires the following: 'Zvfbfwma' (Vector BF16 widening mul-add){{$}} +# CHECK-UNKNOWN: 57 54 45 8c +vfwmaccbf16.vf v8, fa0, v4, v0.t + +# CHECK-INST: vfwmaccbf16.vf v8, fa0, v4 +# CHECK-ENCODING: [0x57,0x54,0x45,0x8e] +# CHECK-ERROR: instruction requires the following: 'Zvfbfwma' (Vector BF16 widening mul-add){{$}} +# CHECK-UNKNOWN: 57 54 45 8e +vfwmaccbf16.vf v8, fa0, v4 + +# Check scalar half FP load/store/move included in this extension. + +# CHECK-INST: flh ft0, 12(a0) +# CHECK-ENCODING: [0x07,0x10,0xc5,0x00] +# CHECK-ERROR: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) or 'Zfbfmin' (Scalar BF16 Converts) or 'Zvfbfwma' (Vector BF16 widening mul-add){{$}} +# CHECK-UNKNOWN: 07 10 c5 00 +flh f0, 12(a0) + +# CHECK-INST: fsh ft6, 2047(s4) +# CHECK-ENCODING: [0xa7,0x1f,0x6a,0x7e] +# CHECK-ERROR: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) or 'Zfbfmin' (Scalar BF16 Converts) or 'Zvfbfwma' (Vector BF16 widening mul-add){{$}} +# CHECK-UNKNOWN: a7 1f 6a 7e +fsh f6, 2047(s4) + +# CHECK-INST: fmv.x.h a2, fs7 +# CHECK-ENCODING: [0x53,0x86,0x0b,0xe4] +# CHECK-ERROR: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) or 'Zfbfmin' (Scalar BF16 Converts) or 'Zvfbfwma' (Vector BF16 widening mul-add){{$}} +# CHECK-UNKNOWN: 53 86 0b e4 +fmv.x.h a2, fs7 + +# CHECK-INST: fmv.h.x ft1, a6 +# CHECK-ENCODING: [0xd3,0x00,0x08,0xf4] +# CHECK-ERROR: instruction requires the following: 'Zfh' (Half-Precision Floating-Point) or 'Zfhmin' (Half-Precision Floating-Point Minimal) or 'Zfbfmin' (Scalar BF16 Converts) or 'Zvfbfwma' (Vector BF16 widening mul-add){{$}} +# CHECK-UNKNOWN: d3 00 08 f4 +fmv.h.x ft1, a6