套接字编程:在 UDP 上发送数据包(C++)

Posted

技术标签:

【中文标题】套接字编程:在 UDP 上发送数据包(C++)【英文标题】:Socket programming : sending packet on UDP (C++) 【发布时间】:2014-10-14 20:54:22 【问题描述】:

我正在尝试在 UDP 中发送数据包消息(具有标头和数据数组)。 我处于初步阶段,在消息中不使用任何数据,并且我想发送此标头,它由结构的结构和嵌套的枚举表示。

除了序列化所述结构然后构造缓冲区数据并发送它们之外,还有其他方法可以在 UDP 上发送数据吗?是否有像 c 中的缓冲区例程,发送数据包的 c++ 套接字编程

【问题讨论】:

这比 您将发送数据包,但这些数据包将由原始字节数据组成。一切都没有内置的标准序列化。 我的问题是,如果你有一个复杂的结构,是否将其序列化到缓冲区中是传输它的唯一方法,或者在 c++ 中是否有类似 Java 的可序列化的东西 @user1895125:是的,你必须自己做。但是有很多工具可以帮助Serializable 确实如此。 【参考方案1】:

如果您的 struct 是字节对齐的并且仅使用 POD 类型,您可以将结构直接传递给 sendto() 而无需先将其复制到另一个缓冲区,例如:

#pragma pack(push, 1) // or other platform-appropriate pack statement
struct myHdr

    uint8_t type;
    uint16_t len;
    //...
;
#pragma pack(pop)

myHdr hdr;
hdr.type = ...;
hdr.len = ...;
...

send(fd, &hdr, sizeof(hdr), 0);

但这种做法确实会令人不悦。一旦你开始添加数据,它就不是很有帮助。但是您可以分配一个缓冲区并使用字节对齐的struct 来填充缓冲区,至少:

#pragma pack(push, 1) // or other platform-appropriate pack statement
struct myHdr

    uint8_t type;
    uint16_t len;
    //...
;
#pragma pack(pop)

uint8_t buffer[65535];
myHdr *hdr = (myHdr*) &buffer[0];
hdr->type = ...;
hdr->len = ...;
...
// fill in &buffer[sizeof(myHdr)] onwards as needed

send(fd, buffer, sizeof(myHdr)+..., 0);

【讨论】:

【参考方案2】:

这正是sendmsg() 函数的用途。它提供了“收集-写入”功能。您为它提供一个或多个(可能是零个或多个)缓冲区地址和长度,然后它将它们全部收集到一个发送中。

但是你不应该使用structs 作为网络协议。使用网络协议作为网络协议。在八位字节中定义自己的应用程序协议,并为自己编写一个库以将结构打包到八位字节流中或从八位字节流中解压缩。

或者使用 XDR 或其同源词。

【讨论】:

以上是关于套接字编程:在 UDP 上发送数据包(C++)的主要内容,如果未能解决你的问题,请参考以下文章

套接字编程,如果我写入的数据超过一个 TCP/UDP 数据包可以携带会怎样?

C++ UDP客户端/套接字编程:不能发送和接收

Python原始套接字编程

原始 UDP 套接字卡在 recvfrom 上

如何确定/设置套接字缓冲区大小?

使用数据包套接字在同一网络接口上发送和接收时无法接收包