如何将C++ ulong 4 字节 IP 地址正确转换为 C# 类型

How to correctly convert C++ ulong 4 bytes IP address to C# type?

本文关键字:转换 类型 地址 IP C++ ulong 字节      更新时间:2023-10-16

C++客户端,我正在向C#服务器发送6个字节的缓冲区。

ULONG addr = htonl(server->sin_addr.s_addr);
USHORT port = server->sin_port; -> Already reversed to network bytes.
char frame[sizeof(USHORT) + sizeof(ULONG)];
memcpy(frame, &port, sizeof(USHORT));
memcpy(&frame[2], &addr, sizeof(ULONG));

int result = send(s, (const char*)frame, sizeof(frame), 0);

如您所见,缓冲区包含:[2 字节端口,4 字节地址]


在 C# 服务器端,Im 然后将端口和地址从网络转换为主机字节。我已经检查以确保收到的缓冲区始终为 6 字节。

ushort port = BitConverter.ToUInt16(buffer, 0);
byte[] temp = new byte[4];
Array.Copy(buffer, 2, temp, 0, temp.Length);
uint address = BitConverter.ToUInt32(temp, 0);
long addressx = IPAddress.NetworkToHostOrder(address);
destPort = (ushort)IPAddress.NetworkToHostOrder((short)port);
destAddress = (new IPAddress(addressx).ToString());

有时,我在初始化new IPAddress(address)时遇到异常,ArgumentOutOfRangeException

我不明白的是,为什么它只是偶尔发生,我做错了什么?

这里的问题是您的addressx要么小于零,要么大于 0x00000000FFFFFFFF。

发生这种情况是因为您在addressuint时调用IPAddress.NetworkToHostOrder(address);。由于没有接受uintNetworkToHostOrder()的重载,这是将参数提升到long并调用NetworkToHostOrder(long)。这会导致某些输入为负值。

您需要做的是使用地址的int形式调用采用 int 的版本:

int address = BitConverter.ToInt32(temp, 0);

现在,当您调用NetworkToHostOrder()时,您将获得一个(可能是负面的(int,您需要将其投射到uint

uint addressx = (uint) IPAddress.NetworkToHostOrder(address);

现在这应该可以工作了:

destAddress = (new IPAddress(addressx).ToString());