Disclaimer: I am not 100% certain whether this is a bug in GNU coreutils
or FreeBSD Linux emulation layer because the behavior is weird. So,
please bear with me.
Consider the following output on FreeBSD 13 from FreeBSD's df(1):
$ df -t ufs -b -T -a
Filesystem Type 512-blocks Used Avail Capacity Mounted on
/dev/da0p2 ufs 4062264 1258336 2478952 34% /
/dev/da0p4 ufs 8106616 279080 7179008 4% /tmp
/dev/da0p5 ufs 8106616 1727528 5730560 23% /var
/dev/da0p6 ufs 16213432 1597320 13319040 11% /var/tmp
/dev/da0p7 ufs 24360504 15754536 6657128 70% /usr
/dev/gvinum/local ufs 48721208 33111696 11711816 74% /usr/local
/dev/gvinum/ports ufs 97482872 47860184 41824064 53% /usr/ports
/dev/gvinum/obj ufs 40614392 31031528 6333720 83% /usr/obj
/dev/gvinum/pgsql ufs 64975096 10500360 49276736 18%
/usr/local/pgsql
/dev/gvinum/nexus2 ufs 64975096 27488304 32288792 46% /var/nexus2
/dev/gvinum/svn ufs 16213432 10366472 4549888 69% /var/svn
/dev/gvinum/osipovmi ufs 60901560 43723800 12305640 78%
/var/osipovmi
/dev/gvinum/poudriere ufs 129990648 74002720 45588680 62%
/var/poudriere
/dev/gvinum/compat ufs 8106616 1969752 5488336 26% /compat
/dev/gvinum/bastille ufs 162498424 117560720 31937832 79%
/usr/local/bastille
and
$ df -t ufs -b -T -a /dev/da0p7
Filesystem Type 512-blocks Used Avail Capacity Mounted on
/dev/da0p7 ufs 24360504 15754536 6657128 70% /usr
Now let's use df(1) from coreutils complied on FreeBSD:
$ gdf -a -B 512 -P -t ufs
Dateisystem 512-Blöcke Benutzt Verfügbar Kapazität Eingehängt auf
/dev/da0p2 4062264 1258336 2478952 34% /
/dev/da0p4 8106616 279080 7179008 4% /tmp
/dev/da0p5 8106616 1727528 5730560 24% /var
/dev/da0p6 16213432 1597320 13319040 11% /var/tmp
/dev/da0p7 24360504 15754536 6657128 71% /usr
/dev/gvinum/local 48721208 33111696 11711816 74% /usr/local
/dev/gvinum/ports 97482872 47860184 41824064 54% /usr/ports
/dev/gvinum/obj 40614392 31031528 6333720 84% /usr/obj
/dev/gvinum/pgsql 64975096 10500488 49276608 18% /usr/local/pgsql
/dev/gvinum/nexus2 64975096 27488304 32288792 46% /var/nexus2
/dev/gvinum/svn 16213432 10366472 4549888 70% /var/svn
/dev/gvinum/osipovmi 60901560 43723800 12305640 79% /var/osipovmi
/dev/gvinum/poudriere 129990648 74002720 45588680 62% /var/poudriere
/dev/gvinum/compat 8106616 1969752 5488336 27% /compat
/dev/gvinum/bastille 162498424 117560728 31937824 79%
/usr/local/bastille
and
$ gdf -a -B 512 -P -t ufs /dev/da0p7
Dateisystem 512-Blöcke Benutzt Verfügbar Kapazität Eingehängt auf
/dev/da0p7 24360504 15754536 6657128 71% /usr
So far so good. Now, I need to use a Linux application on FreeBSD which
expect GNU df(1) in the Linux PATH, did install it and thought at first
that this is a bug in the version I have installed, so I have compiled
latest version on RHEL 7 and copied the executable to FreeBSD:
$ ./df --version
df (GNU coreutils) 9.4
Copyright © 2023 Free Software Foundation, Inc.
Lizenz GPLv3+: GNU GPL Version 3 oder höher <https://gnu.org/licenses/gpl.html>.
Dies ist freie Software: Sie können sie ändern und weitergeben.
Es gibt keinerlei Garantien, soweit wie es das Gesetz erlaubt.
Geschrieben von Torbjörn Granlund, David MacKenzie und Paul Eggert.
$ file ./df
./df: ELF 64-bit LSB executable, x86-64, version 1 (SYSV), dynamically linked,
interpreter /lib64/ld-linux-x86-64.so.2, for GNU/Linux 2.6.32,
BuildID[sha1]=907caf0bb2d7ec27cfbe1f30e7bf63e11328631f, with debug_info, not
stripped
$ file $(which gdf)
/usr/local/bin/gdf: ELF 64-bit LSB executable, x86-64, version 1 (FreeBSD),
dynamically linked, interpreter /libexec/ld-elf.so.1, for FreeBSD 13.2,
FreeBSD-style, stripped
Now let's repeat the operation:
$ ./df -a -B 512 -P -t ufs
Dateisystem 512-Blöcke Benutzt Verfügbar Kapazität Eingehängt auf
/dev/da0p2 4062264 1258336 2478952 34% /
/dev/da0p4 8106616 1969752 5488336 27% /tmp
/dev/da0p5 - - - - /var
/dev/da0p6 16213432 1597320 13319040 11% /var/tmp
/dev/da0p7 - - - - /usr
/dev/gvinum/local 48721208 33111696 11711816 74% /usr/local
/dev/gvinum/ports 97482872 47860184 41824064 54% /usr/ports
/dev/gvinum/obj 40614392 31031528 6333720 84% /usr/obj
/dev/gvinum/pgsql 64975096 10500360 49276736 18% /usr/local/pgsql
/dev/gvinum/nexus2 64975096 27488304 32288792 46% /var/nexus2
/dev/gvinum/svn 16213432 10366472 4549888 70% /var/svn
/dev/gvinum/osipovmi 60901560 43723800 12305640 79% /var/osipovmi
/dev/gvinum/poudriere 129990648 74002720 45588680 62% /var/poudriere
/dev/gvinum/compat - - - - /compat
/dev/gvinum/bastille 162498424 117560736 31937816 79%
/usr/local/bastille
as you can see two filesystems aren't proper and will not appear if the
'-a' is not used. Let's probe this filesystem.
$ ./df -a -B 512 -P -t ufs /dev/da0p7
Dateisystem 512-Blöcke Benutzt Verfügbar Kapazität Eingehängt auf
/dev/da0p7 8106616 1969752 5488336 27% /usr
Does not make sense to me. So I traced both calls with truss to see
where GNU df(1) (the Linux executable) get's the data from.
I can see that both calls do:
linux_open("/dev/da0p7",0x900,030270500) = 3 (0x3)
linux_newfstat(3,0x617140) = 0 (0x0)
close(3) = 0 (0x0)
linux_open("/proc/self/mountinfo",0x80000,0666) = 3 (0x3)
linux_fcntl(0x3,0x3,0x0) = 0 (0x0)
linux_newfstat(3,0x7fffffffc6b0) = 0 (0x0)
linux_mmap2(0x0,0x1000,0x3,0x22,0xffffffffffffffff,0x0) = 34366255104
(0x800637000)
read(3, ...
Now the value in the buffer for read() contains the following in *both*
cases:
590926158 0 0:0 / / rw - ufs /dev/da0p2 rw
1895890801 0 0:0 / /dev rw - devfs devfs rw
699185331 0 0:0 / /tmp rw - ufs /dev/da0p4 rw
2391341225 0 0:0 / /var rw - ufs /dev/da0p5 rw
1704285867 0 0:0 / /var/tmp rw - ufs /dev/da0p6 rw
456922077 0 0:0 / /usr rw - ufs /dev/da0p7 rw
1493237592 0 0:0 / /dev/fd rw - fdescfs fdescfs rw
1037017996 0 0:0 / /usr/local rw - ufs /dev/gvinum/local rw
3473945877 0 0:0 / /usr/ports rw - ufs /dev/gvinum/ports rw
2770259572 0 0:0 / /usr/obj rw - ufs /dev/gvinum/obj rw
2912479969 0 0:0 / /usr/local/pgsql rw - ufs /dev/gvinum/pgsql rw
3422049217 0 0:0 / /var/nexus2 rw - ufs /dev/gvinum/nexus2 rw
3712243071 0 0:0 / /var/svn rw - ufs /dev/gvinum/svn rw
1709919602 0 0:0 / /var/osipovmi rw - ufs /dev/gvinum/osipovmi rw
2191125346 0 0:0 / /var/poudriere rw - ufs /dev/gvinum/poudriere rw
2575517705 0 0:0 / /compat rw - ufs /dev/gvinum/compat rw
829465671 0 0:0 / /usr/local/bastille rw - ufs /dev/gvinum/bastille rw
3036741558 0 0:0 / /proc rw - proc proc rw
2315321230 0
I assume that some code after parsing, likely matching does fail here to
properly identify the filesystem?
Any idea why this happens, where to start digging or what to try?
Michael