Skip to content

[x64][SysV] Pass NO_CLASS eightbytes #104098

Open
@tomeksowi

Description

@tomeksowi

Off-shoot from #103799. Currently NO_CLASS eightbytes are reclassified as INTEGER:

// If we just finished checking the last byte of an eightbyte or the entire struct
if ((offset + 1) % SYSTEMV_EIGHT_BYTE_SIZE_IN_BYTES == 0 || (offset + 1) == helperPtr->structSize)
{
if (!foundFieldInEightByte)
{
// If we didn't find a field in an eightbyte (i.e. there are no explicit offsets that start a field in this eightbyte)
// then the classification of this eightbyte might be NoClass. We can't hand a classification of NoClass to the JIT
// so set the class to Integer (as though the struct has a char[8] padding) if the class is NoClass.
//
// TODO: Fix JIT, NoClass eightbytes are valid and passing them is broken because of this.
if (helperPtr->eightByteClassifications[offset / SYSTEMV_EIGHT_BYTE_SIZE_IN_BYTES] == SystemVClassificationTypeNoClass)
{
helperPtr->eightByteClassifications[offset / SYSTEMV_EIGHT_BYTE_SIZE_IN_BYTES] = SystemVClassificationTypeInteger;
}
}
foundFieldInEightByte = false;
}

System V ABI does not allow such reclassification, NO_CLASS eightbytes are valid for passing to a function. The difference is an INTEGER eightbyte gets assigned an integer argument register for passing; a NO_CLASS eightbyte doesn't get any register assigned. So the reclassification causes a mismatch for subsequent integer arguments.

Note: there's a silent requirement that .NET structs with explicit layouts or manually defined sizes have 'significant' padding. Care should be taken to preserve such padding to maintain backwards compatibility. More in #71711 discussion.

cc @dotnet/samsung

Metadata

Metadata

Assignees

Labels

Priority:2Work that is important, but not critical for the releasearea-CodeGen-coreclrCLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMI

Type

No type

Projects

No projects

Relationships

None yet

Development

No branches or pull requests

Issue actions