【发布时间】:2014-12-01 05:29:00
【问题描述】:
我正在尝试在 C# 中创建以下结构,它是一个基于 C 的复杂结构,我尝试了大多数编组选项,但我总是得到“System.TypeLoadException”。
(附加信息:无法从程序集“WindowsFormsApplication1,Version=1.0.0.0,Culture=neutral,PublicKeyToken=null”加载类型“WindowsFormsApplication1.COMPLEX_STRUCT”,因为它包含偏移量 8 处的对象字段,该对象字段未正确对齐或重叠通过非对象字段。)
关于 IPV6_ADDR 结构,我尝试了 LayoutKind.Explicit 和 LayoutKind.Sequential, 和两者:
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 16)]
public string Addr;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 16)]
public byte[] Addr;
我在 x64 机器上,但 IPV6_ADDR 结构对齐到 8 个字节,所以我不知道是什么问题。
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct IPV4_ADDR
{
public uint Addr;
public uint SubnetNumBits;
};
[StructLayout(LayoutKind.Explicit, Pack = 1)]
public struct IPV6_ADDR
{
[FieldOffset(0)]
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 16)]
public string Addr;
[FieldOffset(16)]
public uint SubnetNumBits;
};
[StructLayout(LayoutKind.Explicit, Pack = 1)]
public struct COMPLEX_STRUCT
{
[FieldOffset(0)]
public byte A;
[FieldOffset(1)]
public byte B;
[FieldOffset(2)]
public byte C;
[FieldOffset(3)]
public byte D;
[FieldOffset(4)]
public byte E;
[FieldOffset(8)]
public IPV4_ADDR IPv4;
[FieldOffset(8)]
public IPV6_ADDR IPv6;
[FieldOffset(28)]
public ushort F;
}
我试图模仿的原始 C 结构:
typedef struct _IPV4_ADDR
{
uint32_t Addr;
uint32_t SubnetNumBits;
} IPV4_ADDR, *PIPV4_ADDR;
typedef struct _IPV6_ADDR
{
uint8_t Addr[16];
uint32_t SubnetNumBits;
} IPV6_ADDR, *PIPV6_ADDR;
typedef struct _COMPLEX_STRUCT
{
uint8_t A;
uint8_t B;
uint8_t C;
uint8_t D;
uint8_t E;
uint8_t Rsvd[3];
union {
IPV4_ADDR IPv4;
IPV6_ADDR IPv6;
} u;
uint16_t F;
} COMPLEX_STRUCT, *PCOMPLEX_STRUCT;
【问题讨论】:
-
@TyCobb 有。因为字符串是由 .NET 运行时管理的,所以不能将具有字符串的结构与在相同本地偏移处不具有字符串的结构重叠。
-
OK Thx,我真的不介意从 string 切换到 byte[] / char[],但我也试过了,还是不行
-
我已将原始结构添加到您的问题中。请删除您的答案。
标签: c# struct marshalling typeloadexception structlayout