You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Document that os.path.ismount() returns true for nested btrfs subvolumes #81520
Lets say, we have a btrfs partion with subvolumes @, mounted at /
and home, which was created directly inside @, such that after mounting @, it can be found at /home.
Then
os.path.ismount("/home") returns True
I would not have expected that, because the program findmnt from the util-linux software package doesn't list it if I run
findmnt -A
I think that the two programs should agree on whether it's a mount point or not but am unsure whether findmnt or os.path.ismount should be altered because I don't know a definite definition of a mountpoint.
Note that I agree with the current behaviour for explicitely mounted subvolumes. An example would be if I have the subvolume @ mounted at / and a subvolume @home created at the toplevel of the btrfs filesystem which is then mounted at /home.
Here findmnt and os.path.ismount agree that this is a mount point.
os.path.ismount() uses the same simple algorithm as a portable version of mountpoint. But mountpoint (and findmnt) from util-linux uses Linux specific methods (reads /proc/mounts or something like). See also bpo-29707.
eike-fokken commented on Jun 20, 2019
eike-fokkenmannequin
MannequinAuthor
More actions
I read the other issue, thanks.
What do you mean by "portable version of mountpoint"? Is there a portable version of mountpoint or was it more a figure of speech?
Concerning the issue itself:
What are the priorities with the behaviour of ismount?
Is it more important to be consistent with the system it is run on or is it more important that every python instance on every system would return the same values?
I see merits for both, I'm just curious what the python developers value more.
In case it is the later I propose to change the docs on ismount again to include that it disagrees with Linux on nested btrfs subvolumes.
If you like I can make a pull request for that.
My favourite solution would be to have agreement with linux on this but at the moment I have no idea how that could be implemented without resorting to Linux native utilities.
What do you mean by "portable version of mountpoint"?
posixpath.ismount is based on a portable method to detect a mountpoint in Unix systems, since POSIX lacks a portable function for this. The implementation is simple. A symlink is never a mountpoint. Otherwise compare the lstat of the path and its parent directory. It's a mountpoint if the st_dev fields are different. If not, it's a mountpoint if the st_ino fields are the same (e.g. "/").
The portable method may fail in particular cases. For instance, a bind mount in the Linux kernel (not bindfs) doesn't create a new device. For example, given "/opt" is bound to "opt" in the current directory on the same filesystem, ismount returns a false negative:
>>> posixpath.ismount('opt')
False
But it's a mountpoint according to the "/proc/self/mountinfo" table:
>>> os.system('mountpoint opt')
opt is a mountpoint
0
The above false negative is documented, so a precedent exists to simply document the false positive with a btrfs subvolume. Developers can make of it what they will. If it matters to not count this case as a mountpoint, a script will have to implement its own platform-specific solution (e.g. use subprocess to call mountpoint).
Ok,
this is my proposal for the documentation. I hope you like it.
Is this the correct place to post it or can I make a direct pull request?
old:
.. function:: ismount(path)
Return ``True`` if pathname *path* is a :dfn:`mount point`: a point in a file
system where a different file system has been mounted. The function checks
whether *path*'s parent, :file:`path/..`, is on a different device than *path*,
or whether :file:`path/..` and *path* point to the same i-node on the same
device --- this should detect mount points for all Unix and POSIX variants.
new:
.. function:: ismount(path)
Return ``True`` if pathname *path* is a :dfn:`mount point`: a point in a file
system where a different file system has been mounted. The function checks
whether *path*'s parent, :file:`path/..`, is on a different device than *path*,
or whether :file:`path/..` and *path* point to the same i-node on the same
device --- this should detect mount points for all Unix and POSIX variants.
Note that in Linux not all mountpoints as recognized by the kernel are found this way.
An example are bind-mounts.
Also some directories return ``True`` although Linux doesn't recognize them as mount points.
An example are nested subvolumes in the Btrfs filesystem
Activity
eike-fokken commentedon Jun 19, 2019
Lets say, we have a btrfs partion with subvolumes @, mounted at /
and home, which was created directly inside @, such that after mounting @, it can be found at /home.
Then
os.path.ismount("/home") returns True
I would not have expected that, because the program findmnt from the util-linux software package doesn't list it if I run
findmnt -A
I think that the two programs should agree on whether it's a mount point or not but am unsure whether findmnt or os.path.ismount should be altered because I don't know a definite definition of a mountpoint.
Note that I agree with the current behaviour for explicitely mounted subvolumes. An example would be if I have the subvolume @ mounted at / and a subvolume @home created at the toplevel of the btrfs filesystem which is then mounted at /home.
Here findmnt and os.path.ismount agree that this is a mount point.
serhiy-storchaka commentedon Jun 19, 2019
What does the mountpoint command returns?
eike-fokken commentedon Jun 19, 2019
mountpoint /nested_subvolume returns
/nested_subvolume is not a mountpoint
mountpoint /explicitely_mounted_subvolume returns
/explicitely_mounted_subvolume is a mountpoint
so agrees with findmnt.
serhiy-storchaka commentedon Jun 19, 2019
os.path.ismount() uses the same simple algorithm as a portable version of mountpoint. But mountpoint (and findmnt) from util-linux uses Linux specific methods (reads /proc/mounts or something like). See also bpo-29707.
eike-fokken commentedon Jun 20, 2019
I read the other issue, thanks.
What do you mean by "portable version of mountpoint"? Is there a portable version of mountpoint or was it more a figure of speech?
Concerning the issue itself:
What are the priorities with the behaviour of ismount?
Is it more important to be consistent with the system it is run on or is it more important that every python instance on every system would return the same values?
I see merits for both, I'm just curious what the python developers value more.
In case it is the later I propose to change the docs on ismount again to include that it disagrees with Linux on nested btrfs subvolumes.
If you like I can make a pull request for that.
My favourite solution would be to have agreement with linux on this but at the moment I have no idea how that could be implemented without resorting to Linux native utilities.
eryksun commentedon Apr 22, 2020
posixpath.ismount is based on a portable method to detect a mountpoint in Unix systems, since POSIX lacks a portable function for this. The implementation is simple. A symlink is never a mountpoint. Otherwise compare the lstat of the path and its parent directory. It's a mountpoint if the st_dev fields are different. If not, it's a mountpoint if the st_ino fields are the same (e.g. "/").
The portable method may fail in particular cases. For instance, a bind mount in the Linux kernel (not bindfs) doesn't create a new device. For example, given "/opt" is bound to "opt" in the current directory on the same filesystem, ismount returns a false negative:
>>> posixpath.ismount('opt') FalseBut it's a mountpoint according to the "/proc/self/mountinfo" table:
>>> os.system('mountpoint opt') opt is a mountpoint 0The above false negative is documented, so a precedent exists to simply document the false positive with a btrfs subvolume. Developers can make of it what they will. If it matters to not count this case as a mountpoint, a script will have to implement its own platform-specific solution (e.g. use subprocess to call
mountpoint).eike-fokken commentedon May 7, 2020
Ok,
this is my proposal for the documentation. I hope you like it.
Is this the correct place to post it or can I make a direct pull request?
old:
.. function:: ismount(path)
Return ``True`` if pathname *path* is a :dfn:`mount point`: a point in a file
system where a different file system has been mounted. The function checks
whether *path*'s parent, :file:`path/..`, is on a different device than *path*,
or whether :file:`path/..` and *path* point to the same i-node on the same
device --- this should detect mount points for all Unix and POSIX variants.
new:
.. function:: ismount(path)
Return ``True`` if pathname *path* is a :dfn:`mount point`: a point in a file
system where a different file system has been mounted. The function checks
whether *path*'s parent, :file:`path/..`, is on a different device than *path*,
or whether :file:`path/..` and *path* point to the same i-node on the same
device --- this should detect mount points for all Unix and POSIX variants.
Note that in Linux not all mountpoints as recognized by the kernel are found this way.
An example are bind-mounts.
Also some directories return ``True`` although Linux doesn't recognize them as mount points.
An example are nested subvolumes in the Btrfs filesystem
12 remaining items
picnixz commentedon Jun 27, 2025
I haven't read the thread but if we can improve the docs, we generally aaccept the PRs.
gh-81520: Document unexpected `os.path.ismount` behaviour with btrfs …
pythongh-81520: Document unexpected `os.path.ismount` behaviour with …
pythongh-81520: Document unexpected `os.path.ismount` behaviour with …
[3.14] gh-81520: Document unexpected `os.path.ismount` behaviour with…
[3.13] gh-81520: Document unexpected `os.path.ismount` behaviour with…
pythongh-81520: Document unexpected `os.path.ismount` behaviour with …
pythongh-81520: Document unexpected `os.path.ismount` behaviour with …
pythongh-81520: Document unexpected `os.path.ismount` behaviour with …
pythongh-81520: Document unexpected `os.path.ismount` behaviour with …
pythongh-81520: Document unexpected `os.path.ismount` behaviour with …
[3.14] pythongh-81520: Document unexpected `os.path.ismount` behaviou…