5

正如问题所述,“隐式声明函数”警告究竟意味着什么?我们刚刚在 gcc 上打开了警告标志,发现了很多这些警告的实例,我很好奇在修复它们之前这可能会导致什么类型的问题?

另外,为什么这是警告而不是错误。gcc 甚至如何能够成功链接此可执行文件?正如您在下面的示例中所见,可执行文件按预期运行。

以以下两个文件为例:

文件1.c

#include <stdio.h>

int main(void)
{
   funcA();
   return 0;
}

文件2.c

#include <stdio.h>

void funcA(void)
{
   puts("hello world");
}

编译和输出

$ gcc -Wall -Wextra -c file1.c file2.c
file1.c: In function 'main':
file1.c:3: warning: implicit declaration of function 'funcA'

$ gcc -Wall -Wextra file1.o file2.o -o test.exe
$ ./test.exe
hello world
4

2 回答 2

11

如果函数具有与隐式声明匹配的定义(即,它返回int并具有固定数量的参数,并且没有原型),并且您始终使用正确数量和类型的参数调用它,那么就没有负面影响(除了糟糕的、过时的风格)。

即,在您上面的代码中,就好像该函数被声明为:

int funcA();

由于这与函数定义funcA()匹配,因此对from的调用会file1.c调用未定义的行为,这意味着它可能会崩溃。在您的架构上,使用您当前的编译器,显然不会 - 但架构和编译器会发生变化。

GCC 能够链接它,因为表示函数入口点的符号在函数类型更改时不会更改(再次......在您当前的架构上,使用您当前的编译器 - 尽管这很常见)。

正确声明你的函数是一件好事 - 如果没有其他原因,它允许你给你的函数一个原型,这意味着如果你用错误数量或类型的参数调用它,编译器必须诊断它。

于 2010-04-22T05:05:52.333 回答
1

它与在块范围内使用具有返回类型的非原型函数声明具有相同的行为int,因为无法指定返回类型,它默认为int,就像 C 中所有未指定类型的声明一样,一切都是int.

可以隐式声明函数的原因是因为它们只能在文件范围内定义,但不清楚未定义的变量是块范围还是文件范围,因此不允许选择一个并提供隐式暂定定义文件或块范围。实际上,实际的隐式声明是块作用域的,因此在引用它的每个函数中首次引用该函数时都会收到警告。

于 2021-03-11T08:18:28.400 回答