简体   繁体   English

没有强制转换的整数指针

[英]Pointer from integer without a cast

When I call a function that expects a pointer, and I pass in a value, I get this warning, and I like that. 当我调用一个需要指针的函数时,我传入一个值,我得到了这个警告,我喜欢这样。

But when the value happens to be a literal '0', I don't get the warning. 但是当值恰好是字面值'0'时,我没有得到警告。 I think this is because C think it's null-pointer, and not a value. 我认为这是因为C认为它是空指针,而不是值。 Is there any way to still get warnings for 0-literals, because I already had some bugs because of it. 有没有办法仍然得到0文字的警告,因为我已经有一些错误因为它。

GCC supports a nonnull attribute on function parameters that can do what you want (as long as the -Wnonnull warning option is enabled): GCC支持函数参数nonnull属性 ,可以执行您想要的操作(只要启用了-Wnonnull警告选项):

void* foo( int* cannot_be_null)  __attribute((nonnull (1))) ;


int main(int argc, char *argv[])
{
    int x;
    foo(&x);

    foo(0);  // line 13 - generates a -Wnonnull warning

    return 0;
}

When compiled using gcc -c -Wnonnull test.c I get: 当使用gcc -c -Wnonnull test.c编译时,我得到:

test.c: In function 'main':
test.c:13:5: warning: null argument where non-null required (argument 1) [-Wnonnull]

You can force this to be an error with -Werror=nonnull . 您可以使用-Werror=nonnull强制执行此错误。

Note that this warning is only thrown when the null pointer literal (another name for 0 ) is used - the following code doesn't trigger the warning: 请注意,仅当使用空指针文字(另一个名称为0 )时才会抛出此警告 - 以下代码不会触发警告:

int* p = NULL;
foo(p);

Not with a raw C compiler unfortunately. 遗憾的是,没有使用原始C编译器。 You should try a lint tool, as splint, that might help you about this (I'm not sure, though). 您应该尝试使用lint工具作为夹板,这可能对您有所帮助(但我不确定)。

Is there any way to still get warnings for 0-literals 有没有办法仍然得到0文字的警告

I don't know about one, an anyway you don't want that. 我不知道一个,无论如何你不想要那个。 The constant numeric value 0, when assigned to a pointer, is implicitly treated as NULL without casting it to a pointer type. 当分配给指针时,常量数值0被隐式地视为NULL而不将其转换为指针类型。

I think conversion to null probably fairly intrinsic to the compiler - It should be easy however to statically check for these cases as they are fairly unique. 我认为转换为null可能对编译器来说是相当固有的 - 但是应该很容易静态地检查这些情况,因为它们是相当独特的。

If you are expecting to pass null and not (int)0, use an explicit NULL enum or define, and then anything matching the pattern YourFunction(0); 如果您希望传递null而不是(int)0,请使用显式NULL枚举或定义,然后使用与模式YourFunction(0)匹配的任何内容; (allowing for white space) is definitely invalid. (允许空格)绝对无效。 Grep could be used quite easily for this if you want to go low-tech. 如果你想要低技术,Grep可以很容易地使用。 Various lint tools might be able to do this as Fabien suggested. Fabien建议,各种棉绒工具都可以做到这一点。

I always try to remember when coding that if you can, make wrong things look as wrong as possible, that way you can detect them all the more easily. 我总是试着记住编码的时候,如果可以的话,让错误的东西看起来尽可能的错误,这样你就可以更容易地发现它们。

This question is similar to the question. 这个问题与问题类似。 Should I use symbolic names like TRUE and FALSE for Boolean constants, or plain 1 and 0?

C programmers must understand that NULL and 0 are interchangeable in pointer contexts, and that an uncast 0 is perfectly acceptable. C程序员必须明白NULL和0在指针上下文中是可互换的,并且uncast 0是完全可以接受的。 Any usage of NULL (as opposed to 0) should be considered a gentle reminder that a pointer is involved; 任何使用NULL(而不是0)都应该被认为是一个涉及指针的温和提示; programmers should not depend on it (either for their own understanding or the compiler's) for distinguishing pointer 0's from integer 0's. 程序员不应该依赖它(无论是为了他们自己的理解还是编译器)来区分指针0和整数0。

It is only in pointer contexts that NULL and 0 are equivalent. 只有在指针上下文中,NULL和0才是等价的。 NULL should not be used when another kind of 0 is required, even though it might work, because doing so sends the wrong stylistic message. 当需要另一种类型0时,不应该使用NULL,即使它可能有效,因为这样做会发送错误的样式消息。 (Furthermore, ANSI allows the definition of NULL to be ((void *)0), which will not work at all in non-pointer contexts.) In particular, do not use NULL when the ASCII null character (NUL) is desired. (此外,ANSI允许NULL的定义为((void *)0),这在非指针上下文中根本不起作用。)特别是,当需要ASCII空字符(NUL)时,不要使用NULL。 Provide your own definition 提供您自己的定义

#define NUL '\0'

if you must. 如果你必须。

This information is from this link 此信息来自此链接

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM