为什么SUN_LEN宏在没有错误的情况下取消引用NULL?

时间:2018-01-20 23:38:41

标签: c linux testing

我目前正在查看clang清理程序错误,该错误告诉我在程序运行期间我取消引用了nullptr。看看问题的根源,我得到了Arch Linux上SUN_LEN的{​​{1}}宏,看起来像这样:

sys/un.h

似乎这个宏总是试图访问NULL,所以故障似乎就在那里。但我非常怀疑这是一个错误,因为这个宏在任何地方使用并且似乎工作正常(除了消毒剂警告),所以我想知道为什么这不会崩溃以及为什么它首先出现在那里?

1 个答案:

答案 0 :(得分:0)

#define SUN_LEN(ptr) ((size_t) (((struct sockaddr_un *) 0)->sun_path)        \
              + strlen ((ptr)->sun_path))

不会取消引用NULL指针。

让我们看一下宏的内部部分:

(((struct sockaddr_un *) 0)->sun_path)

这不是因为这是指向NULL指针的struct sockaddr_un指针。 ->sun_path用于指针算术:

struct sockaddr_un *so = NULL;
char *offset = so->sun_path + strlen(ptr->sun_path);

最后一部分是演员size_t

size_t size = (size_t) offset;

offset中的地址存储转换为数字size_t值。

在这种情况下,它基本上是在做

size_t val = offsetof(struct sockaddr_un, sun_path) +
    strlen(ptr->sun_path) * sizeof *ptr->sun_path;

我不能告诉你的是为什么这个宏以这种方式定义,伙计们 实现这个套接字库可能有很好的理由而不是 使用offsetof,内部也是一个宏。此gcc -E的{​​{1}} 告诉我:

offsetof