UB与不同类型的结构铸件? [复制]

Posted

技术标签:

【中文标题】UB与不同类型的结构铸件? [复制]【英文标题】:UB with structure casting of different types? [duplicate] 【发布时间】:2017-02-15 05:44:43 【问题描述】:

以下代码是否包含未定义行为?该代码仅尝试使用sockaddr_in 结构格式填充sockaddr_storage 结构,然后通过相同的类型将其读回,即。 sockaddr_in。同样在以下调用中,sockaddr_storage 结构通过强制转换传递给sockaddr 结构。我看到了类似的问题,想知道这段代码是否也包含它。该程序在我测试过的任何地方都可以正常工作 -

Run Online

#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <iostream>

using namespace std;

void fillAF_INET(sockaddr_storage &s)
  sockaddr_in *p = reinterpret_cast<sockaddr_in *>(&s);
  p->sin_family = AF_INET;
  p->sin_port = htons(10000);
  inet_pton(AF_INET, "127.0.0.1", &p->sin_addr);


// void fillAF_INET6(sockaddr_storage &s)...
// void fillAF_UNIX(sockaddr_storage &s)...

int main()
  sockaddr_storage s;
  fillAF_INET(s);

  sockaddr_in *p = reinterpret_cast<sockaddr_in *>(&s);
  std::cout << ntohs(p->sin_port) << " ";
  std::cout << boolalpha << (p->sin_family == AF_INET);

  int sock = socket(AF_INET, SOCK_STREAM,0);
  int r = bind(sock, (sockaddr *)&s, sizeof(s));
  // further calls

  return 0;

结果来了:10000 true,绝对正确!

【问题讨论】:

删除了错误处理以保持它的小.. 类似:***.com/questions/9964418/… 【参考方案1】:

代码正确。以下是 Open Group 对sockaddr_storage 的评价:

&lt;sys/socket.h&gt; 标头应定义sockaddr_storage 结构。 该结构应为:

足够大以容纳所有受支持的协议特定地址 结构

在适当的边界对齐,以便可以强制转换指向它的指针 作为指向协议特定地址结构的指针,用于访问 那些没有对齐问题的结构的字段

【讨论】:

'它是正确的' - 你的意思是它是 UB 还是代码是正确的而不是 UB?另见***.com/questions/42178179/… 这是错误的,另请参阅 - ***.com/questions/42176962/…

以上是关于UB与不同类型的结构铸件? [复制]的主要内容,如果未能解决你的问题,请参考以下文章

值类型和引用类型的区别

为什么不同布局兼容类型的两个数组本身也不兼容布局?

SQL表名不同结构相同 如何做成复制订阅?

ARC 和桥接铸件

ABAP 中内表的复制

数组与结构体的区别