Implement RVV widening floating-point conversions

Closed
AL
2mo ago
+271-2

Implements the widening conversions from #734. Second of three PRs sharing
the VFUNARY0 decode site; best taken after #770.

Adds the seven vfwcvt forms (V 1.0 §13.17), producing a 64-bit destination
element from a 32-bit source.

As with vzext/vsext, the destination EEW exceeds the source EEW, so §5.2
requires the source EMUL to be at least 1 and the overlap to sit in the
highest-numbered part of the destination group. rvv_cross_eew_overlap_illegal()
implements the shared-base-register rule instead, which matches the narrowing
direction, so this path uses a dedicated predicate
(rvv_widen_overlap_illegal()) with a comment explaining the distinction.
The predicate was checked against the spec's LMUL=8 example and against
fractional-LMUL cases where the source EMUL falls below 1.

Reserved vs1 values and the single-width / narrowing ranges are rejected;
the decode tests assert that.

Smoke coverage uses 1.5 to separate RNE from RTZ (2.5 gives the same result
under both, so it would not catch a .rtz variant that ignored its suffix)
and -3 to separate the signed and unsigned integer-to-float forms.

make check passes; the build was checked in the default, EXT_V,
JIT+EXT_V and EXT_V-without-EXT_F configurations. clang-format 20.1.7
clean.


Summary by cubic

Implements the seven vfwcvt widening floating-point conversions from #734, producing 64-bit destination elements from 32-bit sources. Previously these encodings returned illegal; now they decode and execute.

New Features

  • Supports all seven forms: float-to-int, int-to-float, and float-to-float, with rtz variants pinning round-towards-zero.
  • Enforces the spec's §5.2 overlap rule via a dedicated predicate, which requires the source EMUL to be at least 1 and the overlap in the highest-numbered destination part.
  • Adds smoke tests using 1.5 and -3 to distinguish rounding modes and signed/unsigned conversions.