Skip to content

Commit b93061a

Browse files
authored
Arm64/SVE: Implemented RoundAwayFromZero, RoundToNearest, RouteToNegativeInfininty, RoundToPositiveInfinity, RoundToZero (#103588)
* Added ConverToInt32 and ConvertToUInt32 for float inputs. * Added flags to handle only low predicate registers. * Fix whitespace * Remove special codegen flag * Added new test template for operations with different return types. * Add new test template. * Added api for ConvertToInt32 and ConvertToUInt 32 for double. * Round SVE intrinsics for floats. * Completed Round SVE fp apis.
1 parent 547e69e commit b93061a

File tree

5 files changed

+237
-0
lines changed

5 files changed

+237
-0
lines changed

src/coreclr/jit/hwintrinsiclistarm64sve.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -169,6 +169,11 @@ HARDWARE_INTRINSIC(Sve, ReverseElement,
169169
HARDWARE_INTRINSIC(Sve, ReverseElement16, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_revh, INS_sve_revh, INS_sve_revh, INS_sve_revh, INS_invalid, INS_invalid}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
170170
HARDWARE_INTRINSIC(Sve, ReverseElement32, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_revw, INS_sve_revw, INS_invalid, INS_invalid}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
171171
HARDWARE_INTRINSIC(Sve, ReverseElement8, -1, -1, false, {INS_invalid, INS_invalid, INS_sve_revb, INS_sve_revb, INS_sve_revb, INS_sve_revb, INS_sve_revb, INS_sve_revb, INS_invalid, INS_invalid}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
172+
HARDWARE_INTRINSIC(Sve, RoundAwayFromZero, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_frinta, INS_sve_frinta}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_EmbeddedMaskedOperation|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
173+
HARDWARE_INTRINSIC(Sve, RoundToNearest, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_frintn, INS_sve_frintn}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_EmbeddedMaskedOperation|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
174+
HARDWARE_INTRINSIC(Sve, RoundToNegativeInfinity, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_frintm, INS_sve_frintm}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_EmbeddedMaskedOperation|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
175+
HARDWARE_INTRINSIC(Sve, RoundToPositiveInfinity, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_frintp, INS_sve_frintp}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_EmbeddedMaskedOperation|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
176+
HARDWARE_INTRINSIC(Sve, RoundToZero, -1, -1, false, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_frintz, INS_sve_frintz}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_EmbeddedMaskedOperation|HW_Flag_EmbeddedMaskedOperation|HW_Flag_LowMaskedOperation)
172177
HARDWARE_INTRINSIC(Sve, SaturatingDecrementBy16BitElementCount, -1, 3, true, {INS_invalid, INS_invalid, INS_sve_sqdech, INS_sve_uqdech, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_HasImmediateOperand|HW_Flag_HasEnumOperand|HW_Flag_SpecialCodeGen|HW_Flag_HasScalarInputVariant|HW_Flag_SpecialImport|HW_Flag_HasRMWSemantics)
173178
HARDWARE_INTRINSIC(Sve, SaturatingDecrementBy32BitElementCount, -1, 3, true, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_sqdecw, INS_sve_uqdecw, INS_invalid, INS_invalid, INS_invalid, INS_invalid}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_HasImmediateOperand|HW_Flag_HasEnumOperand|HW_Flag_SpecialCodeGen|HW_Flag_HasScalarInputVariant|HW_Flag_SpecialImport|HW_Flag_HasRMWSemantics)
174179
HARDWARE_INTRINSIC(Sve, SaturatingDecrementBy64BitElementCount, -1, 3, true, {INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_invalid, INS_sve_sqdecd, INS_sve_uqdecd, INS_invalid, INS_invalid}, HW_Category_SIMD, HW_Flag_Scalable|HW_Flag_HasImmediateOperand|HW_Flag_HasEnumOperand|HW_Flag_SpecialCodeGen|HW_Flag_HasScalarInputVariant|HW_Flag_SpecialImport|HW_Flag_HasRMWSemantics)

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

Lines changed: 105 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4351,6 +4351,111 @@ internal Arm64() { }
43514351
public static unsafe Vector<ulong> ReverseElement8(Vector<ulong> value) { throw new PlatformNotSupportedException(); }
43524352

43534353

4354+
/// RoundAwayFromZero : Round to nearest, ties away from zero
4355+
4356+
/// <summary>
4357+
/// svfloat64_t svrinta[_f64]_m(svfloat64_t inactive, svbool_t pg, svfloat64_t op)
4358+
/// FRINTA Ztied.D, Pg/M, Zop.D
4359+
/// svfloat64_t svrinta[_f64]_x(svbool_t pg, svfloat64_t op)
4360+
/// FRINTA Ztied.D, Pg/M, Ztied.D
4361+
/// svfloat64_t svrinta[_f64]_z(svbool_t pg, svfloat64_t op)
4362+
/// </summary>
4363+
public static unsafe Vector<double> RoundAwayFromZero(Vector<double> value) { throw new PlatformNotSupportedException(); }
4364+
4365+
/// <summary>
4366+
/// svfloat32_t svrinta[_f32]_m(svfloat32_t inactive, svbool_t pg, svfloat32_t op)
4367+
/// FRINTA Ztied.S, Pg/M, Zop.S
4368+
/// svfloat32_t svrinta[_f32]_x(svbool_t pg, svfloat32_t op)
4369+
/// FRINTA Ztied.S, Pg/M, Ztied.S
4370+
/// svfloat32_t svrinta[_f32]_z(svbool_t pg, svfloat32_t op)
4371+
/// </summary>
4372+
public static unsafe Vector<float> RoundAwayFromZero(Vector<float> value) { throw new PlatformNotSupportedException(); }
4373+
4374+
4375+
/// RoundToNearest : Round to nearest, ties to even
4376+
4377+
/// <summary>
4378+
/// svfloat64_t svrintn[_f64]_m(svfloat64_t inactive, svbool_t pg, svfloat64_t op)
4379+
/// FRINTN Ztied.D, Pg/M, Zop.D
4380+
/// svfloat64_t svrintn[_f64]_x(svbool_t pg, svfloat64_t op)
4381+
/// FRINTN Ztied.D, Pg/M, Ztied.D
4382+
/// svfloat64_t svrintn[_f64]_z(svbool_t pg, svfloat64_t op)
4383+
/// </summary>
4384+
public static unsafe Vector<double> RoundToNearest(Vector<double> value) { throw new PlatformNotSupportedException(); }
4385+
4386+
/// <summary>
4387+
/// svfloat32_t svrintn[_f32]_m(svfloat32_t inactive, svbool_t pg, svfloat32_t op)
4388+
/// FRINTN Ztied.S, Pg/M, Zop.S
4389+
/// svfloat32_t svrintn[_f32]_x(svbool_t pg, svfloat32_t op)
4390+
/// FRINTN Ztied.S, Pg/M, Ztied.S
4391+
/// svfloat32_t svrintn[_f32]_z(svbool_t pg, svfloat32_t op)
4392+
/// </summary>
4393+
public static unsafe Vector<float> RoundToNearest(Vector<float> value) { throw new PlatformNotSupportedException(); }
4394+
4395+
4396+
/// RoundToNegativeInfinity : Round towards -∞
4397+
4398+
/// <summary>
4399+
/// svfloat64_t svrintm[_f64]_m(svfloat64_t inactive, svbool_t pg, svfloat64_t op)
4400+
/// FRINTM Ztied.D, Pg/M, Zop.D
4401+
/// svfloat64_t svrintm[_f64]_x(svbool_t pg, svfloat64_t op)
4402+
/// FRINTM Ztied.D, Pg/M, Ztied.D
4403+
/// svfloat64_t svrintm[_f64]_z(svbool_t pg, svfloat64_t op)
4404+
/// </summary>
4405+
public static unsafe Vector<double> RoundToNegativeInfinity(Vector<double> value) { throw new PlatformNotSupportedException(); }
4406+
4407+
/// <summary>
4408+
/// svfloat32_t svrintm[_f32]_m(svfloat32_t inactive, svbool_t pg, svfloat32_t op)
4409+
/// FRINTM Ztied.S, Pg/M, Zop.S
4410+
/// svfloat32_t svrintm[_f32]_x(svbool_t pg, svfloat32_t op)
4411+
/// FRINTM Ztied.S, Pg/M, Ztied.S
4412+
/// svfloat32_t svrintm[_f32]_z(svbool_t pg, svfloat32_t op)
4413+
/// </summary>
4414+
public static unsafe Vector<float> RoundToNegativeInfinity(Vector<float> value) { throw new PlatformNotSupportedException(); }
4415+
4416+
4417+
/// RoundToPositiveInfinity : Round towards +∞
4418+
4419+
/// <summary>
4420+
/// svfloat64_t svrintp[_f64]_m(svfloat64_t inactive, svbool_t pg, svfloat64_t op)
4421+
/// FRINTP Ztied.D, Pg/M, Zop.D
4422+
/// svfloat64_t svrintp[_f64]_x(svbool_t pg, svfloat64_t op)
4423+
/// FRINTP Ztied.D, Pg/M, Ztied.D
4424+
/// svfloat64_t svrintp[_f64]_z(svbool_t pg, svfloat64_t op)
4425+
/// </summary>
4426+
public static unsafe Vector<double> RoundToPositiveInfinity(Vector<double> value) { throw new PlatformNotSupportedException(); }
4427+
4428+
/// <summary>
4429+
/// svfloat32_t svrintp[_f32]_m(svfloat32_t inactive, svbool_t pg, svfloat32_t op)
4430+
/// FRINTP Ztied.S, Pg/M, Zop.S
4431+
/// svfloat32_t svrintp[_f32]_x(svbool_t pg, svfloat32_t op)
4432+
/// FRINTP Ztied.S, Pg/M, Ztied.S
4433+
/// svfloat32_t svrintp[_f32]_z(svbool_t pg, svfloat32_t op)
4434+
/// </summary>
4435+
public static unsafe Vector<float> RoundToPositiveInfinity(Vector<float> value) { throw new PlatformNotSupportedException(); }
4436+
4437+
4438+
/// RoundToZero : Round towards zero
4439+
4440+
/// <summary>
4441+
/// svfloat64_t svrintz[_f64]_m(svfloat64_t inactive, svbool_t pg, svfloat64_t op)
4442+
/// FRINTZ Ztied.D, Pg/M, Zop.D
4443+
/// svfloat64_t svrintz[_f64]_x(svbool_t pg, svfloat64_t op)
4444+
/// FRINTZ Ztied.D, Pg/M, Ztied.D
4445+
/// svfloat64_t svrintz[_f64]_z(svbool_t pg, svfloat64_t op)
4446+
/// </summary>
4447+
public static unsafe Vector<double> RoundToZero(Vector<double> value) { throw new PlatformNotSupportedException(); }
4448+
4449+
/// <summary>
4450+
/// svfloat32_t svrintz[_f32]_m(svfloat32_t inactive, svbool_t pg, svfloat32_t op)
4451+
/// FRINTZ Ztied.S, Pg/M, Zop.S
4452+
/// svfloat32_t svrintz[_f32]_x(svbool_t pg, svfloat32_t op)
4453+
/// FRINTZ Ztied.S, Pg/M, Ztied.S
4454+
/// svfloat32_t svrintz[_f32]_z(svbool_t pg, svfloat32_t op)
4455+
/// </summary>
4456+
public static unsafe Vector<float> RoundToZero(Vector<float> value) { throw new PlatformNotSupportedException(); }
4457+
4458+
43544459
/// Saturating decrement by number of halfword elements
43554460

43564461
/// <summary>

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

Lines changed: 105 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4405,6 +4405,111 @@ internal Arm64() { }
44054405
public static unsafe Vector<ulong> ReverseElement8(Vector<ulong> value) => ReverseElement8(value);
44064406

44074407

4408+
/// RoundAwayFromZero : Round to nearest, ties away from zero
4409+
4410+
/// <summary>
4411+
/// svfloat64_t svrinta[_f64]_m(svfloat64_t inactive, svbool_t pg, svfloat64_t op)
4412+
/// FRINTA Ztied.D, Pg/M, Zop.D
4413+
/// svfloat64_t svrinta[_f64]_x(svbool_t pg, svfloat64_t op)
4414+
/// FRINTA Ztied.D, Pg/M, Ztied.D
4415+
/// svfloat64_t svrinta[_f64]_z(svbool_t pg, svfloat64_t op)
4416+
/// </summary>
4417+
public static unsafe Vector<double> RoundAwayFromZero(Vector<double> value) => RoundAwayFromZero(value);
4418+
4419+
/// <summary>
4420+
/// svfloat32_t svrinta[_f32]_m(svfloat32_t inactive, svbool_t pg, svfloat32_t op)
4421+
/// FRINTA Ztied.S, Pg/M, Zop.S
4422+
/// svfloat32_t svrinta[_f32]_x(svbool_t pg, svfloat32_t op)
4423+
/// FRINTA Ztied.S, Pg/M, Ztied.S
4424+
/// svfloat32_t svrinta[_f32]_z(svbool_t pg, svfloat32_t op)
4425+
/// </summary>
4426+
public static unsafe Vector<float> RoundAwayFromZero(Vector<float> value) => RoundAwayFromZero(value);
4427+
4428+
4429+
/// RoundToNearest : Round to nearest, ties to even
4430+
4431+
/// <summary>
4432+
/// svfloat64_t svrintn[_f64]_m(svfloat64_t inactive, svbool_t pg, svfloat64_t op)
4433+
/// FRINTN Ztied.D, Pg/M, Zop.D
4434+
/// svfloat64_t svrintn[_f64]_x(svbool_t pg, svfloat64_t op)
4435+
/// FRINTN Ztied.D, Pg/M, Ztied.D
4436+
/// svfloat64_t svrintn[_f64]_z(svbool_t pg, svfloat64_t op)
4437+
/// </summary>
4438+
public static unsafe Vector<double> RoundToNearest(Vector<double> value) => RoundToNearest(value);
4439+
4440+
/// <summary>
4441+
/// svfloat32_t svrintn[_f32]_m(svfloat32_t inactive, svbool_t pg, svfloat32_t op)
4442+
/// FRINTN Ztied.S, Pg/M, Zop.S
4443+
/// svfloat32_t svrintn[_f32]_x(svbool_t pg, svfloat32_t op)
4444+
/// FRINTN Ztied.S, Pg/M, Ztied.S
4445+
/// svfloat32_t svrintn[_f32]_z(svbool_t pg, svfloat32_t op)
4446+
/// </summary>
4447+
public static unsafe Vector<float> RoundToNearest(Vector<float> value) => RoundToNearest(value);
4448+
4449+
4450+
/// RoundToNegativeInfinity : Round towards -∞
4451+
4452+
/// <summary>
4453+
/// svfloat64_t svrintm[_f64]_m(svfloat64_t inactive, svbool_t pg, svfloat64_t op)
4454+
/// FRINTM Ztied.D, Pg/M, Zop.D
4455+
/// svfloat64_t svrintm[_f64]_x(svbool_t pg, svfloat64_t op)
4456+
/// FRINTM Ztied.D, Pg/M, Ztied.D
4457+
/// svfloat64_t svrintm[_f64]_z(svbool_t pg, svfloat64_t op)
4458+
/// </summary>
4459+
public static unsafe Vector<double> RoundToNegativeInfinity(Vector<double> value) => RoundToNegativeInfinity(value);
4460+
4461+
/// <summary>
4462+
/// svfloat32_t svrintm[_f32]_m(svfloat32_t inactive, svbool_t pg, svfloat32_t op)
4463+
/// FRINTM Ztied.S, Pg/M, Zop.S
4464+
/// svfloat32_t svrintm[_f32]_x(svbool_t pg, svfloat32_t op)
4465+
/// FRINTM Ztied.S, Pg/M, Ztied.S
4466+
/// svfloat32_t svrintm[_f32]_z(svbool_t pg, svfloat32_t op)
4467+
/// </summary>
4468+
public static unsafe Vector<float> RoundToNegativeInfinity(Vector<float> value) => RoundToNegativeInfinity(value);
4469+
4470+
4471+
/// RoundToPositiveInfinity : Round towards +∞
4472+
4473+
/// <summary>
4474+
/// svfloat64_t svrintp[_f64]_m(svfloat64_t inactive, svbool_t pg, svfloat64_t op)
4475+
/// FRINTP Ztied.D, Pg/M, Zop.D
4476+
/// svfloat64_t svrintp[_f64]_x(svbool_t pg, svfloat64_t op)
4477+
/// FRINTP Ztied.D, Pg/M, Ztied.D
4478+
/// svfloat64_t svrintp[_f64]_z(svbool_t pg, svfloat64_t op)
4479+
/// </summary>
4480+
public static unsafe Vector<double> RoundToPositiveInfinity(Vector<double> value) => RoundToPositiveInfinity(value);
4481+
4482+
/// <summary>
4483+
/// svfloat32_t svrintp[_f32]_m(svfloat32_t inactive, svbool_t pg, svfloat32_t op)
4484+
/// FRINTP Ztied.S, Pg/M, Zop.S
4485+
/// svfloat32_t svrintp[_f32]_x(svbool_t pg, svfloat32_t op)
4486+
/// FRINTP Ztied.S, Pg/M, Ztied.S
4487+
/// svfloat32_t svrintp[_f32]_z(svbool_t pg, svfloat32_t op)
4488+
/// </summary>
4489+
public static unsafe Vector<float> RoundToPositiveInfinity(Vector<float> value) => RoundToPositiveInfinity(value);
4490+
4491+
4492+
/// RoundToZero : Round towards zero
4493+
4494+
/// <summary>
4495+
/// svfloat64_t svrintz[_f64]_m(svfloat64_t inactive, svbool_t pg, svfloat64_t op)
4496+
/// FRINTZ Ztied.D, Pg/M, Zop.D
4497+
/// svfloat64_t svrintz[_f64]_x(svbool_t pg, svfloat64_t op)
4498+
/// FRINTZ Ztied.D, Pg/M, Ztied.D
4499+
/// svfloat64_t svrintz[_f64]_z(svbool_t pg, svfloat64_t op)
4500+
/// </summary>
4501+
public static unsafe Vector<double> RoundToZero(Vector<double> value) => RoundToZero(value);
4502+
4503+
/// <summary>
4504+
/// svfloat32_t svrintz[_f32]_m(svfloat32_t inactive, svbool_t pg, svfloat32_t op)
4505+
/// FRINTZ Ztied.S, Pg/M, Zop.S
4506+
/// svfloat32_t svrintz[_f32]_x(svbool_t pg, svfloat32_t op)
4507+
/// FRINTZ Ztied.S, Pg/M, Ztied.S
4508+
/// svfloat32_t svrintz[_f32]_z(svbool_t pg, svfloat32_t op)
4509+
/// </summary>
4510+
public static unsafe Vector<float> RoundToZero(Vector<float> value) => RoundToZero(value);
4511+
4512+
44084513
/// Saturating decrement by number of halfword elements
44094514

44104515
/// <summary>

src/libraries/System.Runtime.Intrinsics/ref/System.Runtime.Intrinsics.cs

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4816,6 +4816,17 @@ internal Arm64() { }
48164816
public static System.Numerics.Vector<uint> ReverseElement8(System.Numerics.Vector<uint> value) { throw null; }
48174817
public static System.Numerics.Vector<ulong> ReverseElement8(System.Numerics.Vector<ulong> value) { throw null; }
48184818

4819+
public static System.Numerics.Vector<double> RoundAwayFromZero(System.Numerics.Vector<double> value) { throw null; }
4820+
public static System.Numerics.Vector<float> RoundAwayFromZero(System.Numerics.Vector<float> value) { throw null; }
4821+
public static System.Numerics.Vector<double> RoundToNearest(System.Numerics.Vector<double> value) { throw null; }
4822+
public static System.Numerics.Vector<float> RoundToNearest(System.Numerics.Vector<float> value) { throw null; }
4823+
public static System.Numerics.Vector<double> RoundToNegativeInfinity(System.Numerics.Vector<double> value) { throw null; }
4824+
public static System.Numerics.Vector<float> RoundToNegativeInfinity(System.Numerics.Vector<float> value) { throw null; }
4825+
public static System.Numerics.Vector<double> RoundToPositiveInfinity(System.Numerics.Vector<double> value) { throw null; }
4826+
public static System.Numerics.Vector<float> RoundToPositiveInfinity(System.Numerics.Vector<float> value) { throw null; }
4827+
public static System.Numerics.Vector<double> RoundToZero(System.Numerics.Vector<double> value) { throw null; }
4828+
public static System.Numerics.Vector<float> RoundToZero(System.Numerics.Vector<float> value) { throw null; }
4829+
48194830
public static int SaturatingDecrementBy16BitElementCount(int value, [ConstantExpected(Min = 1, Max = (byte)(16))] byte scale, [ConstantExpected] SveMaskPattern pattern = SveMaskPattern.All) { throw null; }
48204831
public static long SaturatingDecrementBy16BitElementCount(long value, [ConstantExpected(Min = 1, Max = (byte)(16))] byte scale, [ConstantExpected] SveMaskPattern pattern = SveMaskPattern.All) { throw null; }
48214832
public static uint SaturatingDecrementBy16BitElementCount(uint value, [ConstantExpected(Min = 1, Max = (byte)(16))] byte scale, [ConstantExpected] SveMaskPattern pattern = SveMaskPattern.All) { throw null; }

0 commit comments

Comments
 (0)