John Reiser   jreiser BitWagon com
March 2, 2013

xstat32_EOVERFLOW provides a wrapper shared library which can mitigate problems caused by 64-bit inode numbers that increasingly affect some "32-bit" Linux software using common file systems.

Programs which run in 32-bit mode on Linux are beginning to suffer from feature-creep in the underlying filesystems which hold data. Filesystems have gotten so big that a 32-bit number is no longer wide enough to store the unique identifier for each file. When this happens, then the basic mechanism used by the C language library to lookup information about a file returns an error (EOVERFLOW) and no useful information. This has been true for several years, but the practical effect has been limited because nearly all the unique identifiers used by actual files stored on common files systems have fit into 32 bits. Today the gradual increase in filesystem size, and the accounting techniques used to track the world-wide sea of data, have begun to use more than 32 bits much more frequently.

The C language runtime library and compilation system has been aware of the situation, and for several years the builders of software packages have been able to specify compile-time options which enable correct operation in the larger environment. However, the options are not the default, they cause some (usually very tiny) increase in runtime costs, and for rare packages the increased size breaks some design assumptions. As a result, today about 1000 of the approximately 6000 software packages in the Fedora Project increasingly could break in common usage in 32-bit environments. Usage of files stored in CIFS and accessed over Samba shares is the most likely trouble spot. In theory other file systems such as ZFS, XFS, btrfs, and even ext4 could be affected, but most of the potentially-affected users have migrated already to 64-bit environments (x86_64) where the problem does not exist.

In the vast majority of cases the solution is to rebuild the package using the compile-time option -D_FILE_OFFSET_BITS=64. However in some cases this option can cause cascading effects which require manual intervention. Also, the current implementation of stat(), fstat(), and lstat() in glibc is unfriendly when returning EOVERFLOW due to st_ino not fitting into 32 bits: then glibc leaves st_size undefined! Unfortunately the C standard allows this behavior, and glibc is not interested in improvements. Most applications ignore st_ino but do use st_size and other members. Despite this common usage, the C standard and glibc force the application to care about st_ino anyway. [st_size is 64 bits regardless of options; otherwise .iso images of full DVDs could not be stored.]

Because 32-bit applications are beginning to suffer more often, it is useful to be able to mitigate the damage: continue operation in most cases while the package is being repaired. xstat32_EOVERFLOW.so is a shared library which can be used as a work-around with no-recompilation and no re-linking. When named by the LD_PRELOAD environment variable, then xstat32_OVERFLOW.so intercepts and overrides glibc's internal conversion from stat64 to stat32. The intercept always converts each member of struct stat, so that all members are defined after each call, and contain correct data modulo the width of the member. In particular st_size always is defined, even if st_ino overflows. If any converted member overflows, then the intercept consults environment variable _XSTAT32_EOVERFLOW for options:

Option Effect
ignore return 0 (success); all members are correct modulo width
error return EOVERFLOW (just like before, except st_size has data)
warn print diagnostic on stderr [once]; return EOVERFLOW
abort call abort()

For the warn option, the message looks like:         **** warning [once only]: xstat32 EOVERFLOW member         where member tells st_ino, st_size, or st_nblock.

The implementation constructs xstat32_EOVERFLOW.so from the Fedora .src.rpm for glibc using these files:

file description
xstat32_EOVERFLOW.html this narrative file
xstat32_EOVERFLOW.patch enhancements to xstatconv.c
xstat32_EOVERFLOW.sh the build recipe as a shell script
xstat32_EOVERFLOW.versions symbol version info for ld
xstat32_EOVERFLOW.tgz compressed archive of above files (5KB)