#40893 [Opn]: PHP reports wrong total and free space for NFS-mounted filesystems on RedHat

From: Date: Sat, 24 Mar 2007 13:19:37 +0000
Subject: #40893 [Opn]: PHP reports wrong total and free space for NFS-mounted filesystems on RedHat
References: 1  Groups: php.bugs 
Request: Send a blank email to php-bugs+get-110751@lists.php.net to get a copy of this message
ID: 40893 User updated by: andrew at digicol dot de Reported By: andrew at digicol dot de Status: Open Bug Type: Filesystem function related Operating System: Redhat EL4 PHP Version: 4.4.5 New Comment: I have no solution, but an explanation: Looking at the code for PHP's filestat.c we see: When statfs is called, size is bytestotal = f_blocks * f_bsize When statvfs is called, size is bytestotal = f_blocks * f_frsize Looking at the system trace, which shows statfs, indicates f_bsize is used, looking at what PHP actually shows for disk_total_space indicates f_frsize is used in the calculation. The problem with RedHat Linux seems to be that is has statvfs, but this calls statfs internally. This is a problem, it confuses PHP about what block size parameter to use for space calculations. I add the following lines to the function disk_total_space in ext/standard/filestat.c and re-compiled php: #if defined(HAVE_SYS_STATVFS_H) && defined(HAVE_STATVFS) syslog(LOG_INFO, "# include <sys/statvfs.h>\n"); #elif defined(HAVE_SYS_STATFS_H) && defined(HAVE_STATFS) syslog(LOG_INFO, "# include <sys/statfs.h>\n"); #elif defined(HAVE_SYS_MOUNT_H) && defined(HAVE_STATFS) syslog(LOG_INFO, "# include <sys/mount.h>\n"); #endif The following command: strace /dot/dc/bin/php-5.2.0-logging/bin/php -r 'echo number_format(disk_total_space("/mnt")) . "\n";' will show: .. statfs("/mnt", {f_type="NFS_SUPER_MAGIC", f_bsize=32768, f_blocks=9158253, f_bfree=5093336, f_bavail=5093336, f_files=0, f_ffree=0, f_fsid={0, 0}, f_namelen=255, f_frsize=4096}) = 0 .. and the this appears in /var/log/messages: Mar 24 14:02:20 dc5ora10gr2 php: # include <sys/statvfs.h> I haven't looked at the source code for df but somehow it is able to cope with it. Previous Comments: ------------------------------------------------------------------------ [2007-03-22 21:26:56] andrew at digicol dot de We get the correct sizes with df (I would not have considered posting the bug report otherwise). We are using df (coreutils) 5.2.1 on RedHat. The RedHat version is RHEL 4 btw, not 3. Maybe it is an NFS-related bug that is handled gracefully in df. ------------------------------------------------------------------------ [2007-03-22 17:19:58] tony2001@php.net From what I can see in df sources, it uses exactly the same logics as PHP, so I don't really see how it's possible that you get correct values with df, especially taking into account that the f_frsize is broken in the same way there. You might want to look at this RH bug: https://bugzilla.redhat.com/bugzilla/show_bug.cgi?id=146427 It says that RHEL3 U4 fixes it. ------------------------------------------------------------------------ [2007-03-22 15:38:21] andrew at digicol dot de RedHat Linux: strace /dot/dc/bin/php/bin/php -r 'echo number_format(disk_total_space("/mnt")) . "\n";' ... statfs("/mnt", {f_type="NFS_SUPER_MAGIC", f_bsize=32768, f_blocks=9158253, f_bfree=5093458, f_bavail=5093458, f_files=0, f_ffree=0, f_fsid={0, 0}, f_namelen=255, f_frsize=4096}) = 0 ... SuSE Linux: strace php -r 'echo number_format(disk_total_space("/mnt")) . "\n";' ... statfs("/mnt", {f_type="NFS_SUPER_MAGIC", f_bsize=32768, f_blocks=9158253, f_bfree=5093458, f_bavail=5093458, f_files=0, f_ffree=0, f_fsid={0, 0}, f_namelen=255, f_frsize=32768}) = 0 ... Just in case this helps, "df -h" seems to invoke the a different system call (statfs64, both systems are 32-bit, I am not an expert regarding system calls). They result in the same f_bsize and fr_size values. Unlike php, df draws the correct conclusions regarding total / free space on both systems: RedHat Linux: strace df -h ... statfs64("/mnt", 84, {f_type="NFS_SUPER_MAGIC", f_bsize=32768, f_blocks=9158253, f_bfree=5093460, f_bavail=5093460, f_files=0, f_ffree=0, f_fsid={0, 0}, f_namelen=255, f_frsize=4096}) = 0 ... SuSE Linux: strace df -h ... statfs64("/mnt", 84, {f_type="NFS_SUPER_MAGIC", f_bsize=32768, f_blocks=9158253, f_bfree=5093460, f_bavail=5093460, f_files=0, f_ffree=0, f_fsid={0, 0}, f_namelen=255, f_frsize=32768}) = 0 ... ------------------------------------------------------------------------ [2007-03-22 15:21:36] tony2001@php.net If you're still able to reproduce it - try to trace it and figure out which blocksize is reported by the system and which function is used - statvfs() or statfs(). ------------------------------------------------------------------------ [2007-03-22 15:17:43] tony2001@php.net Please try using this CVS snapshot: http://snaps.php.net/php5.2-latest.tar.gz For Windows: http://snaps.php.net/win32/php5.2-win32-latest.zip ------------------------------------------------------------------------ The remainder of the comments for this report are too long. To view the rest of the comments, please view the bug report online at http://bugs.php.net/40893 -- Edit this bug report at http://bugs.php.net/?id=40893&edit=1

« previous php.bugs (#110751) next »