if (varNode != nullptr)
{
assert(varNode->isContained());
- srcVarNum = varNode->GetLclNum();
-
- // handle promote situation
+ srcVarNum = varNode->GetLclNum();
LclVarDsc* varDsc = compiler->lvaGetDesc(srcVarNum);
- // This struct also must live in the stack frame
- // And it can't live in a register (SIMD)
- assert(varDsc->lvType == TYP_STRUCT);
+ // This struct also must live in the stack frame.
+ // And it can't live in a register.
assert(varDsc->lvOnFrame && !varDsc->lvRegister);
-
- // We don't split HFA struct
- assert(!varDsc->lvIsHfa());
}
else // addrNode is used
{
if (varNode != nullptr)
{
assert(varNode->isContained());
- srcVarNum = varNode->GetLclNum();
- assert(srcVarNum < compiler->lvaCount);
+ srcVarNum = varNode->GetLclNum();
+ LclVarDsc* varDsc = compiler->lvaGetDesc(srcVarNum);
- // handle promote situation
- LclVarDsc* varDsc = compiler->lvaTable + srcVarNum;
-
- // This struct also must live in the stack frame
- // And it can't live in a register (SIMD)
- assert(varDsc->lvType == TYP_STRUCT);
+ // This struct also must live in the stack frame.
+ // And it can't live in a register.
assert(varDsc->lvOnFrame && !varDsc->lvRegister);
-
- // We don't split HFA struct
- assert(!varDsc->lvIsHfa());
}
else // addrNode is used
{
{
private static readonly HfaUnion s_hfaDblFlt = new HfaUnion { DblHfa = { FirstDblValue = 1.0, SecondDblValue = 2.0 } };
private static readonly HfaDblLngUnion s_dblLngHfa = new HfaDblLngUnion { DblLng = { FirstLngValue = 10, SecondLngValue = 20 } };
+ private static readonly FourDblLngUnion s_fourDblLngHfa = new FourDblLngUnion { Lngs = { LongOne = 30 } };
public static int Main()
{
return 102;
}
+ if (ProblemWithSplitStructBlkMismatch())
+ {
+ return 103;
+ }
+
+ if (ProblemWithSplitStructHfaMismatch(s_fourDblLngHfa.Hfa))
+ {
+ return 104;
+ }
+
return 100;
}
}
[MethodImpl(MethodImplOptions.NoInlining)]
+ private static bool ProblemWithSplitStructBlkMismatch()
+ {
+ var blk = stackalloc byte[sizeof(StructWithFourLongs)];
+ var result = CallForSplitStructWithFourLongs(1, 1, *(StructWithFourLongs*)blk);
+
+ // The stackalloc should have been zeroed-out.
+ return result != 0;
+ }
+
+ [MethodImpl(MethodImplOptions.NoInlining)]
+ private static bool ProblemWithSplitStructHfaMismatch(FourDoublesHfaStruct fourDblHfa)
+ {
+ var result = CallForSplitStructWithFourLongs(1, 1, *(StructWithFourLongs*)&fourDblHfa);
+
+ return result != s_fourDblLngHfa.Lngs.LongOne;
+ }
+
+ [MethodImpl(MethodImplOptions.NoInlining)]
private static double CallForHfaDblStruct(HfaDblStruct value) => value.FirstDblValue;
+
+ [MethodImpl(MethodImplOptions.NoInlining)]
+ private static long CallForSplitStructWithFourLongs(int arg0, int arg1, StructWithFourLongs splitArg) => splitArg.LongOne;
}
[StructLayout(LayoutKind.Explicit)]
public HfaFltStruct FltHfa;
}
+[StructLayout(LayoutKind.Explicit)]
+struct FourDblLngUnion
+{
+ [FieldOffset(0)]
+ public FourDoublesHfaStruct Hfa;
+ [FieldOffset(0)]
+ public StructWithFourLongs Lngs;
+}
+
struct DblLngStruct
{
public long FirstLngValue;
public float ThirdFltValue;
public float FourthFltValue;
}
+
+struct StructWithFourLongs
+{
+ public long LongOne;
+ public long LongTwo;
+ public long LongThree;
+ public long LongFour;
+}
+
+struct FourDoublesHfaStruct
+{
+ public double FirstDblValue;
+ public double SecondDblValue;
+ public double ThirdDblValue;
+ public double FourthDblValue;
+}