Skip to content

Commit 20f11b0

Browse files
ARM64-SVE: Add ConvertToSingle, ConvertToDouble; fix CovertTo* tests (#104478)
1 parent 9487df0 commit 20f11b0

File tree

10 files changed

+406
-45
lines changed

10 files changed

+406
-45
lines changed

Diff for: src/coreclr/jit/hwintrinsic.cpp

+3-1
Original file line numberDiff line numberDiff line change
@@ -2088,9 +2088,11 @@ GenTree* Compiler::impHWIntrinsic(NamedIntrinsic intrinsic,
20882088
#elif defined(TARGET_ARM64)
20892089
switch (intrinsic)
20902090
{
2091+
case NI_Sve_ConvertToDouble:
20912092
case NI_Sve_ConvertToInt32:
2092-
case NI_Sve_ConvertToUInt32:
20932093
case NI_Sve_ConvertToInt64:
2094+
case NI_Sve_ConvertToSingle:
2095+
case NI_Sve_ConvertToUInt32:
20942096
case NI_Sve_ConvertToUInt64:
20952097
// Save the base type of return SIMD. It is used to contain this intrinsic inside
20962098
// ConditionalSelect.

Diff for: src/coreclr/jit/hwintrinsiccodegenarm64.cpp

+2
Original file line numberDiff line numberDiff line change
@@ -586,6 +586,7 @@ void CodeGen::genHWIntrinsic(GenTreeHWIntrinsic* node)
586586
{
587587
case NI_Sve_ConvertToInt32:
588588
case NI_Sve_ConvertToUInt32:
589+
case NI_Sve_ConvertToSingle:
589590
{
590591
embOpt = emitTypeSize(intrinEmbMask.baseType) == EA_8BYTE ? INS_OPTS_D_TO_S
591592
: INS_OPTS_SCALABLE_S;
@@ -594,6 +595,7 @@ void CodeGen::genHWIntrinsic(GenTreeHWIntrinsic* node)
594595

595596
case NI_Sve_ConvertToInt64:
596597
case NI_Sve_ConvertToUInt64:
598+
case NI_Sve_ConvertToDouble:
597599
{
598600
embOpt = emitTypeSize(intrinEmbMask.baseType) == EA_4BYTE ? INS_OPTS_S_TO_D
599601
: INS_OPTS_SCALABLE_D;

Diff for: src/coreclr/jit/hwintrinsiclistarm64sve.h

+2
Original file line numberDiff line numberDiff line change
@@ -48,8 +48,10 @@ HARDWARE_INTRINSIC(Sve, ConditionalExtractAfterLastActiveElementAndRep
4848
HARDWARE_INTRINSIC(Sve, ConditionalExtractLastActiveElement, -1, 3, true, {INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_ExplicitMaskedOperation|HW_Flag_LowMaskedOperation|HW_Flag_HasRMWSemantics|HW_Flag_HasScalarInputVariant|HW_Flag_SpecialCodeGen)
4949
HARDWARE_INTRINSIC(Sve, ConditionalExtractLastActiveElementAndReplicate, -1, 3, true, {INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb, INS_sve_clastb}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_ExplicitMaskedOperation|HW_Flag_LowMaskedOperation|HW_Flag_HasRMWSemantics)
5050
HARDWARE_INTRINSIC(Sve, ConditionalSelect, -1, 3, true, {INS_sve_sel, INS_sve_sel, INS_sve_sel, INS_sve_sel, INS_sve_sel, INS_sve_sel, INS_sve_sel, INS_sve_sel, INS_sve_sel, INS_sve_sel}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_ExplicitMaskedOperation|HW_Flag_SupportsContainment)
51+
HARDWARE_INTRINSIC(Sve, ConvertToDouble, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_scvtf, INS_sve_ucvtf, INS_sve_scvtf, INS_sve_ucvtf, INS_sve_fcvt, INS_invalid}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_BaseTypeFromFirstArg|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
5152
HARDWARE_INTRINSIC(Sve, ConvertToInt32, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_fcvtzs, INS_sve_fcvtzs}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_BaseTypeFromFirstArg|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
5253
HARDWARE_INTRINSIC(Sve, ConvertToInt64, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_fcvtzs, INS_sve_fcvtzs}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_BaseTypeFromFirstArg|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
54+
HARDWARE_INTRINSIC(Sve, ConvertToSingle, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_scvtf, INS_sve_ucvtf, INS_sve_scvtf, INS_sve_ucvtf, INS_invalid, INS_sve_fcvt}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_BaseTypeFromFirstArg|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
5355
HARDWARE_INTRINSIC(Sve, ConvertToUInt32, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_fcvtzu, INS_sve_fcvtzu}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_BaseTypeFromFirstArg|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
5456
HARDWARE_INTRINSIC(Sve, ConvertToUInt64, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_fcvtzu, INS_sve_fcvtzu}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_BaseTypeFromFirstArg|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
5557
HARDWARE_INTRINSIC(Sve, Count16BitElements, 0, 1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_cnth, INS_invalid, INS_invalid, INS_invalid}, HW_Category_Scalar, HW_Flag_Scalable|HW_Flag_HasEnumOperand|HW_Flag_SpecialCodeGen|HW_Flag_NoFloatingPointUsed)

Diff for: src/coreclr/jit/lowerarmarch.cpp

+4-2
Original file line numberDiff line numberDiff line change
@@ -3599,9 +3599,11 @@ void Lowering::ContainCheckHWIntrinsic(GenTreeHWIntrinsic* node)
35993599

36003600
// For now, make sure that we get here only for intrinsics that we are
36013601
// sure about to rely on auxiliary type's size.
3602-
assert((embOp->GetHWIntrinsicId() == NI_Sve_ConvertToInt32) ||
3603-
(embOp->GetHWIntrinsicId() == NI_Sve_ConvertToUInt32) ||
3602+
assert((embOp->GetHWIntrinsicId() == NI_Sve_ConvertToDouble) ||
3603+
(embOp->GetHWIntrinsicId() == NI_Sve_ConvertToInt32) ||
36043604
(embOp->GetHWIntrinsicId() == NI_Sve_ConvertToInt64) ||
3605+
(embOp->GetHWIntrinsicId() == NI_Sve_ConvertToSingle) ||
3606+
(embOp->GetHWIntrinsicId() == NI_Sve_ConvertToUInt32) ||
36053607
(embOp->GetHWIntrinsicId() == NI_Sve_ConvertToUInt64));
36063608

36073609
uint32_t auxSize = genTypeSize(embOp->GetAuxiliaryType());

Diff for: src/libraries/System.Private.CoreLib/src/System/Runtime/Intrinsics/Arm/Sve.PlatformNotSupported.cs

+97
Original file line numberDiff line numberDiff line change
@@ -1879,6 +1879,54 @@ internal Arm64() { }
18791879
public static unsafe Vector<double> ConditionalSelect(Vector<double> mask, Vector<double> left, Vector<double> right) { throw new PlatformNotSupportedException(); }
18801880

18811881

1882+
/// ConvertToDouble : Floating-point convert
1883+
1884+
/// <summary>
1885+
/// svfloat64_t svcvt_f64[_s32]_m(svfloat64_t inactive, svbool_t pg, svint32_t op)
1886+
/// SCVTF Ztied.D, Pg/M, Zop.S
1887+
/// svfloat64_t svcvt_f64[_s32]_x(svbool_t pg, svint32_t op)
1888+
/// SCVTF Ztied.D, Pg/M, Ztied.S
1889+
/// svfloat64_t svcvt_f64[_s32]_z(svbool_t pg, svint32_t op)
1890+
/// </summary>
1891+
public static unsafe Vector<double> ConvertToDouble(Vector<int> value) { throw new PlatformNotSupportedException(); }
1892+
1893+
/// <summary>
1894+
/// svfloat64_t svcvt_f64[_s64]_m(svfloat64_t inactive, svbool_t pg, svint64_t op)
1895+
/// SCVTF Ztied.D, Pg/M, Zop.D
1896+
/// svfloat64_t svcvt_f64[_s64]_x(svbool_t pg, svint64_t op)
1897+
/// SCVTF Ztied.D, Pg/M, Ztied.D
1898+
/// svfloat64_t svcvt_f64[_s64]_z(svbool_t pg, svint64_t op)
1899+
/// </summary>
1900+
public static unsafe Vector<double> ConvertToDouble(Vector<long> value) { throw new PlatformNotSupportedException(); }
1901+
1902+
/// <summary>
1903+
/// svfloat64_t svcvt_f64[_f32]_m(svfloat64_t inactive, svbool_t pg, svfloat32_t op)
1904+
/// FCVT Ztied.D, Pg/M, Zop.S
1905+
/// svfloat64_t svcvt_f64[_f32]_x(svbool_t pg, svfloat32_t op)
1906+
/// FCVT Ztied.D, Pg/M, Ztied.S
1907+
/// svfloat64_t svcvt_f64[_f32]_z(svbool_t pg, svfloat32_t op)
1908+
/// </summary>
1909+
public static unsafe Vector<double> ConvertToDouble(Vector<float> value) { throw new PlatformNotSupportedException(); }
1910+
1911+
/// <summary>
1912+
/// svfloat64_t svcvt_f64[_u32]_m(svfloat64_t inactive, svbool_t pg, svuint32_t op)
1913+
/// UCVTF Ztied.D, Pg/M, Zop.S
1914+
/// svfloat64_t svcvt_f64[_u32]_x(svbool_t pg, svuint32_t op)
1915+
/// UCVTF Ztied.D, Pg/M, Ztied.S
1916+
/// svfloat64_t svcvt_f64[_u32]_z(svbool_t pg, svuint32_t op)
1917+
/// </summary>
1918+
public static unsafe Vector<double> ConvertToDouble(Vector<uint> value) { throw new PlatformNotSupportedException(); }
1919+
1920+
/// <summary>
1921+
/// svfloat64_t svcvt_f64[_u64]_m(svfloat64_t inactive, svbool_t pg, svuint64_t op)
1922+
/// UCVTF Ztied.D, Pg/M, Zop.D
1923+
/// svfloat64_t svcvt_f64[_u64]_x(svbool_t pg, svuint64_t op)
1924+
/// UCVTF Ztied.D, Pg/M, Ztied.D
1925+
/// svfloat64_t svcvt_f64[_u64]_z(svbool_t pg, svuint64_t op)
1926+
/// </summary>
1927+
public static unsafe Vector<double> ConvertToDouble(Vector<ulong> value) { throw new PlatformNotSupportedException(); }
1928+
1929+
18821930
/// ConvertToInt32 : Floating-point convert
18831931

18841932
/// <summary>
@@ -1920,6 +1968,55 @@ internal Arm64() { }
19201968
/// </summary>
19211969
public static unsafe Vector<long> ConvertToInt64(Vector<float> value) { throw new PlatformNotSupportedException(); }
19221970

1971+
1972+
/// ConvertToSingle : Floating-point convert
1973+
1974+
/// <summary>
1975+
/// svfloat32_t svcvt_f32[_f64]_m(svfloat32_t inactive, svbool_t pg, svfloat64_t op)
1976+
/// FCVT Ztied.S, Pg/M, Zop.D
1977+
/// svfloat32_t svcvt_f32[_f64]_x(svbool_t pg, svfloat64_t op)
1978+
/// FCVT Ztied.S, Pg/M, Ztied.D
1979+
/// svfloat32_t svcvt_f32[_f64]_z(svbool_t pg, svfloat64_t op)
1980+
/// </summary>
1981+
public static unsafe Vector<float> ConvertToSingle(Vector<double> value) { throw new PlatformNotSupportedException(); }
1982+
1983+
/// <summary>
1984+
/// svfloat32_t svcvt_f32[_s32]_m(svfloat32_t inactive, svbool_t pg, svint32_t op)
1985+
/// SCVTF Ztied.S, Pg/M, Zop.S
1986+
/// svfloat32_t svcvt_f32[_s32]_x(svbool_t pg, svint32_t op)
1987+
/// SCVTF Ztied.S, Pg/M, Ztied.S
1988+
/// svfloat32_t svcvt_f32[_s32]_z(svbool_t pg, svint32_t op)
1989+
/// </summary>
1990+
public static unsafe Vector<float> ConvertToSingle(Vector<int> value) { throw new PlatformNotSupportedException(); }
1991+
1992+
/// <summary>
1993+
/// svfloat32_t svcvt_f32[_s64]_m(svfloat32_t inactive, svbool_t pg, svint64_t op)
1994+
/// SCVTF Ztied.S, Pg/M, Zop.D
1995+
/// svfloat32_t svcvt_f32[_s64]_x(svbool_t pg, svint64_t op)
1996+
/// SCVTF Ztied.S, Pg/M, Ztied.D
1997+
/// svfloat32_t svcvt_f32[_s64]_z(svbool_t pg, svint64_t op)
1998+
/// </summary>
1999+
public static unsafe Vector<float> ConvertToSingle(Vector<long> value) { throw new PlatformNotSupportedException(); }
2000+
2001+
/// <summary>
2002+
/// svfloat32_t svcvt_f32[_u32]_m(svfloat32_t inactive, svbool_t pg, svuint32_t op)
2003+
/// UCVTF Ztied.S, Pg/M, Zop.S
2004+
/// svfloat32_t svcvt_f32[_u32]_x(svbool_t pg, svuint32_t op)
2005+
/// UCVTF Ztied.S, Pg/M, Ztied.S
2006+
/// svfloat32_t svcvt_f32[_u32]_z(svbool_t pg, svuint32_t op)
2007+
/// </summary>
2008+
public static unsafe Vector<float> ConvertToSingle(Vector<uint> value) { throw new PlatformNotSupportedException(); }
2009+
2010+
/// <summary>
2011+
/// svfloat32_t svcvt_f32[_u64]_m(svfloat32_t inactive, svbool_t pg, svuint64_t op)
2012+
/// UCVTF Ztied.S, Pg/M, Zop.D
2013+
/// svfloat32_t svcvt_f32[_u64]_x(svbool_t pg, svuint64_t op)
2014+
/// UCVTF Ztied.S, Pg/M, Ztied.D
2015+
/// svfloat32_t svcvt_f32[_u64]_z(svbool_t pg, svuint64_t op)
2016+
/// </summary>
2017+
public static unsafe Vector<float> ConvertToSingle(Vector<ulong> value) { throw new PlatformNotSupportedException(); }
2018+
2019+
19232020
/// ConvertToUInt32 : Floating-point convert
19242021

19252022
/// <summary>

Diff for: src/libraries/System.Private.CoreLib/src/System/Runtime/Intrinsics/Arm/Sve.cs

+96
Original file line numberDiff line numberDiff line change
@@ -1937,6 +1937,54 @@ internal Arm64() { }
19371937
public static unsafe Vector<double> ConditionalSelect(Vector<double> mask, Vector<double> left, Vector<double> right) => ConditionalSelect(mask, left, right);
19381938

19391939

1940+
/// ConvertToDouble : Floating-point convert
1941+
1942+
/// <summary>
1943+
/// svfloat64_t svcvt_f64[_s32]_m(svfloat64_t inactive, svbool_t pg, svint32_t op)
1944+
/// SCVTF Ztied.D, Pg/M, Zop.S
1945+
/// svfloat64_t svcvt_f64[_s32]_x(svbool_t pg, svint32_t op)
1946+
/// SCVTF Ztied.D, Pg/M, Ztied.S
1947+
/// svfloat64_t svcvt_f64[_s32]_z(svbool_t pg, svint32_t op)
1948+
/// </summary>
1949+
public static unsafe Vector<double> ConvertToDouble(Vector<int> value) => ConvertToDouble(value);
1950+
1951+
/// <summary>
1952+
/// svfloat64_t svcvt_f64[_s64]_m(svfloat64_t inactive, svbool_t pg, svint64_t op)
1953+
/// SCVTF Ztied.D, Pg/M, Zop.D
1954+
/// svfloat64_t svcvt_f64[_s64]_x(svbool_t pg, svint64_t op)
1955+
/// SCVTF Ztied.D, Pg/M, Ztied.D
1956+
/// svfloat64_t svcvt_f64[_s64]_z(svbool_t pg, svint64_t op)
1957+
/// </summary>
1958+
public static unsafe Vector<double> ConvertToDouble(Vector<long> value) => ConvertToDouble(value);
1959+
1960+
/// <summary>
1961+
/// svfloat64_t svcvt_f64[_f32]_m(svfloat64_t inactive, svbool_t pg, svfloat32_t op)
1962+
/// FCVT Ztied.D, Pg/M, Zop.S
1963+
/// svfloat64_t svcvt_f64[_f32]_x(svbool_t pg, svfloat32_t op)
1964+
/// FCVT Ztied.D, Pg/M, Ztied.S
1965+
/// svfloat64_t svcvt_f64[_f32]_z(svbool_t pg, svfloat32_t op)
1966+
/// </summary>
1967+
public static unsafe Vector<double> ConvertToDouble(Vector<float> value) => ConvertToDouble(value);
1968+
1969+
/// <summary>
1970+
/// svfloat64_t svcvt_f64[_u32]_m(svfloat64_t inactive, svbool_t pg, svuint32_t op)
1971+
/// UCVTF Ztied.D, Pg/M, Zop.S
1972+
/// svfloat64_t svcvt_f64[_u32]_x(svbool_t pg, svuint32_t op)
1973+
/// UCVTF Ztied.D, Pg/M, Ztied.S
1974+
/// svfloat64_t svcvt_f64[_u32]_z(svbool_t pg, svuint32_t op)
1975+
/// </summary>
1976+
public static unsafe Vector<double> ConvertToDouble(Vector<uint> value) => ConvertToDouble(value);
1977+
1978+
/// <summary>
1979+
/// svfloat64_t svcvt_f64[_u64]_m(svfloat64_t inactive, svbool_t pg, svuint64_t op)
1980+
/// UCVTF Ztied.D, Pg/M, Zop.D
1981+
/// svfloat64_t svcvt_f64[_u64]_x(svbool_t pg, svuint64_t op)
1982+
/// UCVTF Ztied.D, Pg/M, Ztied.D
1983+
/// svfloat64_t svcvt_f64[_u64]_z(svbool_t pg, svuint64_t op)
1984+
/// </summary>
1985+
public static unsafe Vector<double> ConvertToDouble(Vector<ulong> value) => ConvertToDouble(value);
1986+
1987+
19401988
/// ConvertToInt32 : Floating-point convert
19411989

19421990
/// <summary>
@@ -1979,6 +2027,54 @@ internal Arm64() { }
19792027
public static unsafe Vector<long> ConvertToInt64(Vector<float> value) => ConvertToInt64(value);
19802028

19812029

2030+
/// ConvertToSingle : Floating-point convert
2031+
2032+
/// <summary>
2033+
/// svfloat32_t svcvt_f32[_f64]_m(svfloat32_t inactive, svbool_t pg, svfloat64_t op)
2034+
/// FCVT Ztied.S, Pg/M, Zop.D
2035+
/// svfloat32_t svcvt_f32[_f64]_x(svbool_t pg, svfloat64_t op)
2036+
/// FCVT Ztied.S, Pg/M, Ztied.D
2037+
/// svfloat32_t svcvt_f32[_f64]_z(svbool_t pg, svfloat64_t op)
2038+
/// </summary>
2039+
public static unsafe Vector<float> ConvertToSingle(Vector<double> value) => ConvertToSingle(value);
2040+
2041+
/// <summary>
2042+
/// svfloat32_t svcvt_f32[_s32]_m(svfloat32_t inactive, svbool_t pg, svint32_t op)
2043+
/// SCVTF Ztied.S, Pg/M, Zop.S
2044+
/// svfloat32_t svcvt_f32[_s32]_x(svbool_t pg, svint32_t op)
2045+
/// SCVTF Ztied.S, Pg/M, Ztied.S
2046+
/// svfloat32_t svcvt_f32[_s32]_z(svbool_t pg, svint32_t op)
2047+
/// </summary>
2048+
public static unsafe Vector<float> ConvertToSingle(Vector<int> value) => ConvertToSingle(value);
2049+
2050+
/// <summary>
2051+
/// svfloat32_t svcvt_f32[_s64]_m(svfloat32_t inactive, svbool_t pg, svint64_t op)
2052+
/// SCVTF Ztied.S, Pg/M, Zop.D
2053+
/// svfloat32_t svcvt_f32[_s64]_x(svbool_t pg, svint64_t op)
2054+
/// SCVTF Ztied.S, Pg/M, Ztied.D
2055+
/// svfloat32_t svcvt_f32[_s64]_z(svbool_t pg, svint64_t op)
2056+
/// </summary>
2057+
public static unsafe Vector<float> ConvertToSingle(Vector<long> value) => ConvertToSingle(value);
2058+
2059+
/// <summary>
2060+
/// svfloat32_t svcvt_f32[_u32]_m(svfloat32_t inactive, svbool_t pg, svuint32_t op)
2061+
/// UCVTF Ztied.S, Pg/M, Zop.S
2062+
/// svfloat32_t svcvt_f32[_u32]_x(svbool_t pg, svuint32_t op)
2063+
/// UCVTF Ztied.S, Pg/M, Ztied.S
2064+
/// svfloat32_t svcvt_f32[_u32]_z(svbool_t pg, svuint32_t op)
2065+
/// </summary>
2066+
public static unsafe Vector<float> ConvertToSingle(Vector<uint> value) => ConvertToSingle(value);
2067+
2068+
/// <summary>
2069+
/// svfloat32_t svcvt_f32[_u64]_m(svfloat32_t inactive, svbool_t pg, svuint64_t op)
2070+
/// UCVTF Ztied.S, Pg/M, Zop.D
2071+
/// svfloat32_t svcvt_f32[_u64]_x(svbool_t pg, svuint64_t op)
2072+
/// UCVTF Ztied.S, Pg/M, Ztied.D
2073+
/// svfloat32_t svcvt_f32[_u64]_z(svbool_t pg, svuint64_t op)
2074+
/// </summary>
2075+
public static unsafe Vector<float> ConvertToSingle(Vector<ulong> value) => ConvertToSingle(value);
2076+
2077+
19822078
/// ConvertToUInt32 : Floating-point convert
19832079

19842080
/// <summary>

0 commit comments

Comments
 (0)