2015-03-23 4 views
10

Zuvor erhielt ich Warnungen von gcc -std=c99, dass usleep() implizit deklariert wurde. Dann stolperte ich über this stackoverflow post, was mich dazu brachte, zu verwenden. Aber jetzt, gcc sagt mir, dass -D_BSD_SOURCE veraltet ist und ich stattdessen -D_DEFAULT_SOURCE verwenden sollte.Was macht -D_DEFAULT_SOURCE?

#warning "_BSD_SOURCE and _SVID_SOURCE are deprecated, use _DEFAULT_SOURCE" 

Warum ist -D_BSD_SOURCE veraltet? Warum wird -D_DEFAULT_SOURCE stattdessen verwendet? Und was macht es?

Ich tat some googling, und die Ergebnisse sind nur mit Menschen gefüllt, die es zum Schließen gcc verwenden. Ich konnte nicht herausfinden warum-D_BSD_SOURCE wurde veraltet, nur dass es ist.

+0

Es geschah in [glibc 2.20] (https://sourceware.org/glibc/wiki/Release/2.20#Deprecation_of__BSD_SOURCE_and__SVID_SOURCE_feature_macros). Für was es tut, die [glibc Dokumentation erklärt, was der beabsichtigte Effekt ist] (http://www.gnu.org/software/libc/manual/html_node/Feature-Test-Macros.html#index-_005fDEFAULT_005fSOURCE). –

+0

Die usleep() - Funktion ist in der Header-Datei unistd.h definiert, jedoch ist sie auf der man-Seite obsolet und verwendet stattdessen nanosleep. Die Funktion nanosleep() ist in der Header-Datei definiert: time.h auch der Linkschritt. für gcc, benötigt den Parameter '-lrt' – user3629249

+0

@ user3629249 Diese [man-Seite für librt] (http://www.unix.com/man-page/opensolaris/3lib/librt/) schlägt vor, dass die Entwicklung neuer Anwendungen nicht nötig ist gib -lrt' an, aber ja, ich bin jetzt nach nanoschlaf() gewechselt. – ryanmjacobs

Antwort

10

Die glibc manual beschreibt jedes Feature-Test-Makro (FTM) einschließlich _DEFAULT_SOURCE:

Wenn Sie dieses Makro definieren, werden die meisten Funktionen auseinander enthalten von X/Open, AKE und GNU-Erweiterungen: die Wirkung zu ermöglichen, ist Features von der 2008 Edition von POSIX, sowie bestimmte BSD und SVID Funktionen ohne ein separates Feature-Test-Makro, um sie zu steuern. Das Definieren dieses Makros allein und ohne die Verwendung von Compiler-Optionen wie -ansi oder -std=c99 hat die gleiche Wirkung wie das Definieren von Feature-Test-Makros; Wenn diese Optionen zusammen mit anderen Feature-Test-Makros definiert werden oder wenn die Optionen wie -ansi verwendet werden, werden diese Features aktiviert, auch wenn die anderen -Optionen andernfalls dazu führen würden, dass sie deaktiviert werden.

This LWN.net article über FTMs bietet uns eine Begründung (unter anderem vielleicht interessanten Informationen):

Die ursprüngliche Absicht scheint gewesen zu sein, in jedem der glibc Header-Dateien, die FTMs beschäftigt, nur einer der __USE_* internen Makros sollte die Exposition einer bestimmten Definition bestimmen. Darüber hinaus sollten die Makros nicht in verschachtelten #ifdef Direktiven verwendet werden. Eine Inspektion der glibc-Header-Dateien zeigt schnell, dass die Realität weit von der Absicht ist es, eine Situation, die Roland McGrath führte to suggest, dass es Zeit für eine große Bereinigung Dinge wieder auf die vorgesehene Situation zu bringen war. Roland dachte, dass diese Aufgabe durch die Beseitigung der _BSD_SOURCE und _SVID_SOURCE FTMs, vereinfacht werden könnte, die, obwohl sie einen Zweck historisch hatten, aufgehört haben, in diesen Tagen nützlich zu sein . Mehr, sagte er, die einzigen Makros, die für modernen Quellcode benötigt werden, sind solche, die sich auf formale Standards plus _GNU_SOURCE beziehen.

Joseph Myers duly obliged mit einer Reihe von Patches, um die ersten Schritte in dieser Arbeit zu implementieren. Der von geförderte konservative Ansatz von Roland führte dazu, dass die Entwertung der FTMs _BSD_SOURCE und _SVID_SOURCE über zwei glibc-Versionen erfolgt. Version 2.19 von Glibc hinzugefügt ein neues FTM, _DEFAULT_SOURCE.Wenn Sie dieses Makro definieren, werden die Standarddefinitionen auch dann angezeigt, wenn die explizite Definition anderer Makros dazu führt, dass dies nicht geschieht. Die Wirkung dieses Makro zu definieren, ist äquivalent zu der Wirkung von explizit definieren drei Makros in früheren Versionen glibc:

cc -D_BSD_SOURCE -D_SVID_SOURCE -D_POSIX_C_SOURCE=200809C 

Also, wenn Sie _BSD_SOURCE oder _SVID_SOURCE definieren müssen, einfach _DEFAULT_SOURCE zu definieren. glibc Versionen < = 2.18 kümmern sich nicht darum und Versionen> = 2.19 warnen nicht, wenn beide oder alle drei definiert sind.

+0

Natürlich ist die wirkliche Lösung, den veralteten "usleep" (wenn möglich) zu vermeiden und stattdessen ['nanosleep'] (http://man7.org/linux/man-pages/man2/nanosleep.2.html) zu verwenden Die Single Unix Specification hat das nicht entfernt. –

+3

@ChronoKitsune: Ja, ich hatte etwas darüber geschrieben, aber er hat nicht nach diesem speziellen Fall gefragt und so endete es nicht in der Antwort. Und um 'nanosleep()' mit '-std = c99' zu verwenden, müssen Sie auch ein FTM definieren, aber zumindest ist es ein POSIX! – cremno

1

Ich brauche Portabilität jenseits von Linux und darüber hinaus Glibc, und ich mag # Ifdefs. so:

/* asprintf() does not appear on linux without this */ 
#define _GNU_SOURCE 

/* gettimeofday() does not appear on linux without this. */ 
#define _BSD_SOURCE 

/* modern glibc will complain about the above if it doesn't see this. */ 
#define _DEFAULT_SOURCE