Commit
r15-6245-g4f4e13dd235b introduced new modes for MVE tuples, but
missed adding support for them in a few places.
Adding them to the list in arm_attr_length_move_neon is not sufficient
since we later face another ICE where the compiler does not know how
to split move of such data.
The patch therefore enhances the define_splits for OI and XI moves in
neon.md, via the introduction of new iterators.
In addition, it seems consistent to update output_move_neon such that
VALID_NEON_*_MODE are used only when TARGET_NEON.
gcc/ChangeLog:
PR target/118131
* config/arm/arm.cc (output_move_neon): Check TARGET_NEON as
needed.
(arm_attr_length_move_neon): Add support for V2x and V4x MVE tuple
modes.
* config/arm/iterators.md (VSTRUCT2, VSTRUCT4): New.
* config/arm/neon.md: Use VSTRUCT2 instead of OI and VSTRUCT4
instead of XI in define_split.
nregs = REG_NREGS (reg) / 2;
gcc_assert (VFP_REGNO_OK_FOR_DOUBLE (regno)
|| NEON_REGNO_OK_FOR_QUAD (regno));
- gcc_assert (VALID_NEON_DREG_MODE (mode)
- || VALID_NEON_QREG_MODE (mode)
- || VALID_NEON_STRUCT_MODE (mode)
+ gcc_assert ((TARGET_NEON
+ && (VALID_NEON_DREG_MODE (mode)
+ || VALID_NEON_QREG_MODE (mode)
+ || VALID_NEON_STRUCT_MODE (mode)))
|| (TARGET_HAVE_MVE
- && VALID_MVE_STRUCT_MODE (mode)));
+ && (VALID_MVE_MODE (mode)
+ || VALID_MVE_STRUCT_MODE (mode))));
gcc_assert (MEM_P (mem));
addr = XEXP (mem, 0);
return "";
}
-/* Compute and return the length of neon_mov<mode>, where <mode> is
- one of VSTRUCT modes: EI, OI, CI or XI. */
+/* Compute and return the length of neon_mov<mode>, where <mode> is one of
+ VSTRUCT modes: EI, OI, CI or XI for Neon, and V2x16QI, V2x8HI, V2x4SI,
+ V2x8HF, V2x4SF, V2x16QI, V2x8HI, V2x4SI, V2x8HF, V2x4SF for MVE. */
int
arm_attr_length_move_neon (rtx_insn *insn)
{
{
case E_EImode:
case E_OImode:
+ case E_V2x16QImode:
+ case E_V2x8HImode:
+ case E_V2x4SImode:
+ case E_V2x8HFmode:
+ case E_V2x4SFmode:
return 8;
case E_CImode:
return 12;
case E_XImode:
+ case E_V4x16QImode:
+ case E_V4x8HImode:
+ case E_V4x4SImode:
+ case E_V4x8HFmode:
+ case E_V4x4SFmode:
return 16;
default:
gcc_unreachable ();
(V4x4SF "TARGET_HAVE_MVE_FLOAT")
])
+;; Structure types of the same size as OImode
+(define_mode_iterator VSTRUCT2 [OI
+ (V2x16QI "TARGET_HAVE_MVE")
+ (V2x8HI "TARGET_HAVE_MVE")
+ (V2x4SI "TARGET_HAVE_MVE")
+ (V2x8HF "TARGET_HAVE_MVE_FLOAT")
+ (V2x4SF "TARGET_HAVE_MVE_FLOAT")
+ ])
+
+;; Structure types of the same size as XImode
+(define_mode_iterator VSTRUCT4 [XI
+ (V4x16QI "TARGET_HAVE_MVE")
+ (V4x8HI "TARGET_HAVE_MVE")
+ (V4x4SI "TARGET_HAVE_MVE")
+ (V4x8HF "TARGET_HAVE_MVE_FLOAT")
+ (V4x4SF "TARGET_HAVE_MVE_FLOAT")
+ ])
+
;; Opaque structure types used in table lookups (except vtbl1/vtbx1).
(define_mode_iterator VTAB [TI EI OI])
})
(define_split
- [(set (match_operand:OI 0 "s_register_operand" "")
- (match_operand:OI 1 "s_register_operand" ""))]
+ [(set (match_operand:VSTRUCT2 0 "s_register_operand" "")
+ (match_operand:VSTRUCT2 1 "s_register_operand" ""))]
"(TARGET_NEON || TARGET_HAVE_MVE)&& reload_completed"
[(set (match_dup 0) (match_dup 1))
(set (match_dup 2) (match_dup 3))]
})
(define_split
- [(set (match_operand:XI 0 "s_register_operand" "")
- (match_operand:XI 1 "s_register_operand" ""))]
+ [(set (match_operand:VSTRUCT4 0 "s_register_operand" "")
+ (match_operand:VSTRUCT4 1 "s_register_operand" ""))]
"(TARGET_NEON || TARGET_HAVE_MVE) && reload_completed"
[(set (match_dup 0) (match_dup 1))
(set (match_dup 2) (match_dup 3))