Platform Specific Headers
There is often a need to provide platform specific macros that allow a developer access to low-level platform functionality.
The benefits of having the C library provide these low-level macros are as follows:
- The C library development headers are already likely to be installed for development. This makes it easy for users to rely on the low-level headers always being there.
- The C library is traditionally the lowest library layer and it makes logical sense to put some of these low-level routines in the library.
- If some functions of the C library use these macros themselves then it makes even more sense from a bootstrapping perspective to have the macros available locally.
The problems with having the C library provide these low-level macros are as follows:
- The macro is not available to systems that don't use glibc, but might use other GNU tools like gcc and binutils.
- A copy of the headers is provided by some other package to support non-glibc platforms tha use GNU tools and we end up with two copies of the header floating around.
The benefits of having GCC provide the header:
- Available to all other OSs that GCC supports.
- The compiler provided headers are already likely to be installed for development. This makes it easy for users to rely on the low-level headers always being there.
- If glibc uses the header in question then it makes bootstrapping harder.
The problems with having the C library provide these low-level macros are as follows:
- GCC is more interested in having the macros be built-in functions that the compiler can schedule.
- GCC does not want to be a catch-all project for platform macros and prefers to stay on the topic of computation and synchronization.
- GCC may change the implementation of the built-in function if the underlying instruction set architecture changes.
The following guidelines help in deciding wether the header should live in GCC or GLIBC:
- If the header provides macros that are ISA specific and have nothing to do with an OS, then GCC should provide them as built-ins.
- If the header provides macros that are OS specific, either GCC or GLIBC could provide the header, though GLIBC is preferred because it already has a lot of information about the OS.
- If the header provides macros that are OS specific, and used by GLIBC, then GLIBC should provide them.
The general solution for providing low-level macros is to export them as follows:
- Non-standard low-level headers that define macros and static inline functions go in:
sys/platform/ if the headers are platform specific but not OS specific.
bits/ if the headers are platform and OS specific.
Each is uniquely named per platform to avoid users thinking they have anything in common e.g., sys/platform/$arch.h or sys/platform/ppc.h, but not sys/platform.h.
The platform can, if they choose, create per-macro header files and then include them into the master platform header e.g., sys/platform/ppc-program-priority-registers.h is included by sys/platform/ppc.h
There should be a coordinated way to include the GCC version of the platform header such that user programs need only ever include sys/platform/$arch.h.
The platform specific header shall pick up the OS specific header by performing a #include <bits/$arch.h>, e.g., #include <bits/ppc.h>.
Document them in manual/platform.texi.
The easiest way to ship a header is to add it to the sysdep_headers variable, for example, the combination of Linux-specific headers on PowerPC could be provided like this:
--- a/sysdeps/powerpc/Makefile +++ b/sysdeps/powerpc/Makefile @@ -26,3 +32,5 @@ gen-as-const-headers += rtld-global-offsets.sym # get offset to __locale_struct.__ctype_tolower gen-as-const-headers += locale-defines.sym endif + +sysdeps_header += sys/platform/ppc.h
--- a/sysdeps/unix/sysv/linux/powerpc/Makefile +++ b/sysdeps/unix/sysv/linux/powerpc/Makefile @@ -15,3 +15,5 @@ endif ifeq ($(subdir),elf) sysdep_routines += dl-vdso endif + +sysdep_headers += bits/ppc.h
Then ensure that you have checked in a sys/platform/ppc.h header underneath your target platform sysdeps directory e.g., sysdeps/powerpc/sys/platform/ppc.h and a bits/ppc.h underneath your target OS specific sysdeps directory e.g., sysdeps/unix/sysv/linux/powerpc/bits/ppc.h.