我发现问题such as this one已经接近解决我的困境。但是,我还没有找到一种以通用方式解决这个问题的简洁方法。
我有一个项目有很多结构,将用于二进制数据传输。这些数据需要是Big Endian,当然,大多数.Net架构都是Little Endian。这意味着当我将结构转换为字节时,我的值的字节顺序会反转。
是否有一种相当直接的方法来强制我的结构包含Big Endian格式的数据,或者有没有办法将这些结构一般性地写入输出Big Endian数据的字节数组(和字节数组到结构体)?
以下是我已经完成的一些示例代码。
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public unsafe struct StructType_1
{
short shortVal;
ulong ulongVal;
int intVal;
}
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public unsafe struct StructType_2
{
long longVal_1;
long longVal_2;
long longVal;
int intVal;
}
...
public static class StructHelper
{
//How can I change the following methods so that the struct data
//is converted to and from BigEndian data?
public static byte[] StructToByteArray<T>(T structVal) where T : struct
{
int size = Marshal.SizeOf(structVal);
byte[] arr = new byte[size];
IntPtr ptr = Marshal.AllocHGlobal(size);
Marshal.StructureToPtr(structVal, ptr, true);
Marshal.Copy(ptr, arr, 0, size);
Marshal.FreeHGlobal(ptr);
return arr;
}
public static T StructFromByteArray<T>(byte[] bytes) where T : struct
{
int sz = Marshal.SizeOf(typeof(T));
IntPtr buff = Marshal.AllocHGlobal(sz);
Marshal.Copy(bytes, 0, buff, sz);
T ret = (T)Marshal.PtrToStructure(buff, typeof(T));
Marshal.FreeHGlobal(buff);
return ret;
}
}
答案 0 :(得分:1)
如果您不介意将每个字段读取并写入流(可能会影响性能),您可以使用Jon Skeet的EndianBinaryWriter:https://stackoverflow.com/a/1540269/106159
代码看起来像这样:
public unsafe struct StructType_2
{
long longVal_1;
long longVal_2;
long longVal;
int intVal;
}
using (MemoryStream memory = new MemoryStream())
{
using (EndianBinaryWriter writer = new EndianBinaryWriter(EndianBitConverter.Big, stream))
{
writer.Write(longVal_1);
writer.Write(longVal_2);
writer.Write(longVal);
writer.Write(intVal);
}
byte[] buffer = memory.ToArray();
// Use buffer
}
您可以使用EndianBinaryReader
向相反方向发送数据。
这当然有两个相当大的缺点:
另请查看此类似问题的答案:Marshalling a big-endian byte collection into a struct in order to pull out values
答案 1 :(得分:0)
鉴于显示转换uint
的{{3}}示例,我怀疑不会。