1

我有以下代码

static pthread_mutex_t watchdogMutex = PTHREAD_MUTEX_INITIALIZER;
static pthread_cond_t watchdogCond = PTHREAD_COND_INITIALIZER;

使用 Splint 时出现以下错误/警告

静态 watchdogCond._数据。_mutex 初始化为空值:watchdogCond._数据。_mutex = (void )0 没有空注释的引用被分配或初始化为 NULL。使用 / @null@*/ 将引用声明为可能为空的指针。(使用 -nullassign 禁止警告)

这有什么问题,这是一个真正的危险吗?

4

2 回答 2

4

听起来夹板在将指针显式初始化为空时存在问题,并且需要某种覆盖注释注释来禁用警告。我会简单地听从它的建议并使用该-nullassign选项来禁用此警告。您的代码正在做什么或实现定义初始化器宏的方式没有什么不好或有害的。这只是夹板有非理性的恐惧。

于 2011-05-10T12:25:43.257 回答
2

这似乎pthread_mutex_t是一个不透明的指针(您可以向下追踪typedef以找出答案)。在 Splint 中,默认情况下指针不可为空。如果你想要一个可以为空的指针,你必须用语义注释来声明它/*@null@*/,例如:

char * ptr1;
/*@null@*/ char * ptr2;

ptr1 = NULL; /* warning: implicitly not-nullable pointer */
ptr2 = NULL; /* OK: explicitly nullable pointer */

根据手册,关于null 状态有 3 个选项:

  • null可能是空指针。
  • notnull非空指针。
  • relnull放松空值检查。将 NULL 分配给它或将其用作非空指针时不会出错。

使用不可为空的指针的好处是你不需要每次得到它们时都检查它们。例如,您可以将函数参数注释为/*@notnull@*/,然后在取消引用它之前不需要检查。if(pointer == NULL)这减少了检查并简化了您的代码。

忽略这些警告的危险在于,如果您告诉 Splint 一个特定的指针不可能为空,然后您尝试分配NULL给它,则该空指针可能最终被取消引用并且程序可能崩溃。

在我看来,您的实际问题是 Splint 的策略,它认为所有指针都隐含不可为空。这迫使您注释所有可能的空指针。

于 2011-05-10T13:28:19.197 回答