4051 Commits

Author SHA1 Message Date
Alan Somers
a4856c96d0 fusefs: raise protocol level to 7.12
This commit raises the protocol level and adds backwards-compatibility code
to handle structure size changes.  It doesn't implement any new features.
The new features added in protocol 7.12 are:

* server-side umask processing (which FreeBSD won't do)
* asynchronous inode and directory entry invalidation (which I'll do next)

Sponsored by:	The FreeBSD Foundation
2019-05-29 16:39:52 +00:00
Alan Somers
e039bafa87 fusefs: add comments explaining why 7.11 features aren't implemented
Protocol 7.11 adds two new features, but neither of them were defined
correctly.  FUSE_IOCTL messages don't work for 32-bit daemons on a 64-bit
host (fixed in protocol 7.16).  FUSE_POLL is basically unusable until 7.21.
Before 7.21, the client can't choose which events to register for; the
client registers for "something" and the server replies to say which events
the client is registered for.  Also, before 7.21 there was no way for a
client to deregister a file handle.

Sponsored by:	The FreeBSD Foundation
2019-05-29 02:03:08 +00:00
Alan Somers
9c62bc7045 fusefs: raise protocol level to 7.11
This commit adds the definitions for protocol 7.11 but doesn't yet implement
the new features.  The new features are optional, so they can come later.

Sponsored by:	The FreeBSD Foundation
2019-05-29 00:54:49 +00:00
Alan Somers
3f105d16a0 fusefs: raise protocol level to 7.10
Protocol version 7.10 has only one new feature, and I'm choosing not to
implement it, so this commit is basically a noop.  The sole new feature is
the FOPEN_NONSEEKABLE flag, which a fuse file system can return to indicate
that a certain file handle cannot be seeked.  However, I'm unaware of any
file system in ports that uses this flag.

Sponsored by:	The FreeBSD Foundation
2019-05-29 00:01:36 +00:00
Alan Somers
d4fd0c8148 fusefs: set the flags fields of fuse_write_in and fuse_read_in
These fields are supposed to contain the file descriptor flags as supplied
to open(2) or set by fcntl(2).  The feature is kindof useless on FreeBSD
since we don't supply all of these flags to fuse (because of the weak
relationship between struct file and struct vnode).  But we should at least
set the access mode flags (O_RDONLY, etc).

This is the last fusefs change needed to get full protocol 7.9 support.
There are still a few options we don't support for good reason (mandatory
file locking is dumb, flock support is broken in the protocol until 7.17,
etc), but there's nothing else to do at this protocol level.

Sponsored by:	The FreeBSD Foundation
2019-05-28 01:09:19 +00:00
Alan Somers
8aa24ed381 fusefs: flock(2) locks must be implemented in-kernel
If a FUSE file system sets the FUSE_POSIX_LOCKS flag then it can support
fcntl(2)-style locks directly.  However, the protocol does not adequately
support flock(2)-style locks until revision 7.17.  They must be implemented
locally in-kernel instead.  This unfortunately breaks the interoperability
of fcntl(2) and flock(2) locks for file systems that support the former.
C'est la vie.

Prior to this commit flock(2) would get sent to the server as a
fcntl(2)-style lock with the lock owner field set to stack garbage.

Sponsored by:	The FreeBSD Foundation
2019-05-28 00:03:46 +00:00
Alan Somers
9bcecf0fd7 fusefs: clear fuse_getattr_in.getattr_flags
Protocol 7.9 adds this field.  We could use it to store the file handle of
the file whose attributes we're requesting.  However, that requires extra
work at runtime to look up a file handle, and I'm not aware of any file
systems that care.  So it's easiest just to clear it.

Sponsored by:	The FreeBSD Foundation
2019-05-27 22:25:39 +00:00
Alan Somers
bda39894c5 fusefs: set FUSE_WRITE_CACHE when writing from cache
This bit tells the server that we're not sure which uid, gid, and/or pid
originated the write.  I don't know of a single file system that cares, but
it's part of the protocol.

Sponsored by:	The FreeBSD Foundation
2019-05-27 21:36:28 +00:00
Alan Somers
93fecd02a1 fusefs: misc build fixes
* Only build the tests on platforms with C++14 support
* Fix an undefined symbol error on lint builds
* Remove an unused function: fiov_clear

Sponsored by:	The FreeBSD Foundation
2019-05-25 21:40:27 +00:00
Alan Somers
e97ae4ad2d fusefs: implement FUSE_ASYNC_READ
If a daemon sets the FUSE_ASYNC_READ flag during initialization, then the
client is allowed to issue multiple concurrent reads for the same file
handle.  Otherwise concurrent reads are not allowed.  This commit implements
it.  Previously we unconditionally disallowed concurrent reads.

Sponsored by:	The FreeBSD Foundation
2019-05-24 05:12:43 +00:00
Alan Somers
ad587bc5df fusefs: fix some garbage left behind by r348209
Sponsored by:	The FreeBSD Foundation
2019-05-24 00:56:50 +00:00
Alan Somers
e76986fde0 fusefs: fix exporting fuse filesystems with nfsd
A previous commit made fuse exportable via userland NFS servers.
Compatibility with the in-kernel nfsd required two more changes:

* During read and write operations, implicitly do a FUSE_OPEN if there isn't
  already a valid file handle.  That's because nfsd never calls VOP_OPEN.
* During VOP_READDIR, if an implicit open was necessary, directory offsets
  from a previous VOP_READDIR may not be valid, so VOP_READDIR may have to
  start from the beginning and read until it encounters the requested
  offset.

I've done only limited testing over NFS, so there are probably still some
more bugs.  Thanks to rmacklem for all of the readdir changes, which he had
made for his pnfs work.

Sponsored by:	The FreeBSD Foundation
2019-05-23 23:06:26 +00:00
Alan Somers
db7b0e747f fusefs: assume the mountpoint's generation is 0
This seems to be libfuse's behavior (its documentation notwithstanding).

Sponsored by:	The FreeBSD Foundation
2019-05-23 22:57:57 +00:00
Alan Somers
e5b50fe736 fusefs: Make fuse file systems NFS-exportable
This commit adds the VOPs needed by userspace NFS servers (tested with
net/unfs3).  More work is needed to make the in-kernel nfsd work, because of
its stateless nature.  It doesn't open files prior to doing I/O.  Also, the
NFS-related VOPs currently ignore the entry cache.

Sponsored by:	The FreeBSD Foundation
2019-05-23 00:44:01 +00:00
Alan Somers
2013b723d3 fusefs: improve attribute cacheing
Consolidate all calls to fuse_vnode_setsize as a result of a file attribute
change to one location in fuse_internal_setattr.  There are still a few
calls elsewhere that happen as a result of a write.

Sponsored by:	The FreeBSD Foundation
2019-05-23 00:22:03 +00:00
Alan Somers
18a2264e27 fusefs: fix "recursing on non recursive lockmgr" panic
When mounted with -o default_permissions and when
vfs.fusefs.data_cache_mode=2, fuse_io_strategy would try to clear the suid
bit after a successful write by a non-owner.  When combined with a
not-yet-committed attribute-caching patch I'm working on, and if the
FUSE_SETATTR response indicates an unexpected filesize (legal, if the file
system has other clients), this would end up calling vtruncbuf.  That would
panic, because the buffer lock was already held by bufwrite or bufstrategy
or something else upstack from fuse_vnop_strategy.

Sponsored by:	The FreeBSD Foundation
2019-05-22 23:30:51 +00:00
Alan Somers
b6b7fe7c7d fusefs: remove the vfs.fusefs.sync_resize syctl, correctly this time
In r347547 I intended to remove the vfs.fusefs.sync_resize sysctl, leaving
fusefs's behavior as though sync_resize had its default value.  But I forgot
that I had already turned off sync_resize in my development system's
/etc/sysctl.conf.

This commit complete removes the optional behavior that was formerly
controlled by sync_resize.  There's no need for explicitly calling
FUSE_SETATTR after every FUSE_WRITE that extends a file.  The daemon can
infer that the file is being extended.  If this sysctl was added as a
workaround for a buggy daemon, there's no clue as to what that daemon may
have been.

Sponsored by:	The FreeBSD Foundation
2019-05-22 19:49:25 +00:00
Alan Somers
a6fac00c53 fusefs: Allow update mounts
Allow "mount -u" to change some mount options for fusefs.

Sponsored by:	The FreeBSD Foundation
2019-05-21 19:34:39 +00:00
Alan Somers
d311d6c467 fusefs: eliminate a superfluous fuse_node_setparent
Sponsored by:	The FreeBSD Foundation
2019-05-20 20:55:01 +00:00
Alan Somers
6f8114adcc fusefs: unset MNT_LOCAL
The kernel can't tell whether or not a fuse file system is truly local.  But
what really matters is two things:

1) Can I/O to a file system block indefinitely?
2) Can the file system bypass the O_BENEATH restriction during lookup?

For fuse, the answer to both of those question is yes.  So as far as the
kernel is concerned, it's a non-local file system.

Sponsored by:	The FreeBSD Foundation
2019-05-20 20:54:09 +00:00
Alan Somers
fe221e0177 fusefs: forward UTIME_NOW to the server
If a user sets both atime and mtime to UTIME_NOW when calling a syscall like
utimensat(2), allow the server to choose what "now" means.  Due to the
design of FreeBSD's VFS, it's not possible to do this for just one of atime
or mtime; it's all or none.

PR:		237181
Sponsored by:	The FreeBSD Foundation
2019-05-16 23:17:39 +00:00
Alan Somers
e7f73af118 fusefs: allow the server to specify st_blksize
If the server sets fuse_attr.blksize to a nonzero value in the response to
FUSE_GETATTR, then the client should use that as the value for
stat.st_blksize .

Sponsored by:	The FreeBSD Foundation
2019-05-16 22:50:04 +00:00
Alan Somers
16bd2d47c7 fusefs: Upgrade FUSE protocol to version 7.9.
This commit upgrades the FUSE API to protocol 7.9 and adds unit tests for
backwards compatibility with servers built for version 7.8.  It doesn't
implement any of 7.9's new features yet.

Sponsored by:	The FreeBSD Foundation
2019-05-16 17:24:11 +00:00
Alan Somers
96192dfce0 fusefs: diff reduction vs the upstream sources
fuse_kernel.h defines the structures used by the FUSE protocol.  Originally
it came from libfuse, but the current source of truth is the Linux kernel.
This commit minimizes the diffs between our version and the Linux version as
of 21f3da95d (protocol version 7.8).

The flags field of struct fuse_listxattr_out and fuse_listxattr_in was an
error in our header.  Those fields don't exist in Linux or libfuse, and
they've never been used in FreeBSD.  In fact, those structs don't even exist
in Linux and libfuse; those projects confusingly overload the identical
fuse_getexattr_in and fuse_getxattr_out structs.

Sponsored by:	The FreeBSD Foundation
2019-05-15 22:51:25 +00:00
Alan Somers
3d15b234a4 fusefs: don't track a file's size in two places
fuse_vnode_data.filesize was mostly redundant with
fuse_vnode_data.cached_attrs.st_size, but didn't have exactly the same
meaning.  It was very confusing.  This commit eliminates the former.  It
also eliminates fuse_vnode_refreshsize, which ignored the cache timeout
value.

Sponsored by:	The FreeBSD Foundation
2019-05-15 00:38:52 +00:00
Alan Somers
96658124d7 fusefs: eliminate superfluous FUSE_GETATTR when filesize=0
fuse_vnode_refreshsize was using 0 as a flag value for filesize meaning
"uninitialized" (thanks to the malloc(...M_ZERO) in fuse_vnode_alloc.  But
this led to unnecessary getattr operations when the filesize legitimately
happened to be zero.  Fix by adding a distinct flag value.

Sponsored by:	The FreeBSD Foundation
2019-05-13 23:30:06 +00:00
Alan Somers
5940f822ae fusefs: remove the vfs.fusefs.data_cache_invalidate sysctl
This sysctl was added > 6.5 years ago and I don't know why.  The description
seems at odds with the code.  While it's supposed to "discard clean cached
data" during VOP_INACTIVE, it looks like it would discard any cached data,
clean or otherwise.

Sponsored by:	The FreeBSD Foundation
2019-05-13 20:57:21 +00:00
Alan Somers
fcefa6ef66 fusefs: remove the vfs.fusefs.mmap_enable sysctl
This sysctl was added > 6.5 years ago for no clear reason.  Perhaps it was
intended to gate an unstable feature?  But now there's no reason to globally
disable mmap.  I'm not deleting the -ono_mmap mount option just yet, because
it might be useful as a workaround for bug 237588.

Sponsored by:	The FreeBSD Foundation
2019-05-13 20:42:09 +00:00
Alan Somers
515183969d fusefs: remove the vfs.fusefs.refresh_size sysctl
This was added > 6.5 years ago with no evident reason why.  It probably had
something to do with the incomplete cached attribute implementation.  But
cache attributes work now.  I see no reason to retain this sysctl.

Sponsored by:	The FreeBSD Foundation
2019-05-13 20:31:10 +00:00
Alan Somers
4d09e76a73 fusefs: remove the vfs.fusefs.sync_resize syctl
This sysctl was added > 6.5 years ago for no clear purpose.  I'm guessing
that it may have had something to do with the incomplete attribute cache.
But the attribute cache works now.  Since there's no clear motivation for
this sysctl, it's best to remove it.

Sponsored by:	The FreeBSD Foundation
2019-05-13 19:47:31 +00:00
Alan Somers
bad4c94dc8 fusefs: remove the vfs.fusefs.fix_broken_io sysctl
This looks like it may have been a workaround for a specific buggy FUSE
filesystem.  However, there's no information about what that bug may have
been, and the workaround is > 6.5 years old, so I consider the sysctl to be
unmaintainable.

Sponsored by:	The FreeBSD Foundation
2019-05-13 19:31:09 +00:00
Alan Somers
4abf87666a fusefs: reap dead sysctls
Remove the "sync_unmount" and "init_backgrounded" sysctls and the associated
options from mount_fusefs.  Add no backwards-compatibility hidden options to
mount_fusefs because these options never had any effect, and are therefore
unlikely to be used.

Sponsored by:	The FreeBSD Foundation
2019-05-13 19:03:46 +00:00
Alan Somers
7648bc9fee MFHead @347527
Sponsored by:	The FreeBSD Foundation
2019-05-13 18:25:55 +00:00
Alan Somers
8350cbd8d6 [skip ci] fusefs: remove an obsolete comment
Sponsored by:	The FreeBSD Foundation
2019-05-13 15:39:54 +00:00
Alan Somers
f82e92e52b fusefs: enhance an SDT probe added in r346998
Sponsored by:	The FreeBSD Foundation
2019-05-13 15:39:19 +00:00
Alan Somers
0a7c63e075 fusefs: Report the number of available ops in kevent(2)
Just like /dev/devctl, /dev/fuse will now report the number of operations
available for immediate read in the kevent.data field during kevent(2).

Sponsored by:	The FreeBSD Foundation
2019-05-12 15:27:18 +00:00
Alan Somers
3429092cd1 fusefs: support kqueue for /dev/fuse
/dev/fuse was already pollable with poll and select.  Add support for
kqueue, too.  And add tests for polling with poll, select, and kqueue.

Sponsored by:	The FreeBSD Foundation
2019-05-11 22:58:25 +00:00
Alan Somers
7e0aac2408 fusefs: return ENOTCONN instead of EIO if the daemon dies suddenly
If the daemon dies, return ENOTCONN for all operations that have already
been sent to the daemon, as well as any new ones.

Sponsored by:	The FreeBSD Foundation
2019-05-10 16:41:33 +00:00
Alan Somers
d5024ba275 fusefs: minor optimization to interrupted fuse operations
If the daemon is known to ignore FUSE_INTERRUPT, then we may as well block
all signals while waiting for a response.

Sponsored by:	The FreeBSD Foundation
2019-05-10 16:31:51 +00:00
Alan Somers
8b73a4c5ae fusefs: fix running multiple daemons concurrently
When a FUSE daemon dies or closes /dev/fuse, all of that daemon's pending
requests must be terminated.  Previously that was done in /dev/fuse's
.d_close method.  However, d_close only gets called on the *last* close of
the device.  That means that if multiple daemons were running concurrently,
all but the last daemon to close would leave their I/O hanging around.  The
problem was easily visible just by running "kyua -v parallelism=2 test" in
fusefs's test directory.

Fix this bug by terminating a daemon's pending I/O during /dev/fuse's
cdvpriv dtor method instead.  That method runs on every close of a file.

Also, fix some potential races in the tests:
* Clear SA_RESTART when registering the daemon's signal handler so read(2)
  will return EINTR.
* Wait for the daemon to die before unmounting the mountpoint, so we won't
  see an unwanted FUSE_DESTROY operation in the mock file system.

Sponsored by:	The FreeBSD Foundation
2019-05-10 15:02:29 +00:00
Alan Somers
d5ff268834 fusefs: create sockets with FUSE_MKNOD, not FUSE_CREATE
libfuse expects sockets to be created with FUSE_MKNOD, not FUSE_CREATE,
because that's how Linux does it.  My first attempt at creating sockets
(r346894) used FUSE_CREATE because FreeBSD uses VOP_CREATE for this purpose.
There are no backwards-compatibility concerns with this change, because
socket support hasn't yet been merged to head.

Sponsored by:	The FreeBSD Foundation
2019-05-09 16:25:01 +00:00
Alan Somers
002e54b0aa fusefs: clear a dir's attr cache when its contents change
Any change to a directory's contents should cause its mtime and ctime to be
updated by the FUSE daemon.  Clear its attribute cache so we'll get the new
attributs the next time that they're needed.  This affects the following
VOPs: VOP_CREATE, VOP_LINK, VOP_MKDIR, VOP_MKNOD, VOP_REMOVE, VOP_RMDIR, and
VOP_SYMLINK

Reported by:	pjdfstest
Sponsored by:	The FreeBSD Foundation
2019-05-09 01:16:34 +00:00
Alan Somers
8e45ec4e64 fusefs: fix a permission handling bug during VOP_RENAME
If the file to be renamed is a directory and it's going to get a new parent,
then the user must have write permissions to that directory, because the
".." dirent must be changed.

Reported by:	pjdfstest
Sponsored by:	The FreeBSD Foundation
2019-05-08 22:28:13 +00:00
Alan Somers
d943c93e76 fusefs: allow non-owners to set timestamps to UTIME_NOW
utimensat should allow anybody with write access to set atime and mtime to
UTIME_NOW.

PR:		237181
Sponsored by:	The FreeBSD Foundation
2019-05-08 19:42:00 +00:00
Alan Somers
4ae3a56cb1 fusefs: updated cached attributes during VOP_LINK.
FUSE_LINK returns a new set of attributes.  fusefs should cache them just
like it does during other VOPs.  This is not only a matter of performance
but of correctness too; without caching the new attributes the vnode's nlink
value would be out-of-date.

Reported by:	pjdfstest
Sponsored by:	The FreeBSD Foundation
2019-05-08 18:12:38 +00:00
Alan Somers
a2bdd7379b fusefs: drop suid after a successful chown by a non-root user
Drop sgid too.  Also, drop them after a successful chgrp.

Reported by:	pjdfstest
Sponsored by:	The FreeBSD Foundation
2019-05-07 22:38:13 +00:00
Alan Somers
4e83d6555e fusefs: allow the null chown and null chgrp
Even an unprivileged user should be able to chown a file to its current
owner, or chgrp it to its current group.  Those are no-ops.

Reported by:	pjdfstest
Sponsored by:	The FreeBSD Foundation
2019-05-07 01:27:23 +00:00
Alan Somers
1c8a5f5e39 fusefs: disable posix_fallocate
fuse file systems have far too much variability for the standard
posix_fallocate implementation to work.  A future protocol revision (7.19)
adds a FUSE_FALLOCATE operation, but we don't support that yet.  Better to
simply return EINVAL until then.

Reported by:	pjdfstest
Sponsored by:	The FreeBSD Foundation
2019-05-07 00:03:05 +00:00
Alan Somers
3fa127896b fusefs: allow ftruncate on files without write permission
ftruncate should succeed as long as the file descriptor is writable, even if
the file doesn't have write permission.  This is important when combined
with O_CREAT.

Reported by:	pjdfstest
Sponsored by:	The FreeBSD Foundation
2019-05-06 20:46:58 +00:00
Alan Somers
8cfb44315a fusefs: Fix another obscure permission handling bug
Don't allow unprivileged users to set SGID on files to whose group they
don't belong.  This is slightly different than what POSIX says we should do
(clear sgid on return from a successful chmod), but it matches what UFS
currently does.

Reported by:	pjdfstest
Sponsored by:	The FreeBSD Foundation
2019-05-06 16:54:35 +00:00