3

这段代码:

       char buff[255];
       memcpy(buff,0,255);

编译器在编译过程中没有给出任何警告,但过程因分段错误而失败但是当我编译以下代码时

       char buff[255];
       memcpy(buff,2,255);

编译器给出以下警告

警告:传递 'memcpy' 的参数 2 使指针从整数而不进行强制转换 [默认启用]

为什么编译器没有对常量 0 发出警告我正在使用 GCC 版本 4.7.2

还有一些编译器标志会对此类代码发出警告

4

3 回答 3

13

0在指针上下文中使用时被隐式转换为空指针。 2没有隐式转换为指针类型,因此会发出警告。

您可以在comp.lang.c常见问题解答第 5 节,特别是问题 5.2中阅读更多内容。

在这里的快速测试中,GCC 和 Clang 都没有警告过这种0情况(没有额外的标志),但是clang 静态分析器会:

example.c:6:4: warning: Null pointer argument in call to memory copy function
   memcpy(buff,0,255);
   ^~~~~~~~~~~~~~~~~~
/usr/include/secure/_string.h:55:6: note: expanded from macro 'memcpy'
   ? __builtin___memcpy_chk (dest, src, len, __darwin_obsz0 (dest))     \
     ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
1 warning generated.

正如这里的评论中其他地方所提到的,如果您通过了,GCC 会发出警告-Wnonnull(也包括在 中-Wall):

$ gcc -Wnonnull example.c -o example
example.c: In function ‘main’:
example.c:6: warning: null argument where non-null required (argument 2)
于 2013-06-02T18:31:57.983 回答
3

2不是指针;因此您会收到警告。

0是空指针,因此编译器看不到该代码有任何问题。

在 的上下文中memcpy(),传递空指针没有意义,但编译器不会对每个可能的无意义函数调用发出警告。
尤其是在 C 语言中,您应该编写有意义的代码。

于 2013-06-02T18:31:36.883 回答
1

因为0在指针上下文中是一个空指针常量,而 2 是一个整数类型int,即使在指针上下文中也是如此。

于 2013-06-02T18:37:43.763 回答