4055 Commits

Author SHA1 Message Date
Alan Somers
44f10c6e40 fusefs: cache negative lookups
The FUSE protocol includes a way for a server to tell the client that a
negative lookup response is cacheable for a certain amount of time.

PR:		236226
Sponsored by:	The FreeBSD Foundation
2019-04-09 21:22:02 +00:00
Konstantin Belousov
ae90941431 Add vn_fsync_buf().
Provide a convenience function to avoid the hack with filling fake
struct vop_fsync_args and then calling vop_stdfsync().

Sponsored by:	The FreeBSD Foundation
MFC after:	1 week
2019-04-09 20:20:04 +00:00
Konstantin Belousov
997febb1e7 Fix dirty buf exhaustion easily triggered with msdosfs.
If truncate(2) is performed on msdosfs file, which extends the file by
system-depended large amount, fs creates corresponding amount of dirty
delayed-write buffers, which can consume all buffers.  Such buffers
cannot be flushed by the bufdaemon because the ftruncate() thread owns
the vnode lock.  So the system runs out of free buffers, and even
truncate() thread starves, which means deadlock because it owns the
vnode lock.

Fix this by doing vnode fsync in extendfile() when low memory or low
buffers condition detected, which flushes all dirty buffers belonging
to the file being extended.

Note that the more usual fallback to bawrite() does not work
acceptable in this situation, because it would only allow one buffer
to be recycled.  Other filesystems, most important UFS, do not allow
userspace to create arbitrary amount of dirty delayed-write buffers
without feedback, so bawrite() is good enough for them.

Reported and tested by:	pho
Sponsored by:	The FreeBSD Foundation
MFC after:	1 week
2019-04-09 19:55:02 +00:00
Alan Somers
ccb75e4939 fusefs: implement entry cache timeouts
Follow-up to r346046.  These two commits implement fuse cache timeouts for
both entries and attributes.  They also remove the vfs.fusefs.lookup_cache
enable sysctl, which is no longer needed now that cache timeouts are
honored.

PR:		235773
Sponsored by:	The FreeBSD Foundation
2019-04-09 17:23:34 +00:00
Alan Somers
3f2c630c74 fusefs: implement attribute cache timeouts
The FUSE protocol allows the server to specify the timeout period for the
client's attribute and entry caches.  This commit implements the timeout
period for the attribute cache.  The entry cache's timeout period is
currently disabled because it panics, and is guarded by the
vfs.fusefs.lookup_cache_expire sysctl.

PR:		235773
Reported by:	cem
Sponsored by:	The FreeBSD Foundation
2019-04-09 00:47:38 +00:00
Alan Somers
cad677915f fusefs: cache file attributes
FUSE_LOOKUP, FUSE_GETATTR, FUSE_SETATTR, FUSE_MKDIR, FUSE_LINK,
FUSE_SYMLINK, FUSE_MKNOD, and FUSE_CREATE all return file attributes with a
cache validity period.  fusefs will now cache the attributes, if the server
returns a non-zero cache validity period.

This change does _not_ implement finite attr cache timeouts.  That will
follow as part of PR 235773.

PR:		235775
Reported by:	cem
Sponsored by:	The FreeBSD Foundation
2019-04-08 18:45:41 +00:00
Rick Macklem
80405bcf79 Add INET6 support for the upcalls to the nfsuserd daemon.
The kernel code uses UDP to do upcalls to the nfsuserd(8) daemon to get
updates to the username<->uid and groupname<->gid mappings.
A change to AF_LOCAL last year had to be reverted, since it could result
in vnode locking issues on the AF_LOCAL socket.
This patch adds INET6 support and the required #ifdef INET and INET6
to the code.

Requested by:	bz
PR:		205193
Reviewed by:	bz, rgrimes
MFC after:	2 weeks
Differential Revision:	http://reviews.freebsd.org/D19218
2019-04-06 21:53:46 +00:00
Alan Somers
2c338af141 fusefs: fix a panic on mount
Don't page fault if the file descriptor provided with "-o fd" is invalid.
This is a merge of r345419 from the projects/fuse2 branch.

Reviewed by:	ngie
Tested by:	Marek Zarychta <zarychtam@plan-b.pwste.edu.pl>
MFC after:	2 weeks
Sponsored by: The FreeBSD Foundation
Differential Revision:	https://reviews.freebsd.org/D19836
2019-04-06 18:04:04 +00:00
Alan Somers
caf5f57d2d fusefs: implement VOP_ACCESS
VOP_ACCESS was never fully implemented in fusefs.  This change:
* Removes the FACCESS_DO_ACCESS flag, which pretty much disabled the whole
  vop.
* Removes a quixotic special case for VEXEC on regular files.  I don't know
  why that was in there.
* Removes another confusing special case for VADMIN.
* Removes the FACCESS_NOCHECKSPY flag.  It seemed to be a performance
  optimization, but I'm unconvinced that it was a net positive.
* Updates test cases.

This change does NOT implement -o default_permissions.  That will be handled
separately.

PR:		236291
Sponsored by:	The FreeBSD Foundation
2019-04-05 18:37:48 +00:00
Alan Somers
efa23d9784 fusefs: enforce -onoallow_other even beneath the mountpoint
When -o allow_other is not in use, fusefs is supposed to prevent access to
the filesystem by any user other than the one who owns the daemon.  Our
fusefs implementation was only enforcing that restriction at the mountpoint
itself.  That was usually good enough because lookup usually descends from
the mountpoint.  However, there are cases when it doesn't, such as when
using openat relative to a file beneath the mountpoint.

PR:		237052
Sponsored by:	The FreeBSD Foundation
2019-04-05 17:21:23 +00:00
Alan Somers
140bb4927a fusefs: correctly return EROFS from VOP_ACCESS
Sponsored by:	The FreeBSD Foundation
2019-04-05 15:33:43 +00:00
Rick Macklem
02c8dd7d72 Revert r320698, since the related userland changes were reverted by r338192.
r338192 reverted the changes to nfsuserd so that it could use an AF_LOCAL
socket, since it resulted in a vnode locking panic().
Post r338192 nfsuserd daemons use the old AF_INET socket for upcalls and
do not use these kernel changes.
I left them in for a while, so that nfsuserd daemons built from head sources
between r320757 (Jul. 6, 2017) and r338192 (Aug. 22, 2018) would need them
by default.
This only affects head, since the changes were never MFC'd.
I will add an UPDATING entry, since an nfsuserd daemon built from head
sources between r320757 and r338192 will not run unless the "-use-udpsock"
option is specified. (This command line option is only in the affected
revisions of the nfsuserd daemon.)

I suspect few will be affected by this, since most who run systems built
from head sources (not stable or releases) will have rebuilt their nfsuserd
daemon from sources post r338192 (Aug. 22, 2018)

This is being reverted in preparation for an update to include AF_INET6
support to the code.
2019-04-04 23:30:27 +00:00
Alan Somers
a7e81cb3db fusefs: properly handle FOPEN_KEEP_CACHE
If a fuse file system returne FOPEN_KEEP_CACHE in the open or create
response, then the client is supposed to _not_ clear its caches for that
file.  I don't know why clearing the caches would be the default given that
there's a separate flag to bypass the cache altogether, but that's the way
it is.  fusefs(5) will now honor this flag.

Our behavior is slightly different than Linux's because we reuse file
handles.  That means that open(2) wont't clear the cache if there's a
reusable file handle, even if the file server wouldn't have sent
FOPEN_KEEP_CACHE had we opened a new file handle like Linux does.

PR:		236560
Sponsored by:	The FreeBSD Foundation
2019-04-04 20:30:14 +00:00
Alan Somers
8d013bec7a fusefs: fix some uninitialized memory references
This bug was long present, but was exacerbated by r345876.

The problem is that fiov_refresh was bzero()ing a buffer _before_ it
reallocated that buffer.  That's obviously the wrong order.  I fixed the
order in r345876, which exposed the main problem.  Previously, the first 160
bytes of the buffer were getting bzero()ed when it was first allocated in
fiov_init.  Subsequently, as that buffer got recycled between callers, the
portion used by the _previous_ caller was getting bzero()ed by the current
caller in fiov_refresh.  The problem was never visible simply because no
caller was trying to use more than 160 bytes.

Now the buffer gets properly bzero()ed both at initialization time and any
time it gets enlarged or reallocated.

Sponsored by:	The FreeBSD Foundation
2019-04-04 20:24:58 +00:00
Rodney W. Grimes
6c1c6ae537 Use IN_foo() macros from sys/netinet/in.h inplace of handcrafted code
There are a few places that use hand crafted versions of the macros
from sys/netinet/in.h making it difficult to actually alter the
values in use by these macros.  Correct that by replacing handcrafted
code with proper macro usage.

Reviewed by:		karels, kristof
Approved by:		bde (mentor)
MFC after:		3 weeks
Sponsored by:		John Gilmore
Differential Revision:	https://reviews.freebsd.org/D19317
2019-04-04 19:01:13 +00:00
Alan Somers
9a696dc6bb MFHead@r345880 2019-04-04 18:26:32 +00:00
Alan Somers
12292a99ac fusefs: correctly handle short writes
If a FUSE daemon returns FOPEN_DIRECT_IO when a file is opened, then it's
allowed to write less data than was requested during a FUSE_WRITE operation
on that file handle.  fusefs should simply return a short write to userland.

The old code attempted to resend the unsent data.  Not only was that
incorrect behavior, but it did it in an ineffective way, by attempting to
"rewind" the uio and uiomove the unsent data again.

This commit correctly handles short writes by returning directly to
userland if FOPEN_DIRECT_IO was set.  If it wasn't set (making the short
write technically a protocol violation), then we resend the unsent data.
But instead of rewinding the uio, just resend the data that's already in the
kernel.

That necessitated a few changes to fuse_ipc.c to reduce the amount of bzero
activity.  fusefs may be marginally faster as a result.

PR:		236381
Sponsored by:	The FreeBSD Foundation
2019-04-04 16:51:34 +00:00
Alan Somers
35cf0e7e56 fusefs: fix a panic in VOP_READDIR
The original fusefs import, r238402, contained a bug in fuse_vnop_close that
could close a directory's file handle while there were still other open file
descriptors.  The code looks deliberate, but there is no explanation for it.
This necessitated a workaround in fuse_vnop_readdir that would open a new
file handle if, "for some mysterious reason", that vnode didn't have any
open file handles.  r345781 had the effect of causing the workaround to
panic, making the problem more visible.

This commit removes the workaround and the original bug, which also fixes
the panic.

Sponsored by:	The FreeBSD Foundation
2019-04-03 20:57:43 +00:00
Alan Somers
9f10f423a9 fusefs: send FUSE_FLUSH during VOP_CLOSE
The FUSE protocol says that FUSE_FLUSH should be send every time a file
descriptor is closed.  That's not quite possible in FreeBSD because multiple
file descriptors can share a single struct file, and closef doesn't call
fo_close until the last close.  However, we can still send FUSE_FLUSH on
every VOP_CLOSE, which is probably good enough.

There are two purposes for FUSE_FLUSH.  One is to allow file systems to
return EIO if they have an error when writing data that's cached
server-side.  The other is to release POSIX file locks (which fusefs(5) does
not yet support).

PR:		236405, 236327
Sponsored by:	The FreeBSD Foundation
2019-04-03 19:59:45 +00:00
Konstantin Belousov
c973ee9e06 msdosfs: zero tail of the last block on truncation for VREG vnodes as well.
Despite the call to vtruncbuf() from detrunc(), which results in
zeroing part of the partial page after EOF, there still is a
possibility to retain the stale data which is revived on file
enlargement.  If the filesystem block size is greater than the page
size, partial block might keep other after-EOF pages wired and they
get reused then.  Fix it by zeroing whole part of the partial buffer
after EOF, not relying on vnode_pager_setsize().

PR:	236977
Reported by:	asomers
Tested by:	pho
Sponsored by:	The FreeBSD Foundation
MFC after:	1 week
2019-04-03 17:02:18 +00:00
Alan Somers
e312493b37 fusefs: during ftruncate, discard cached data past truncation point
During truncate, fusefs was discarding entire cached blocks, but it wasn't
zeroing out the unused portion of a final partial block.  This resulted in
reads returning stale data.

PR:		233783
Reported by:	fsx
Sponsored by:	The FreeBSD Foundation
2019-04-03 02:29:56 +00:00
Alan Somers
d3a8f2dd09 fusefs: fix a just-introduced panic in readdir
r345808 changed the interface of fuse_filehandle_open, but failed to update
one caller.

Sponsored by:	The FreeBSD Foundation
2019-04-02 19:20:55 +00:00
Alan Somers
9e4448719b fusefs: cleanup and refactor some recent commits
This commit cleans up after recent commits, especially 345766, 345768, and
345781.  There is no functional change.  The most important change is to add
comments documenting why we can't send flags like O_APPEND in
FUSE_WRITE_OPEN.

PR:		236340
Sponsored by:	The FreeBSD Foundation
2019-04-02 18:09:40 +00:00
Konstantin Belousov
5c4ce6fac2 tmpfs: plug holes on rw->ro mount update.
In particular:
- suspend the mount around vflush() to avoid new writes come after the
  vnode is processed;
- flush pending metadata updates (mostly node times);
- remap all rw mappings of files from the mount into ro.

It is not clear to me how to handle writeable mappings on rw->ro for
tmpfs best.  Other filesystems, which use vnode vm object, call
vgone() on vnodes with writers, which sets the vm object type to
OBJT_DEAD, and keep the resident pages and installed ptes as is.  In
particular, the existing mappings continue to work as far as
application only accesses resident pages, but changes are not flushed
to file.

For tmpfs the vm object of VREG vnodes also serves as the data pages
container, giving single copy of the mapped pages, so it cannot be set
to OBJT_DEAD.  Alternatives for making rw mappings ro could be either
invalidating them at all, or marking as CoW.

Tested by:	pho
Sponsored by:	The FreeBSD Foundation
MFC after:	2 weeks
Differential revision:	https://reviews.freebsd.org/D19737
2019-04-02 13:59:04 +00:00
Konstantin Belousov
e1cdc30faa tmpfs: ignore tmpfs_set_status() if mount point is read-only.
In particular, this fixes atimes still changing for ro tmpfs.
tmpfs_set_status() gains tmpfs_mount * argument.

Tested by:	pho
Sponsored by:	The FreeBSD Foundation
MFC after:	2 weeks
Differential revision:	https://reviews.freebsd.org/D19737
2019-04-02 13:49:32 +00:00
Konstantin Belousov
ae26575394 Block creation of the new nodes for read-only tmpfs mounts.
Tested by:	pho
Sponsored by:	The FreeBSD Foundation
MFC after:	2 weeks
Differential revision:	https://reviews.freebsd.org/D19737
2019-04-02 13:41:26 +00:00
Alan Somers
f8d4af104b fusefs: send FUSE_OPEN for every open(2) with unique credentials
By default, FUSE performs authorization in the server.  That means that it's
insecure for the client to reuse FUSE file handles between different users,
groups, or processes.  Linux handles this problem by creating a different
FUSE file handle for every file descriptor.  FreeBSD can't, due to
differences in our VFS design.

This commit adds credential information to each fuse_filehandle.  During
open(2), fusefs will now only reuse a file handle if it matches the exact
same access mode, pid, uid, and gid of the calling process.

PR:		236844
Sponsored by:	The FreeBSD Foundation
2019-04-01 20:42:15 +00:00
Alan Somers
363a74163b fusefs: allow opening files O_EXEC
O_EXEC is useful for fexecve(2) and fchdir(2).  Treat it as another fufh
type alongside the existing RDONLY, WRONLY, and RDWR.  Prior to r345742 this
would've caused a memory and performance penalty.

PR:		236329
Sponsored by:	The FreeBSD Foundation
2019-04-01 16:36:02 +00:00
Alan Somers
4a6d5507f7 fusefs: fix an inverted error check in my last commit
This should be merged alongside 345766

Sponsored by:	The FreeBSD Foundation
2019-04-01 16:15:29 +00:00
Alan Somers
5ec10aa527 fusefs: replace obsolete array idioms
r345742 replaced fusefs's fufh array with a fufh list.  But it left a few
array idioms in place.  This commit replaces those idioms with more
efficient list idioms.  One location is in fuse_filehandle_close, which now
takes a pointer argument.  Three other locations are places that had to loop
over all of a vnode's fuse filehandles.

Sponsored by:	The FreeBSD Foundation
2019-04-01 14:23:43 +00:00
Alan Somers
1cedd6dfac fusefs: replace the fufh table with a linked list
The FUSE protocol allows each open file descriptor to have a unique file
handle.  On FreeBSD, these file handles must all be stored in the vnode.
The old method (also used by OSX and OpenBSD) is to store them all in a
small array.  But that limits the total number that can be stored.  This
commit replaces the array with a linked list (a technique also used by
Illumos).  There is not yet any change in functionality, but this is the
first step to fixing several bugs.

PR:		236329, 236340, 236381, 236560, 236844
Discussed with:	cem
Sponsored by:	The FreeBSD Foundation
2019-03-31 03:19:10 +00:00
Alan Somers
5fccbf313a fusefs: don't force direct io for files opened O_WRONLY
Previously fusefs would treat any file opened O_WRONLY as though the
FOPEN_DIRECT_IO flag were set, in an attempt to avoid issuing reads as part
of a RMW write operation on a cached part of the file.  However, the FUSE
protocol explicitly allows reads of write-only files for precisely that
reason.

Sponsored by:	The FreeBSD Foundation
2019-03-30 00:57:07 +00:00
Alan Somers
f220ef0b35 fix the GENERIC-NODEBUG build after r345675
Submitted by:	cy
Reported by:	cy, Michael Butler <imb@protected-networks.net>
MFC after:	2 weeks
X-MFC-With:	345675
2019-03-29 14:07:30 +00:00
Alan Somers
415e34c4d5 MFHead@r345677 2019-03-29 03:25:20 +00:00
Alan Somers
080518d810 fusefs: convert debug printfs into dtrace probes
fuse(4) was heavily instrumented with debug printf statements that could
only be enabled with compile-time flags. They fell into three basic groups:

1. Totally redundant with dtrace FBT probes. These I deleted.
2. Print textual information, usually error messages. These I converted to
   SDT probes of the form fuse:fuse:FILE:trace. They work just like the old
   printf statements except they can be enabled at runtime with dtrace. They
   can be filtered by FILE and/or by priority.
3. More complicated probes that print detailed information. These I
   converted into ad-hoc SDT probes.

Also, de-inline fuse_internal_cache_attrs.  It's big enough to be a regular
function, and this way it gets a dtrace FBT probe.

This commit is a merge of r345304, r344914, r344703, and r344664 from
projects/fuse2.

Reviewed by:	cem
MFC after:	2 weeks
Sponsored by:	The FreeBSD Foundation
Differential Revision:	https://reviews.freebsd.org/D19667
2019-03-29 02:13:06 +00:00
Alan Somers
98852a32af fusefs: fix error handling in fuse_vnop_strategy
Reported by:	cem
Sponsored by:	The FreeBSD Foundation
2019-03-28 21:57:42 +00:00
Alan Somers
f203d1734d fusefs: don't ignore errors in fuse_vnode_refreshsize
Reported by:	Coverity
Coverity CID:	1368622
Sponsored by:	The FreeBSD Foundation
2019-03-27 16:45:30 +00:00
Alan Somers
019dca0199 fusefs: delete dead code in fuse_vnop_setattr
The dead code in question was a broken and incomplete attempt to support the
default_permissions mount option during VOP_SETATTR.  There wasn't anything
there worth saving; I'll have to rewrite it later.

Reported by:	Coverity
Coverity CID:	1008668
Sponsored by:	The FreeBSD Foundation
2019-03-27 16:19:02 +00:00
Alan Somers
3885d4091d fusefs: fix a derefence-after-null-check
Reported by:	Coverity
Coverity CID:	1017940
Sponsored by:	The FreeBSD Foundation
2019-03-27 14:15:35 +00:00
Alan Somers
e0bec057db fusefs: correctly set fuse_release_in.flags in an error path
fuse_vnop_create must close the newly created file if it can't allocate a
vnode.  When it does so, it must use the same file flags for FUSE_RELEASE as
it used for FUSE_OPEN or FUSE_CREATE.

Reported by:	Coverity
Coverity CID:	1066204
Sponsored by:	The FreeBSD Foundation
2019-03-27 02:57:59 +00:00
Alan Somers
4a4282cb06 FUSEFS: during FUSE_READDIR, set the read size correctly.
The old formula was unnecessarily restrictive.

Sponsored by:	The FreeBSD Foundation
2019-03-27 02:01:34 +00:00
Alan Somers
3ba6a4d473 fusefs: set fuse_init_in->max_readahead correctly
The old value was correct only by coincidence.

Sponsored by:	The FreeBSD Foundation
2019-03-27 01:49:35 +00:00
Alan Somers
fd2749f25d fusefs: delete dead code
This change also inlines several previously #define'd symbols that didn't
really have the meanings indicated by the comments.

Sponsored by:	The FreeBSD Foundation
2019-03-26 03:02:45 +00:00
Maxim Sobolev
4f20706113 Refine r345425: get rid of superfluous helper macro that I have added.
MFC after:	2 weeks
2019-03-26 01:28:10 +00:00
Allan Jude
b4b3e3498b Make TMPFS_PAGES_MINRESERVED a kernel option
TMPFS_PAGES_MINRESERVED controls how much memory is reserved for the system
and not used by tmpfs.

On very small memory systems, the default value may be too high and this
prevents these small memory systems from using reroot, which is required
for them to install firmware updates.

Submitted by:	Hiroki Mori <yamori813@yahoo.co.jp>
Reviewed by:	mizhka
Differential Revision:	https://reviews.freebsd.org/D13583
2019-03-25 07:46:20 +00:00
Alan Somers
19ef317d62 fusefs: fallback to MKNOD/OPEN if a filesystem doesn't support CREATE
If a FUSE filesystem returns ENOSYS for FUSE_CREATE, then fallback to
FUSE_MKNOD/FUSE_OPEN.

Also, fix a memory leak in the error path of fuse_vnop_create.  And do a
little cleanup in fuse_vnop_open.

PR:		199934
Reported by:	samm@os2.kiev.ua
Sponsored by:	The FreeBSD Foundation
2019-03-23 00:22:29 +00:00
Maxim Sobolev
ac1a10efad Make it possible to update TMPFS mount point from read-only to read-write
and vice versa.

Reviewed by:	delphij
Approved by:	delphij
MFC after:	2 weeks
Differential Revision:	https://reviews.freebsd.org/D19682
2019-03-22 21:31:21 +00:00
Alan Somers
bf4d70841f fusefs: support VOP_MKNOD
PR:		236236
Sponsored by:	The FreeBSD Foundation
2019-03-22 19:08:48 +00:00
Alan Somers
8ba190efeb fusefs: fix a panic on mount
Don't page fault if the file descriptor provided with "-o fd" is invalid.

Sponsored by:	The FreeBSD Foundation
2019-03-22 17:53:13 +00:00
Alan Somers
6248288e97 fusefs: correctly handle cacheable negative LOOKUP responses
The FUSE protocol allows for LOOKUP to return a cacheable negative response,
which means that the file doesn't exist and the kernel can cache its
nonexistence.  As of this commit fusefs doesn't cache the nonexistence, but
it does correctly handle such responses.  Prior to this commit attempting to
create a file, even with O_CREAT would fail with ENOENT if the daemon
returned a cacheable negative response.

PR:		236231
Sponsored by:	The FreeBSD Foundation
2019-03-21 23:31:10 +00:00