通过c套接字发送struct

时间:2011-08-25 14:56:05

标签: c++ sockets udp

我正在构建一个UDP聊天应用。是否安全地通过c套接字发送C结构并在另一端发送memset接收数据? struct中的所有数据都使用memset进行空值,因此我假设结构的大小始终是常量。我可能遇到什么问题?

更有经验的程序员如何接近这个?

4 个答案:

答案 0 :(得分:6)

是的,它是安全的但我们首先应该警告。您可能遇到问题,如果您在不同的平台之间传递它,那么您需要担心字节排序/打包(可能在其他许多问题中) )。话虽如此,如果您不知道如何做到这一点,那么假设您将按照发送的顺序可靠地接收struct是不安全的。

答案 1 :(得分:5)

然而,你这样做,单位测试它的地狱。编译器和平台在这些方面变化很大,所以不要盲目地假设它是一致的。

编译器可能会随心所欲地更改结构对齐(例如,出于性能原因)。要求一些限制通常是编译器特定的,尽管MSVC和gcc(通过扩展)支持这个限制

#pragma pack(push, 1)
struct Foo {
  // ..
};
#pragma pack(pop)

这迫使它在1字节边界上对齐,因此没有布尔值。

如果您想完全符合要求,请自行序列化每个字段。这真的不是那么多工作。

如其他人所提到的,你还必须处理字数。

答案 2 :(得分:3)

  

struct中的所有数据都使用memset进行空值,因此我假设结构的大小始终是常量。

这没有多大意义。对象始终具有固定大小。 “与memset一起使用Nullpadding”与它无关。

  

在C套接字上发送C结构并在另一端发送memset接收数据是否安全?

不,不是真的。

最好考虑发送“数据”而不是内存中对象的确切字节物理内容。

  

我可能会遇到什么问题?

  • 会员填充
  • 数据对齐
  • 类型尺寸
  • 字节序
  • 间接 - 指向数据的指针而不是数据本身
  

更有经验的程序员如何接近这个?

最好正确地进行序列化。

创建一种数据格式,无论您使用哪种计算机,您的应用程序都会识别该数据格式,并使用它来表示您的聊天数据。

  1. 有时为了提高效率,您必须设计二进制格式,并使用聪明,强大的技术在目标计算机上正确地反序列化信息,并考虑上面列出的因素。

  2. 但是,对于简单的工作,您可以使用人类可读的文本格式。不能真的出错。

答案 3 :(得分:1)

您必须小心您的结构不包含指针(如char*字符串)。这也适用于在结构中存储std::string的情况,因为std::string内部有一个指针。