Этот простой.c файл:
#include <unistd.h>
void test() {
char string[40];
gethostname(string,40);
}
... при нормальной компиляции хорошо работает:
$ cc -Wall -c -o tmp.o tmp.c
$
... но при компиляции в режиме C99 дает предупреждение:
$ cc -Wall -std=c99 -c -o tmp.o tmp.c
tmp.c: In function `test':
tmp.c:5: warning: implicit declaration of function `gethostname'
$
Результант.o файл прекрасен, и соединение работ. Я был бы точно так же, как для избавлений от предупреждения. Я могу достигнуть этого hacky способом, вставив объявления мой собственный.h файл.
Что о C99 означает, что объявления в unistd.h не становятся включенными? Это может быть преодолено, не бросая правильность C99?
Я вижу, что та же проблема для другого стандарта освобождает.
Вам может потребоваться определить некоторые макросы особым способом, чтобы получить прототип для gethostname ()
From man gethostname
:
Feature Test Требования к макросам для glibc (см. feature_test_macros (7)):
gethostname (): _BSD_SOURCE || _XOPEN_SOURCE> = 500 sethostname (): _BSD_SOURCE || (_XOPEN_SOURCE && _XOPEN_SOURCE <500)
Итак:
#define _BSD_SOURCE
#include <unistd.h>
void test() {
char string[40];
gethostname(string,40);
}
Кровавые подробности:
Если вы не укажете параметр -std-c99
, тогда features.h
(который неявно включен unistd.h
) по умолчанию будет иметь значение _BSD_SOURCE
таким образом, что будет включен прототип для gethostname ()
. Однако указание -std = c99
заставляет компилятор автоматически определять __ STRICT_ANSI __
, что, в свою очередь, приводит к тому, что features.h
не определяет _BSD_SOURCE
, если вы не используете его собственное определение макроса функции (как указано выше).
gethostname ()
не является стандартной функцией C (она нигде не упоминается в стандарте C99), поэтому символ неправильно определен при компиляции в соответствии со стандартом.
Если вы используете набор инструментов gcc
, используйте -std = gnu99
, и вы получите желаемое поведение.
В качестве альтернативы, глядя на
, кажется, что вы могли бы использовать -D_GNU_SOURCE
или -D_XOPEN_SOURCE = 500
, чтобы получить желаемое поведение.
Прочтите man gethostname
. В требованиях к макросу для тестирования функций указано, что для получения имени хоста из unistd.h требуется _BSD_SOURCE
(или _XOPEN_SOURCE> 500
).
Далее прочтите man feature_test_macros
. Вы обнаружите, что -std = c99
включает __ STRICT_ANSI __
, который в выключает _BSD_SOURCE
. Это означает, что вы не сможете получить gethostname
из unistd.h
, если не определите _BSD_SOURCE
снова. Обычно я помещаю _GNU_SOURCE в мою командную строку (т.е. gcc -D_GNU_SOURCE -std = c99 file.c
) для большинства вещей, что также включает _BSD_SOURCE
.
P.S. Страница руководства содержит пример программы, которая может распечатать текущие ft-макросы. Вы можете скомпилировать и запустить его для некоторых настроек компилятора.