11

我的代码看起来像这样,其中 addr 是 sockaddr*:

struct sockaddr_in *sin = (struct sockaddr_in *) addr;
const char *IP=inet_ntoa(sin -> sin_addr);

我相信这是使用 Berkeley 套接字的非常典型的代码。

但是,当我编译它时,我收到以下警告:
dereferencing pointer 'sin' does break strict anti-aliasing rules

在网上搜索,我发现一些关于我做事方式非常典型的事实的讨论,但是这个编译器警告也很真实,不是一件好事。

重做此代码以修复警告而不只是使其静音的正确方法是什么?

4

4 回答 4

5

我有同样的问题 - 它看起来像 gcc 中的一个错误。

我能够通过使用来解决它

(*sin).sin_addr

代替

sin->sin_addr
于 2013-08-20T17:59:03.460 回答
2

是的,这是 gcc 和套接字的一个已知问题。问题基本上似乎是这个 ip[46] 东西的设计方式与 gcc 人们认为他们可以推断出指针别名的假设不兼容。

我通常会先在struct

struct in_addr* act = &(sin->sin_addr);

然后使用*act.

于 2010-08-12T07:09:02.163 回答
1

根据您的使用方式struct sockaddr,我认为您的代码已损坏,或者 gcc 已损坏。struct sockaddr并且struct sockaddr_in有一个共同的初始元素(sa_family/ sin_family),因此如果您只通过两个指针访问了这个元素,它就不会违反别名规则;C99 允许这样做。此外,struct sockaddr没有其他您可以访问的元素。它在很大程度上是原始套接字地址多态性的不透明类型。如果您一直在探索特定于实现的内部结构struct sockaddr,或者更糟糕的是,如果您声明了一个struct sockaddr对象而不仅仅是一个指针或在这些对象之间执行复制,您的代码被破坏了。如果您没有这样做,并且 gcc 会发出警告,声称您违反了别名规则,那么 gcc 的警告生成就会被破坏。如果是后者,我当然不会感到惊讶。

于 2010-08-12T05:54:26.433 回答
-2

If your header file and your compiler are both parts of the same C or C++ implementation, complain to your vendor and ask them to put a suitable #pragma in their header file to silence their compiler. As implementor, they're allowed to play games like that, as long as they provide a conforming implementation.

If your header file and your compiler came from two separate C or C++ implementations, you're lucky that things work as well as they do, and you have to solve it yourself.

于 2010-08-12T05:29:44.387 回答