-
Notifications
You must be signed in to change notification settings - Fork 5.5k
Expand file tree
/
Copy pathRuntime_69472.cs
More file actions
109 lines (90 loc) · 3.26 KB
/
Copy pathRuntime_69472.cs
File metadata and controls
109 lines (90 loc) · 3.26 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
namespace Runtime_69472;
using System;
using System.Runtime.CompilerServices;
using Xunit;
// Validates the fgOptimizeCast extension that looks through GT_COMMA wrappers
// to fold `CAST<small>(COMMA(side-effects, IND<small-same-size>))` into
// `COMMA(side-effects, IND<castToType>)`. The common shape is
// `(sbyte)span[i]` which previously emitted a zero-extending load followed by
// a sign-extending cast and should now collapse to a single `movsx` (or
// equivalently `movzx`) load.
//
// Correctness must hold across signed/unsigned source-and-target combinations
// and across all relevant integer values for the small type.
public class Runtime_69472
{
[MethodImpl(MethodImplOptions.NoInlining)]
private static int SbyteFromByteArr(byte[] a, int i) => (sbyte)a[i];
[MethodImpl(MethodImplOptions.NoInlining)]
private static int ByteFromSbyteArr(sbyte[] a, int i) => (byte)a[i];
[MethodImpl(MethodImplOptions.NoInlining)]
private static int ShortFromUshortArr(ushort[] a, int i) => (short)a[i];
[MethodImpl(MethodImplOptions.NoInlining)]
private static int UshortFromShortArr(short[] a, int i) => (ushort)a[i];
[MethodImpl(MethodImplOptions.NoInlining)]
private static int SbyteFromReadOnlySpan(ReadOnlySpan<byte> s, int i) => (sbyte)s[i];
[MethodImpl(MethodImplOptions.NoInlining)]
private static unsafe int SbyteFromPointer(byte* p) => (sbyte)*p;
[MethodImpl(MethodImplOptions.NoInlining)]
private static int SbyteFromByteField(Boxed b) => (sbyte)b._value;
private sealed class Boxed
{
public byte _value;
}
[Fact]
public static int TestEntryPoint()
{
bool ok = true;
for (int v = 0; v < 256; v++)
{
byte b = (byte)v;
sbyte sb = unchecked((sbyte)v);
byte[] ba = new[] { b };
sbyte[] sba = new[] { sb };
int expSbyteFromByte = unchecked((sbyte)b);
int expByteFromSbyte = (byte)sb;
if (SbyteFromByteArr(ba, 0) != expSbyteFromByte)
{
ok = false;
}
if (ByteFromSbyteArr(sba, 0) != expByteFromSbyte)
{
ok = false;
}
if (SbyteFromReadOnlySpan(ba, 0) != expSbyteFromByte)
{
ok = false;
}
if (SbyteFromByteField(new Boxed { _value = b }) != expSbyteFromByte)
{
ok = false;
}
unsafe
{
byte bb = b;
if (SbyteFromPointer(&bb) != expSbyteFromByte)
{
ok = false;
}
}
}
for (int v = 0; v <= 0xFFFF; v++)
{
ushort uw = (ushort)v;
short sw = unchecked((short)v);
ushort[] ua = new[] { uw };
short[] sa = new[] { sw };
if (ShortFromUshortArr(ua, 0) != unchecked((short)uw))
{
ok = false;
}
if (UshortFromShortArr(sa, 0) != (ushort)sw)
{
ok = false;
}
}
return ok ? 100 : 1;
}
}