Skip to content

impNormStructVal's OBJ(ADDR(LCL_VAR)) wrapping logic can be too permissive #69965

@SingleAccretion

Description

@SingleAccretion

Reproduction:

using System.Runtime.Intrinsics;
using System.Runtime.CompilerServices;

Problem(new StructWithOverlappedVtor128[1]);

[MethodImpl(MethodImplOptions.NoInlining | MethodImplOptions.AggressiveOptimization)]
private static void Problem(StructWithOverlappedVtor128[] a)
{
    static Vector128<int> Tunnel(StructWithOverlappedVtor128[] a) => a[0].Vtor;

    CallForVtor(Tunnel(a));
}

[StructLayout(LayoutKind.Explicit)]
struct StructWithOverlappedVtor128
{
    [FieldOffset(1)]
    public Vector128<int> Vtor;
    [FieldOffset(1)]
    public Vector128<uint> AnotherVtor;
}

[MethodImpl(MethodImplOptions.NoInlining)]
static void CallForVtor(Vector128<int> value) { }

Run with a checked Jit.

Expected result: program exists successfully.

Actual result:

Assert failure(PID 10988 [0x00002aec], Thread: 23524 [0x5be4]): Assertion failed 'structHnd != NO_CLASS_HANDLE' in 'RyuJitReproduction.Program:Problem(RyuJitReproduction.Program+StructWithOverlappedVtor128[])' during 'Morph - Global' (IL size 12; hash 0x5e9882cb; FullOpts)

    File: C:\Users\Accretion\source\dotnet\runtime\src\coreclr\jit\gentree.cpp Line: 17169
    Image: C:\Users\Accretion\source\dotnet\runtime\artifacts\tests\coreclr\windows.x64.Checked\Tests\Core_Root\CoreRun.exe

There are multiple layers of problems which ultimately lead to this.

1) impNormStructVal sometimes does not wrap makeTemp locals in OBJ(ADDR):

if ((forceNormalization || (structType == TYP_STRUCT)) && !structVal->OperIsBlk())
{
    // Wrap it in a GT_OBJ
    structVal = gtNewObjNode(structHnd, gtNewOperNode(GT_ADDR, TYP_BYREF, structVal));
}

2) FIELD morphing loses the handle when it dissolves the node into an IND struct.
3) Args morphing relies on being able to acquire the struct handle from a SIMD-typed node.
4) The logic in gtGetStructHandleIfPresent tries to get the handle for Vector128<float> if it cannot find anything else. This is a workaround that simply does not work.

Metadata

Metadata

Labels

area-CodeGen-coreclrCLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMIbug

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions