Date: Wed, 12 Jul 2017 22:19:52 +1000 (EST) From: Bruce Evans <brde@optusnet.com.au> To: John Baldwin <jhb@freebsd.org> Cc: Ian Lepore <ian@freebsd.org>, Edward Tomasz Napierala <trasz@freebsd.org>, rgrimes@freebsd.org, src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: Re: svn commit: r320803 - head/sbin/mount Message-ID: <20170712200850.T1271@besplex.bde.org> In-Reply-To: <5242112.0aHCQARnit@ralph.baldwin.cx> References: <20170708171641.GA1129@brick> <20170711201230.GB1725@brick> <1499805315.45330.14.camel@freebsd.org> <5242112.0aHCQARnit@ralph.baldwin.cx>
next in thread | previous in thread | raw e-mail | index | archive | help
On Tue, 11 Jul 2017, John Baldwin wrote: > On Tuesday, July 11, 2017 02:35:15 PM Ian Lepore wrote: >> I think the docs on this are pretty clear... under -u it says: >> >> The set of options is determined by applying the options specified >> in the argument to -o and finally applying the -r or -w option. >> >> To me, that says that nothing in /etc/fstab is germane to mount -u >> unless one of the other args to mount -u is -o fstab. >> >> This change (r320803) seems like an acceptable workaround, but I think >> the correct long term fix would be to not even open /etc/fstab on mount >> -u without -o fstab. But that may be harder to do than to say; I still >> haven't actually looked at the code involved. I thought that it did do that (not look in fstab, except possibly for pathnames). > I concur with this. I've always viewed '-u' as meaning "apply a delta > to the current configuration", not "add this delta to the fstab options > and then apply that entire set of options". In practice, it seems that > it doesn't do either of those, but instead it seems to treats the options > passed to -o as the entire list of options. This is perhaps a bit > surprising. I thought that everyone knew that the behaviour is to blow away the current options, since this is surprisingly bad. My fingers know this, and exploit it to reduce typing for mounting the root file system rw: - "rw" is not an option, but is the absense of the "ro" option, so to change the root file system from read-only to read-write, my fingers type "mount /" -- this blows away "ro" - however, all my fs's are mounted with noatime and I don't want to blow this away unintentionally. My fingers know this, so they actually type "mount -o noatime" for the previous operation. This is part of a large suite of design and implementation bugs. dwmalone@ added [-u -o] "fstab" and "current" options to give more control and save typing, but these weren't complete and they rotted with the larger design and implementation bug nmount(2). "current" only gives the current settings that are in the mount flags returned by statfs(2), and "fstab" doesn't blow away the current settings that aren't in the mount flags. nmount(2) increased the problem by making it too easy to add unstructured options that are not in the mount flags and moving parsing of options to the kernel. mount(8) with no args only displays the options in the mount flags. > For example, suppose you had this: > > /etc/fstab: > > /dev/md0 /bar ufs ro,noauto,noexec 0 0 > > # mount /bar > # mount | grep bar ooooooop > /dev/md0 on /bar (ufs, local, noexec, read-only) > # mount -u -o rw /bar > /dev/md0 on /bar (ufs, local) > > (We just lost "noexec" from fstab by upgrading to read-write) Expect to lose that are in the mount flags like this. But unstructured options tend to be sticky due to undocumented implementation details. This causes my most problems with nfs tcp/udp flags and nfs read/write sizes. Even when these were parsed in nfs_mount(8), IIRC the absence of an option in the command line was passed to the kernel as nothing and interpreted by the kernel as a null change. With nmount(2), userland does almost no option processing so more clearly passes absent options as nothing so the result is whatever undocumented interpretation the kernel prefers. For read/write sizes, nfs also "fixes" wrong sizes by adjusting to limits. There is API for determining what sizes its ends up with, so the only way to know what sizes you are setting is to always set sizes that won't be adjusted and remember what these are in userland. > # mount -u -o nosuid /bar > # mount | grep bar > /dev/md0 on /bar (ufs, local, nosuid) > > (Did not lose "read-write" somehow, RO vs RW must be magically sticky?) RW is just the default. It is not a flag, but the absense of the "ro" flag. nmount(2) still handles negative options worse than mount(8) using much much larger code, but after many years of fixes it handles this "rw" negative option well enough. Most generic flags have 3 variants like "ro", "noro" and "nonoro", and "ro" also has variants "" "rw". Non-generic flags (implemented in individual file systems) tend to have less orthogonality. Sometimes if the basic flag is "nofoo", there is no flag "foo". Sometimes there is a flag "nonofoo" to negate "foo". > # mount -u -o fstab,nosuid /bar > # mount |grep bar > /dev/md0 on /bar (ufs, local, noexec, nosuid) > > (Did not honor "ro" from fstab! Left mount RW) Correction: after many years of fixes, nmount(2) still doesn't understand the "ro" flag. This example works correctly with old mount utilities using mount(2). This is with the same current kernel -- mount(8) from FreeBSD-~5.2 parses the options correctly and then uses mount(2), while mount(8) from FreeBSD-10 uses nmount(2). Even nmount(2) can handle this, so the bug must be in parsing or concatenating fstab options. "fstab" seems to work correctly with newer mount(8) for options in fstab except "ro". > It would seem that there is no actual rhyme or reason to how mount -u works, > and certainly Edward's change doesn't make it worse. I would like to have > some kind of mode where you can toggle one or more options without disturbing > others. Maybe if we had a new "special" option called "current" or some such > that is like "fstab" but instead represents the options currently in force, > then you could do true delta operations via 'mount -o current,rw -u /foo'. > As it is, there doesn't currently seem to a reliable way to achieve that > functionality. -u -o current was implemented in 1999, but never really worked. To summarize, -u tends to preserve the current settings for everything except the mount flags that you can actually see, and should change all of those flags to 0. So -u -o -current tends to preserve everything. Bruce
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20170712200850.T1271>