我想在Linux系统上编译一个C程序。 我有一个stdlib.h
的#include
语句。
当我用gcc
编译程序时,如下所示:
gcc -std=c99 -g -o progfoo progfoo.c progbar.c
我收到有关Implicit declaration of function [srand48, drand48, bzero, or close]
警告。
编译为:
gcc -g -o progfoo progfoo.c progbar.c
没有给我警告,但它确实对我使用for
循环(这是首先添加-std=c99
的理由)大喊大叫。
鉴于这个man srand48
提到包括我所拥有的<stdlib.h>
,我不确定还有什么问题可以解决。 for
循环对于任何事情来说都不是必须的(它们只是为了节省初始化数组的时间),所以我没有问题去除它们,但是在我做之前我想确认c99
标准是否取代了我的#include
陈述。
我正在使用gcc 4.1.2-50 (Red Hat)
。
可以-std = c99防止我的#包含工作正常吗?
不,但是他们可能在你的工作方式上显示出局限性:-)
虽然函数[sd]rand48
在stdlib.h
有一个原型,但它们在#ifdef
,至少在我的系统中:
#if defined __USE_SVID || defined __USE_XOPEN
所以你可能不得不明确地设置这些宏之一。
但是,在尝试之前,请注意它不起作用。 这是因为所有这些东西都是用gcc
的特性测试宏来控制的 。
有一组非常复杂的规则用于在features.h
设置或关闭特定功能,并且在那里创建的宏控制头文件包含和排除的内容。 根据__USE_*
自己提供的其他宏, __USE_*
变体被清除并设置在该头文件中。
例如,要设置__USE_SVID
以便使用srand48
,则需要为编译器提供一个-D_SVID_SOURCE
参数。
但也许更简单的方法就是使用C99和GNU扩展。 要做到这一点,用-std=gnu99
替换-std=c99
。
而且,对于bzero
和close
,这些可以分别从strings.h
和unistd.h
获得。
我起初有点困惑,为什么这些编译与-std=c99
时,他们是完全无关的 C99,但后来我意识到,国旗只控制标准的C标题给你。
既不strings.h
(注意复数名称,这不是 string.h
)也不是unistd.h
是ISO C的一部分。
看起来你正在使用的功能不是ISO C99,所以当你要求严格的C99合规性时,它们将不可见。
信息在这里: https : //bugzilla.redhat.com/show_bug.cgi?id=130815
标志-D_POSIX_C_SOURCE=200809L
应该工作。
另请参阅此问题: 当-std = c99被设置时,为什么gcc不能找到random()接口?
你得到的错误听起来像你正在使用的函数没有被声明。 你确定你包含正确的标题吗?
而且,使用-std=c99
可能会禁用一些不属于标准的扩展。 你所提到的功能都不是C标准的一部分。 如果你不能为它们找到单独的标题,你可以试试-std=gnu99
。
-std=c99
会导致头文件忽略任何可能与使用C99保留名称空间外部名称(包括所有标准POSIX函数)冲突的内容。 请求头文件的可移植方式为您提供POSIX接口是将_POSIX_C_SOURCE
定义为与所需的POSIX版本相对应的值。 对于最新的POSIX(2008),这意味着:
#define _POSIX_C_SOURCE 200809L
或者在命令行上:
-D_POSIX_C_SOURCE=200809L
编辑:看来你想要的功能不在POSIX的基础,但在XSI选项,所以你应该定义_XOPEN_SOURCE
到一个合适的值( 700
是最新的),以获得他们。 这也可以通过命令行或源文件来完成(但是如果来自源文件,则必须在包含任何系统标题之前完成。
隐式声明(假定未声明的函数返回int)在C99中不再允许。
也就是说,gcc不会中止汇编。
尝试为bzero
包含strings.h
,另请参见paxdiablo的答案。
您要求符合标准,并且C99不将srand48()
定义srand48()
<stdlib.h>
提供的函数。
对于GNU C库,您可以通过定义/usr/include/features.h
顶部注释中列出的一个或多个选项来请求其他功能,可以通过在#include
之前的#define
或-D
标志gcc
。
对于srand48()
(和drand48()
),您可能需要-D_XOPEN_SOURCE=500
或-D_SVID_SOURCE
(或源文件中的#define _XOPEN_SOURCE 500
等)。
bzero()
和close()
应该可以在-std=c99
情况下工作,如果你包含了文件头文件,分别是<strings.h>
和<unistd.h>
。