ByteStructConverter.cs 2.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Text;
  5. using System.Runtime.InteropServices;
  6. namespace Aitex.Core.Util
  7. {
  8. public class ByteStructConverter
  9. {
  10. public static T ToStruct<T>(byte[] by) where T : struct
  11. {
  12. int objectSize = Marshal.SizeOf(typeof(T));
  13. if (objectSize > by.Length) return default(T);
  14. // Allocate some unmanaged memory.
  15. IntPtr buffer = Marshal.AllocHGlobal(objectSize);
  16. // Copy the read byte array (byte[]) into the unmanaged memory block.
  17. Marshal.Copy(by, 0, buffer, objectSize);
  18. // Push the memory into a new struct of type (T).
  19. T returnStruct = (T)Marshal.PtrToStructure(buffer, typeof(T));
  20. // Free the unmanaged memory block.
  21. Marshal.FreeHGlobal(buffer);
  22. return returnStruct;
  23. }
  24. public static object ToStruct(byte[] buffer, Type t)
  25. {
  26. int objectSize = Marshal.SizeOf(t);
  27. if (objectSize > buffer.Length) return null;
  28. // Allocate some unmanaged memory.
  29. IntPtr buf = Marshal.AllocHGlobal(objectSize);
  30. // Copy the read byte array (byte[]) into the unmanaged memory block.
  31. Marshal.Copy(buffer, 0, buf, objectSize);
  32. // Push the memory into a new struct of type (T).
  33. object result = Marshal.PtrToStructure(buf, t);
  34. // Free the unmanaged memory block.
  35. Marshal.FreeHGlobal(buf);
  36. return result;
  37. }
  38. public static byte[] Struct2Bytes(object o)
  39. {
  40. // create a new byte buffer the size of your struct
  41. byte[] buffer = new byte[Marshal.SizeOf(o)];
  42. // pin the buffer so we can copy data into it w/o GC collecting it
  43. GCHandle bufferHandle = GCHandle.Alloc(buffer, GCHandleType.Pinned);
  44. // copy the struct data into the buffer
  45. Marshal.StructureToPtr(o, bufferHandle.AddrOfPinnedObject(), false);
  46. // free the GC handle
  47. bufferHandle.Free();
  48. return buffer;
  49. }
  50. }
  51. }