D_GNU_SOURCE的解释是什么?为什么要使用它,以及何时使用它?

7

我知道这是一个传递到函数中的宏。你能否解释一下这个宏的用途以及在什么情况下我需要使用它?

4个回答

5

_GNU_SOURCE启用了GNU C库支持的C和操作系统标准的GNU扩展,如asprintf。如果使用这样的非标准函数和宏,请定义它。


使用这种非标准方案的缺点是什么?它在平台之间不可移植。 - Whoami
@Whoami:确实存在不可移植性。C库的man页面记录了哪些标准功能是符合规范的。 - Fred Foo
谢谢回复。顺便说一下,我尝试了以下代码:#include <stdio.h>int main (int argc, char **argv) { char *p; asprintf (&p, "%s", "Welcome"); printf ("String is %s ", p); }gcc -o mysample mysample.c :我能够编译和执行这段代码。我在源代码中没有包含_GNU_SOURCE,也没有在编译时使用宏。但是为什么还能够编译通过呢? - Whoami

4

3

如果您的应用程序符合POSIX.1-(IEEE 1003.1-2008,ISO/IEC 9945:2009)和/或Single Unix Specification 2008(ISO/IEC 9945:2009 with X/Open Curses),则可以确保应用程序的可移植性。使用_GNU_SOURCE将很可能限制源代码仅适用于GNU/Linux和GNU/Hurd系统,除非进行额外的工作以解决在其他平台上的不可移植性。

一些公司和政府/军事合同可能需要使用特定的平台标准。

如果您正在开发希望在多个Unix和类Unix系统(包括具有可用POSIX兼容性的Microsoft Windows NT、2000及更高版本)上提供的开源/免费软件应用程序,则将开发限制为POSIX.1库函数会使此任务更加容易。其他目标包括自由/开放BSD平台NetBSD、FreeBSD、OpenBSD、DragonflyBSD,以及商业Unix系统(Solaris、AIX、HP/UX等),这些系统不包括_GNU_SOURCE功能。

如果您使用可移植函数的修改功能,我无法想到一个例子,但我相信这种情况确实存在,在非GNU平台上可能会产生微妙的错误。

因此,一般来说,如果您的开发已经锁定在GNU/Linux和GNU/Hurd上,则可以自由使用此类扩展,但是避免在可能部署在其他Unix和类Unix操作系统上的任何应用程序中使用此类扩展。

我正在处理一个从另外两个Unix平台移植到Linux的大型代码库,我们谨慎地使用_GNU_SOURCE扩展,尽管大部分开发仅限于现代POSIX或IEEE 1003.1 / Single Unix Spec和C99(标准C库)标准以实现未来的兼容性。


谢谢你的回复。顺便说一下,我尝试了以下代码:#include <stdio.h> int main ( int argc, char ** argv) { char *p; asprintf (&p, "%s", "Welcome"); printf ("String is %s ", p); }gcc -o mysample mysample.c:我能够编译并执行该代码。我在源代码中没有包含_GNU_SOURCE,在编译时也没有使用宏。但是为什么它还能编译呢? - Whoami
1
GCC文档中的C语言方言选项列出了“gnu89”/“gnu90”是默认选项(在4.6.2版本和许多其他版本中也是如此)。使用gcc -v检查您的版本,使用cpp -dM </dev/null查找预定义头文件。_GNU_SOURCE未定义,因此,正如gcc手册所解释的那样,默认情况下允许不与ANSI/ISO标准冲突的扩展。_GNU_SOURCE还将允许修改或与ANSI/ISO标准冲突的GNU扩展。 - mctylr
关于“可移植函数的功能变更”:我对寻找在不同特性测试宏下具有不同声明的函数的示例很感兴趣,并找到了一个:mmap在Solaris上至少根据POSIX合规级别有不同的声明 - hmijail

1

标准未规定的某些函数在库中提供,但仅在定义了某些特性测试宏时才可用。 _GNU_SOURCE 是使这些函数可用的宏之一。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接