RISC-V: Add support for 'XVentanaCondOps' reusing 'Zicond' support

'XVentanaCondOps' is a vendor extension from Ventana Micro Systems
containing two instructions for conditional move and will be supported on
their Veyron V1 CPU.

And most notably (for historical reasons), 'XVentanaCondOps' and the
standard 'Zicond' extension are functionally equivalent (only encodings and
instruction names are different).

*   czero.eqz == vt.maskc
*   czero.nez == vt.maskcn

This commit adds support for the 'XVentanaCondOps' extension by extending
'Zicond' extension support.  With this, we can now reuse the optimization
using the 'Zicond' extension for the 'XVentanaCondOps' extension.

The specification for the 'XVentanaCondOps' extension is based on:
<https://github.com/ventanamicro/ventana-custom-extensions/releases/download/v1.0.1/ventana-custom-extensions-v1.0.1.pdf>

gcc/ChangeLog:

	* common/config/riscv/riscv-common.cc (riscv_ext_flag_table):
	Parse 'XVentanaCondOps' extension.
	* config/riscv/riscv-opts.h (MASK_XVENTANACONDOPS): New.
	(TARGET_XVENTANACONDOPS): Ditto.
	(TARGET_ZICOND_LIKE): New to represent targets with conditional
	moves like 'Zicond'.  It includes RV64 + 'XVentanaCondOps'.
	* config/riscv/riscv.cc (riscv_rtx_costs): Replace TARGET_ZICOND
	with TARGET_ZICOND_LIKE.
	(riscv_expand_conditional_move): Ditto.
	* config/riscv/riscv.md (mov<mode>cc): Replace TARGET_ZICOND with
	TARGET_ZICOND_LIKE.
	* config/riscv/riscv.opt: Add new riscv_xventana_subext.
	* config/riscv/zicond.md: Modify description.
	(eqz_ventana): New to match corresponding czero instructions.
	(nez_ventana): Ditto.
	(*czero.<eqz>.<GPR><X>): Emit a 'XVentanaCondOps' instruction if
	'Zicond' is not available but 'XVentanaCondOps' + RV64 is.
	(*czero.<eqz>.<GPR><X>): Ditto.
	(*czero.eqz.<GPR><X>.opt1): Ditto.
	(*czero.nez.<GPR><X>.opt2): Ditto.

gcc/testsuite/ChangeLog:

	* gcc.target/riscv/xventanacondops-primitiveSemantics.c: New test,
	* gcc.target/riscv/xventanacondops-primitiveSemantics-rv32.c: New
	test to make sure that XVentanaCondOps instructions are disabled
	on RV32.
	* gcc.target/riscv/xventanacondops-xor-01.c: New test,
This commit is contained in:
Tsukasa OI 2023-08-30 02:34:35 +00:00
parent a134b6ce8e
commit af88776caa
9 changed files with 82 additions and 14 deletions

View file

@ -1493,6 +1493,8 @@ static const riscv_ext_flag_table_t riscv_ext_flag_table[] =
{"xtheadmempair", &gcc_options::x_riscv_xthead_subext, MASK_XTHEADMEMPAIR},
{"xtheadsync", &gcc_options::x_riscv_xthead_subext, MASK_XTHEADSYNC},
{"xventanacondops", &gcc_options::x_riscv_xventana_subext, MASK_XVENTANACONDOPS},
{NULL, NULL, 0}
};

View file

@ -321,6 +321,12 @@ enum riscv_entity
#define TARGET_XTHEADMEMPAIR ((riscv_xthead_subext & MASK_XTHEADMEMPAIR) != 0)
#define TARGET_XTHEADSYNC ((riscv_xthead_subext & MASK_XTHEADSYNC) != 0)
#define MASK_XVENTANACONDOPS (1 << 0)
#define TARGET_XVENTANACONDOPS ((riscv_xventana_subext & MASK_XVENTANACONDOPS) != 0)
#define TARGET_ZICOND_LIKE (TARGET_ZICOND || (TARGET_XVENTANACONDOPS && TARGET_64BIT))
/* We only enable VLS modes for VLA vectorization since fixed length VLMAX mode
is the highest priority choice and should not conflict with VLS modes. */
#define TARGET_VECTOR_VLS \

View file

@ -2767,7 +2767,7 @@ riscv_rtx_costs (rtx x, machine_mode mode, int outer_code, int opno ATTRIBUTE_UN
*total = COSTS_N_INSNS (1);
return true;
}
else if (TARGET_ZICOND
else if (TARGET_ZICOND_LIKE
&& outer_code == SET
&& ((GET_CODE (XEXP (x, 1)) == REG
&& XEXP (x, 2) == CONST0_RTX (GET_MODE (XEXP (x, 1))))
@ -3864,7 +3864,7 @@ riscv_expand_conditional_move (rtx dest, rtx op, rtx cons, rtx alt)
cond, cons, alt)));
return true;
}
else if (TARGET_ZICOND
else if (TARGET_ZICOND_LIKE
&& GET_MODE_CLASS (mode) == MODE_INT)
{
/* The comparison must be comparing WORD_MODE objects. We must

View file

@ -2611,7 +2611,7 @@
(if_then_else:GPR (match_operand 1 "comparison_operator")
(match_operand:GPR 2 "sfb_alu_operand")
(match_operand:GPR 3 "sfb_alu_operand")))]
"TARGET_SFB_ALU || TARGET_XTHEADCONDMOV || TARGET_ZICOND"
"TARGET_SFB_ALU || TARGET_XTHEADCONDMOV || TARGET_ZICOND_LIKE"
{
if (riscv_expand_conditional_move (operands[0], operands[1],
operands[2], operands[3]))

View file

@ -257,6 +257,9 @@ int riscv_ztso_subext
TargetVariable
int riscv_xthead_subext
TargetVariable
int riscv_xventana_subext
Enum
Name(isa_spec_class) Type(enum riscv_isa_spec_class)
Supported ISA specs (for use with the -misa-spec= option):

View file

@ -1,4 +1,5 @@
;; Machine description for the RISC-V Zicond extension
;; Machine description for the RISC-V Zicond extension and functionally-
;; equivalent XVentanaCondOps vendor extension
;; Copyright (C) 2022-23 Free Software Foundation, Inc.
;; This file is part of GCC.
@ -20,16 +21,25 @@
(define_code_iterator eq_or_ne [eq ne])
(define_code_attr eqz [(eq "nez") (ne "eqz")])
(define_code_attr nez [(eq "eqz") (ne "nez")])
(define_code_attr eqz_ventana [(eq "n") (ne "")])
(define_code_attr nez_ventana [(eq "") (ne "n")])
;; Zicond
;; Zicond / XVentanaCondOps
(define_insn "*czero.<eqz>.<GPR:mode><X:mode>"
[(set (match_operand:GPR 0 "register_operand" "=r")
(if_then_else:GPR (eq_or_ne (match_operand:X 1 "register_operand" "r")
(const_int 0))
(match_operand:GPR 2 "register_operand" "r")
(const_int 0)))]
"TARGET_ZICOND"
"czero.<eqz>\t%0,%2,%1"
"TARGET_ZICOND_LIKE"
{
if (TARGET_ZICOND)
return "czero.<eqz>\t%0,%2,%1";
else if (TARGET_XVENTANACONDOPS && TARGET_64BIT)
return "vt.maskc<eqz_ventana>\t%0,%2,%1";
else
gcc_unreachable ();
}
)
(define_insn "*czero.<nez>.<GPR:mode><X:mode>"
@ -38,8 +48,15 @@
(const_int 0))
(const_int 0)
(match_operand:GPR 2 "register_operand" "r")))]
"TARGET_ZICOND"
"czero.<nez>\t%0,%2,%1"
"TARGET_ZICOND_LIKE"
{
if (TARGET_ZICOND)
return "czero.<nez>\t%0,%2,%1";
else if (TARGET_XVENTANACONDOPS && TARGET_64BIT)
return "vt.maskc<nez_ventana>\t%0,%2,%1";
else
gcc_unreachable ();
}
)
;; Special optimization under eq/ne in primitive semantics
@ -49,8 +66,15 @@
(const_int 0))
(match_operand:GPR 2 "register_operand" "1")
(match_operand:GPR 3 "register_operand" "r")))]
"TARGET_ZICOND && rtx_equal_p (operands[1], operands[2])"
"czero.eqz\t%0,%3,%1"
"TARGET_ZICOND_LIKE && rtx_equal_p (operands[1], operands[2])"
{
if (TARGET_ZICOND)
return "czero.eqz\t%0,%3,%1";
else if (TARGET_XVENTANACONDOPS && TARGET_64BIT)
return "vt.maskc\t%0,%3,%1";
else
gcc_unreachable ();
}
)
(define_insn "*czero.nez.<GPR:mode><X:mode>.opt2"
@ -60,7 +84,14 @@
(match_operand:GPR 2 "register_operand" "r")
(match_operand:GPR 3 "register_operand" "1")))]
"TARGET_ZICOND && rtx_equal_p (operands[1], operands[3])"
"czero.eqz\t%0,%2,%1"
{
if (TARGET_ZICOND)
return "czero.eqz\t%0,%2,%1";
else if (TARGET_XVENTANACONDOPS && TARGET_64BIT)
return "vt.maskc\t%0,%2,%1";
else
gcc_unreachable ();
}
)
;; Combine creates this form in some cases (particularly the coremark
@ -72,7 +103,7 @@
(match_operand 2 "immediate_operand"))
(match_operand:X 3 "register_operand")))
(clobber (match_operand:X 4 "register_operand"))]
"TARGET_ZICOND && TARGET_ZBS"
"TARGET_ZICOND_LIKE && TARGET_ZBS"
[(set (match_dup 4) (zero_extract:X (match_dup 1) (const_int 1) (match_dup 2)))
(set (match_dup 0) (if_then_else:X (eq:X (match_dup 4) (const_int 0))
(const_int 0)
@ -85,7 +116,7 @@
(match_operand 2 "immediate_operand"))
(match_operand:X 3 "register_operand")))
(clobber (match_operand:X 4 "register_operand"))]
"TARGET_ZICOND && !TARGET_ZBS && (UINTVAL (operands[2]) < 11)"
"TARGET_ZICOND_LIKE && !TARGET_ZBS && (UINTVAL (operands[2]) < 11)"
[(set (match_dup 4) (and:X (match_dup 1) (match_dup 2)))
(set (match_dup 0) (if_then_else:X (eq:X (match_dup 4) (const_int 0))
(const_int 0)

View file

@ -0,0 +1,8 @@
/* { dg-do compile } */
/* { dg-options "-march=rv32gc_xventanacondops -mabi=ilp32d" } */
/* { dg-skip-if "" { *-*-* } {"-O0" "-Og"} } */
#include "zicond-primitiveSemantics.c"
/* { dg-final { scan-assembler-not "vt\\.maskc\t" } } */
/* { dg-final { scan-assembler-not "vt\\.maskcn\t" } } */

View file

@ -0,0 +1,10 @@
/* { dg-do compile } */
/* { dg-options "-march=rv64gc_xventanacondops -mabi=lp64d" } */
/* { dg-skip-if "" { *-*-* } {"-O0" "-Og"} } */
#include "zicond-primitiveSemantics.c"
/* { dg-final { scan-assembler-times "vt\\.maskc\t" 6 } } */
/* { dg-final { scan-assembler-times "vt\\.maskcn\t" 6 } } */
/* { dg-final { scan-assembler-not "beq" } } */
/* { dg-final { scan-assembler-not "bne" } } */

View file

@ -0,0 +1,8 @@
/* { dg-do compile } */
/* { dg-options "-march=rv64gc_xventanacondops -mabi=lp64d" } */
/* { dg-skip-if "" { *-*-* } { "-O0" "-Og" "-Os" "-Oz" } } */
#include "zicond-xor-01.c"
/* { dg-final { scan-assembler-times "vt\\.maskc\t" 1 } } */
/* { dg-final { scan-assembler-times "xor\t" 1 } } */