On Tue, Mar 25, 2025 at 05:06:54PM +0100, Hanna Czenczek wrote:
> FUSE allows creating multiple request queues by "cloning" /dev/fuse FDs
> (via open("/dev/fuse") + ioctl(FUSE_DEV_IOC_CLONE)).
>
> We can use this to implement multi-threading.
>
> Note that the interface presented here differs from the multi-queue
> interface of virtio-blk: The latter maps virtqueues to iothreads, which
> allows processing multiple virtqueues in a single iothread. The
> equivalent (processing multiple FDs in a single iothread) would not make
> sense for FUSE because those FDs are used in a round-robin fashion by
> the FUSE kernel driver. Putting two of them into a single iothread will
> just create a bottleneck.
>
> Therefore, all we need is an array of iothreads, and we will create one
> "queue" (FD) per thread.
>
> @@ -275,14 +351,24 @@ static int fuse_export_create(BlockExport *blk_exp,
>
> g_hash_table_insert(exports, g_strdup(exp->mountpoint), NULL);
>
> - exp->fuse_fd = fuse_session_fd(exp->fuse_session);
> - ret = fcntl(exp->fuse_fd, F_SETFL, O_NONBLOCK);
> + assert(exp->num_queues >= 1);
> + exp->queues[0].fuse_fd = fuse_session_fd(exp->fuse_session);
> + ret = fcntl(exp->queues[0].fuse_fd, F_SETFL, O_NONBLOCK);
As mentioned before, F_SETFL should be set by read-modify-write.
--
Eric Blake, Principal Software Engineer
Red Hat, Inc.
Virtualization: qemu.org | libguestfs.org