Почему разные заголовки имеют одинаковое имя? - PullRequest
7 голосов
/ 19 июля 2011

У меня есть несколько копий, скажем, stddef.h в моей системе, одна находится в пути /usr/include/linux/stddef.h и выглядит следующим образом:

#ifndef _LINUX_STDDEF_H
#define _LINUX_STDDEF_H

#undef NULL
#if defined(__cplusplus)
#define NULL 0
#else
#define NULL ((void *)0)
#endif

#endif

Другая находится в пути /usr/lib/i386-linux-gnu/gcc/i686-linux-gnu/4.5/include/ и это тот, который используется, когда я говорю #include <stddef.h>.То, что его содержание сильно отличается от первого, содержит определения ptrdiff_t, size_t и т. Д.

Мой вопрос: насколько мне известно, стандарты C / C ++ требуют, чтобы определениеиз size_t следует поместить в stddef.h, однако первый не следует за этим.Это явно не то, что упоминается в стандартах C / C ++.Если этот файл включен для какой-то другой цели, почему оба этих файла названы stddef.h, не было бы безопаснее / понятнее, если бы они имели разные имена?

Ответы [ 3 ]

3 голосов
/ 19 июля 2011

Ядро linux не связывается со стандартной библиотекой c, поэтому, как правило, стандартные включаемые файлы не могут использоваться безопасно, поэтому ядро ​​linux использует свои собственные включаемые файлы, которые, как известно, не используют функции библиотеки c или данные.

Любое программное обеспечение, которое должно работать в пространстве ядра, например модули ядра, должно использовать файлы include / linux, а не файлы стандартной библиотеки.

Очевидно, что включаемые файлы ядра охватывают только то, что, вероятно, потребуется в ядре, поэтому это очень небольшое подмножество стандартных включаемых файлов с.

0 голосов
/ 19 июля 2011

Я думаю, что один связан с заголовком GCC Standerd, а другой связан с определением ядра.Таким образом, содержимое различно с одной и той же целью в разных сферах.

0 голосов
/ 19 июля 2011

Стандарт C требует, чтобы для определения size_t было достаточно, включая stddef.h. Под капотом его можно выложить по желанию разработчиков библиотеки.

Вы увидите это много в linux, прежде всего потому, что многие реализации различаются в разных системах (например, x86 против arm), и проще всего поместить определенную версию в отдельный каталог.

Примечание. Однако в конкретном случае /usr/include/linux/stddef.h это заголовок ядра (предназначен для компиляции ядра). Это не предназначалось для включения в исходный код пользовательского пространства.


Этот edit должен ответить на комментарий shinkou. Я не знаю, как делать многострочные комментарии, так что это самый простой способ:

$ cat incltest.c 
#include <stddef.h>

$ cpp -H incltest.c
...
. /usr/lib/x86_64-linux-gnu/gcc/x86_64-linux-gnu/4.5.2/include/stddef.h
...

Вы можете сделать это для любого заголовка.

Как правило, если в вашей системе несколько версий GCC, у вас будет несколько версий cpp (и, следовательно, вы можете видеть, что разные версии используются разными компиляторами):

$ cpp-4.4 -H incltest.c 
. /usr/lib/x86_64-linux-gnu/gcc/x86_64-linux-gnu/4.4.5/include/stddef.h
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...