From f40173de7b43f9014aadd33f46a8a170fb8aa05c Mon Sep 17 00:00:00 2001 From: Filip Navara Date: Sat, 3 Feb 2024 12:13:44 +0100 Subject: [PATCH 1/2] Mark unaligned reads in NativeFormatReader as unaligned for the JIT --- .../src/System/Runtime/CompilerServices/Unsafe.cs | 10 ++++++++++ .../NativeFormat/NativeFormatReader.Primitives.cs | 7 ++++--- 2 files changed, 14 insertions(+), 3 deletions(-) diff --git a/src/coreclr/nativeaot/Runtime.Base/src/System/Runtime/CompilerServices/Unsafe.cs b/src/coreclr/nativeaot/Runtime.Base/src/System/Runtime/CompilerServices/Unsafe.cs index 7c77d12b7cc38..d45340d22d0d9 100644 --- a/src/coreclr/nativeaot/Runtime.Base/src/System/Runtime/CompilerServices/Unsafe.cs +++ b/src/coreclr/nativeaot/Runtime.Base/src/System/Runtime/CompilerServices/Unsafe.cs @@ -109,5 +109,15 @@ public static ref T AsRef(in T source) { throw new PlatformNotSupportedException(); } + + /// + /// Reads a value of type from the given location. + /// + [Intrinsic] + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static T ReadUnaligned(ref readonly byte source) + { + throw new PlatformNotSupportedException(); + } } } diff --git a/src/coreclr/tools/Common/Internal/NativeFormat/NativeFormatReader.Primitives.cs b/src/coreclr/tools/Common/Internal/NativeFormat/NativeFormatReader.Primitives.cs index 7f7a8ebdcec53..0b979008f5ee6 100644 --- a/src/coreclr/tools/Common/Internal/NativeFormat/NativeFormatReader.Primitives.cs +++ b/src/coreclr/tools/Common/Internal/NativeFormat/NativeFormatReader.Primitives.cs @@ -8,6 +8,7 @@ // --------------------------------------------------------------------------- using System.Diagnostics; +using System.Runtime.CompilerServices; namespace Internal.NativeFormat { @@ -23,21 +24,21 @@ public static byte ReadUInt8(ref byte* stream) public static ushort ReadUInt16(ref byte* stream) { - ushort result = *(ushort*)(stream); // Assumes little endian and unaligned access + ushort result = Unsafe.ReadUnaligned(ref *stream); // Assumes little endian and unaligned access stream += 2; return result; } public static uint ReadUInt32(ref byte* stream) { - uint result = *(uint*)(stream); // Assumes little endian and unaligned access + uint result = Unsafe.ReadUnaligned(ref *stream); // Assumes little endian and unaligned access stream += 4; return result; } public static ulong ReadUInt64(ref byte* stream) { - ulong result = *(ulong*)(stream); // Assumes little endian and unaligned access + ulong result = Unsafe.ReadUnaligned(ref *stream); // Assumes little endian and unaligned access stream += 8; return result; } From 972ca8e64bc948f65cbf80c50f46b7937e7a7770 Mon Sep 17 00:00:00 2001 From: Filip Navara Date: Sat, 3 Feb 2024 12:43:27 +0100 Subject: [PATCH 2/2] Better fix --- .../src/System/Runtime/CompilerServices/Unsafe.cs | 2 +- .../Internal/NativeFormat/NativeFormatReader.Primitives.cs | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/coreclr/nativeaot/Runtime.Base/src/System/Runtime/CompilerServices/Unsafe.cs b/src/coreclr/nativeaot/Runtime.Base/src/System/Runtime/CompilerServices/Unsafe.cs index d45340d22d0d9..136872edd4a47 100644 --- a/src/coreclr/nativeaot/Runtime.Base/src/System/Runtime/CompilerServices/Unsafe.cs +++ b/src/coreclr/nativeaot/Runtime.Base/src/System/Runtime/CompilerServices/Unsafe.cs @@ -115,7 +115,7 @@ public static ref T AsRef(in T source) /// [Intrinsic] [MethodImpl(MethodImplOptions.AggressiveInlining)] - public static T ReadUnaligned(ref readonly byte source) + public static T ReadUnaligned(void* source) { throw new PlatformNotSupportedException(); } diff --git a/src/coreclr/tools/Common/Internal/NativeFormat/NativeFormatReader.Primitives.cs b/src/coreclr/tools/Common/Internal/NativeFormat/NativeFormatReader.Primitives.cs index 0b979008f5ee6..b0d0551735562 100644 --- a/src/coreclr/tools/Common/Internal/NativeFormat/NativeFormatReader.Primitives.cs +++ b/src/coreclr/tools/Common/Internal/NativeFormat/NativeFormatReader.Primitives.cs @@ -24,21 +24,21 @@ public static byte ReadUInt8(ref byte* stream) public static ushort ReadUInt16(ref byte* stream) { - ushort result = Unsafe.ReadUnaligned(ref *stream); // Assumes little endian and unaligned access + ushort result = Unsafe.ReadUnaligned(stream); // Assumes little endian and unaligned access stream += 2; return result; } public static uint ReadUInt32(ref byte* stream) { - uint result = Unsafe.ReadUnaligned(ref *stream); // Assumes little endian and unaligned access + uint result = Unsafe.ReadUnaligned(stream); // Assumes little endian and unaligned access stream += 4; return result; } public static ulong ReadUInt64(ref byte* stream) { - ulong result = Unsafe.ReadUnaligned(ref *stream); // Assumes little endian and unaligned access + ulong result = Unsafe.ReadUnaligned(stream); // Assumes little endian and unaligned access stream += 8; return result; }