Linux applications depend on two different interfaces: the kernel system-call ABI and a C library. The ABI defines the transition into the kernel for a particular architecture. A C library implements the ISO C and POSIX interfaces that programs compile against, and it adds the process-startup code, dynamic loader, name-service lookup, threading support, locale handling, and many interfaces that do not map to one system call. The kernel therefore does not provide a complete C runtime.
GNU libc Origins and Releases #
Richard Stallman announced the GNU Project on September 27, 1983. GNU libc development followed in the later 1980s; Roland McGrath made some of the earliest published contributions. A 1988 GNU Bulletin reported that most libraries were complete.
Early release material must be treated carefully. The GNU FTP archives retain historical glibc patches and the release archive, but archival coverage is not a complete release database. For example, releases and patches from the glibc 1.x era have different availability and dating conventions. The archives are stronger evidence than retrospective version lists or package metadata.
glibc 2.0 was released in January 1997, and the 2.x series became GNU libc’s continuing ABI line. Current source, release material, and the manual are maintained by the project at sourceware.org and in the glibc source repository. “glibc 2.x” describes a source and ABI family; compatibility for supported older interfaces is managed through ABI rules rather than changing the major library filename for every release.
From Linux libc to glibc #
Early Linux systems adapted GNU libc code, then Linux developers maintained a Linux-specific fork while upstream glibc developed separately. The fork is commonly called Linux libc. Its shared-library generations included libc4 and libc5:
- libc4 and earlier supported programs in the historical
a.outexecutable environment. - libc5 accompanied Linux’s transition to ELF shared objects, enabling the modern dynamic-linking model used by distributions.
- Distributions later migrated to GNU libc 2.x. Debian-derived package names such
as
libc6identify the glibc 2.x shared-library ABI generation; they do not mean “glibc version 6.”
The kernel.org libc5 archive preserves later source snapshots. It is the appropriate starting point for source history; claims about a particular fork point, release date, or maintainer should be checked against the corresponding archived tree or release announcement. Directory reorganizations and imported code make a single-source-lineage claim misleading.
Why a libc Transition Is an ABI Migration #
Replacing libc requires more than recompiling an executable because the library participates in the process ABI:
- startup objects arrange entry into
mainand process termination; - the dynamic loader finds shared objects and resolves symbols;
- exported structures, calling conventions, and versioned symbols determine whether old binaries continue to load;
- the resolver and Name Service Switch (NSS) modules implement service lookups; and
- POSIX threads coordinate userspace state with kernel synchronization primitives.
An upgrade therefore must keep the loader, development headers, shared libraries,
NSS modules, package manager, and recovery tools consistent. A binary built against
one libc can fail before main if it requires an unavailable symbol version or if
the interpreter recorded in its ELF PT_INTERP segment cannot be found. glibc’s
ABI list documents that supported
architectures expose different symbol sets and version baselines.
Linux C Library Choices #
glibc is not the only C library implementing the Linux system-call ABI:
- musl emphasizes a compact, standards-oriented design and is common in static and minimal systems.
- uClibc-ng targets embedded Linux systems with configurable features.
- Android’s Bionic is tailored to the Android platform.
Source compatibility does not imply binary compatibility. glibc extensions, symbol versions, dynamic-loader behavior, NSS modules, and ABI details can make a program specific to glibc even when its source appears portable. Use maintained project manuals for current behavior, and use release archives, original headers, the target architecture ABI, and the matching kernel version when investigating a historical binary.
Reading Historical Documentation #
Current manual pages document current interfaces and may record when behavior appeared or changed. Historical source and binaries must be interpreted against the original headers, C library, architecture ABI, and kernel behavior. Archive material provides context for the libc5-to-glibc transition, but current builds should follow the documentation maintained by the selected C library and distribution.
Comments
Read or comment on GitHub (sign-in required to comment)