namespace LyraApi; using System.Diagnostics.CodeAnalysis; using System.Runtime.InteropServices; public static class MarshalUtils { internal struct AlignmentHelper where T : unmanaged { #pragma warning disable CS0649 // Field is never assigned to, and will always have its default value 0 public byte Padding; public T Target; #pragma warning restore CS0649 // Field is never assigned to, and will always have its default value 0 } public static int AlignmentOf() where T : unmanaged { return (int)Marshal.OffsetOf>(nameof(AlignmentHelper.Target)); } public static byte[] GetBytes([DisallowNull] T data) { int size = Marshal.SizeOf(data); byte[] arr = new byte[size]; IntPtr ptr = IntPtr.Zero; try { ptr = Marshal.AllocHGlobal(size); Marshal.StructureToPtr(data, ptr, true); Marshal.Copy(ptr, arr, 0, size); } finally { Marshal.FreeHGlobal(ptr); } return arr; } public static T? FromBytes<[DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors)] T>(byte[] data) { var ptr = GCHandle.Alloc(data, GCHandleType.Pinned); try { //var res = (T?)Marshal.PtrToStructure(ptr.AddrOfPinnedObject(), typeof(T)); var res = Marshal.PtrToStructure(ptr.AddrOfPinnedObject()); return res; } finally { ptr.Free(); } } }