Skip to content

Commit

Permalink
Ensure VN handles both forms of the xarch shift instructions for SIMD (
Browse files Browse the repository at this point in the history
  • Loading branch information
tannergooding authored Sep 19, 2023
1 parent 3b9b4fd commit 41a8e39
Show file tree
Hide file tree
Showing 3 changed files with 98 additions and 0 deletions.
60 changes: 60 additions & 0 deletions src/coreclr/jit/valuenum.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7432,6 +7432,26 @@ ValueNum ValueNumStore::EvalHWIntrinsicFunBinary(var_types type,
case NI_AVX512BW_ShiftLeftLogical:
#endif
{
#ifdef TARGET_XARCH
if (TypeOfVN(arg1VN) == TYP_SIMD16)
{
// The xarch shift instructions support taking the shift amount as
// a simd16, in which case they take the shift amount from the lower
// 64-bits.

uint64_t shiftAmount = GetConstantSimd16(arg1VN).u64[0];

if (genTypeSize(baseType) != 8)
{
arg1VN = VNForIntCon(static_cast<int32_t>(shiftAmount));
}
else
{
arg1VN = VNForLongCon(static_cast<int64_t>(shiftAmount));
}
}
#endif // TARGET_XARCH

return EvaluateBinarySimd(this, GT_LSH, /* scalar */ false, type, baseType, arg0VN, arg1VN);
}

Expand All @@ -7445,6 +7465,26 @@ ValueNum ValueNumStore::EvalHWIntrinsicFunBinary(var_types type,
case NI_AVX512BW_ShiftRightArithmetic:
#endif
{
#ifdef TARGET_XARCH
if (TypeOfVN(arg1VN) == TYP_SIMD16)
{
// The xarch shift instructions support taking the shift amount as
// a simd16, in which case they take the shift amount from the lower
// 64-bits.

uint64_t shiftAmount = GetConstantSimd16(arg1VN).u64[0];

if (genTypeSize(baseType) != 8)
{
arg1VN = VNForIntCon(static_cast<int32_t>(shiftAmount));
}
else
{
arg1VN = VNForLongCon(static_cast<int64_t>(shiftAmount));
}
}
#endif // TARGET_XARCH

return EvaluateBinarySimd(this, GT_RSH, /* scalar */ false, type, baseType, arg0VN, arg1VN);
}

Expand All @@ -7457,6 +7497,26 @@ ValueNum ValueNumStore::EvalHWIntrinsicFunBinary(var_types type,
case NI_AVX512BW_ShiftRightLogical:
#endif
{
#ifdef TARGET_XARCH
if (TypeOfVN(arg1VN) == TYP_SIMD16)
{
// The xarch shift instructions support taking the shift amount as
// a simd16, in which case they take the shift amount from the lower
// 64-bits.

uint64_t shiftAmount = GetConstantSimd16(arg1VN).u64[0];

if (genTypeSize(baseType) != 8)
{
arg1VN = VNForIntCon(static_cast<int32_t>(shiftAmount));
}
else
{
arg1VN = VNForLongCon(static_cast<int64_t>(shiftAmount));
}
}
#endif // TARGET_XARCH

return EvaluateBinarySimd(this, GT_RSZ, /* scalar */ false, type, baseType, arg0VN, arg1VN);
}

Expand Down
30 changes: 30 additions & 0 deletions src/tests/JIT/Regression/JitBlue/Runtime_91175/Runtime_91175.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.aa

using System.Runtime.CompilerServices;
using System.Runtime.Intrinsics;
using System.Runtime.Intrinsics.X86;
using Xunit;

public class TestClass
{
[MethodImpl(MethodImplOptions.NoInlining)]
public static Vector256<int> Method0() => Avx2.ShiftRightArithmetic(Vector256<int>.AllBitsSet, Vector128<int>.AllBitsSet);

[MethodImpl(MethodImplOptions.NoInlining)]
public static Vector128<int> Method1() => Sse2.ShiftRightArithmetic(Vector128<int>.AllBitsSet, Vector128<int>.AllBitsSet);

[Fact]
public static void TestEntryPoint()
{
if (Avx2.IsSupported)
{
_ = Method0();
}

if (Sse2.IsSupported)
{
_ = Method1();
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<Optimize>True</Optimize>
</PropertyGroup>
<ItemGroup>
<Compile Include="$(MSBuildProjectName).cs" />
</ItemGroup>
</Project>

0 comments on commit 41a8e39

Please sign in to comment.