With this change all ZVOL updates are initiated from the SPA sync context
instead of a mix of the sync and open contexts. The updates are queued to
be applied by a dedicated thread in the original order. This should ensure
that ZVOLs always accurately reflect the corresponding datasets. ZFS ioctl
operations wait on the mentioned thread to complete its work. Thus, the
illusion of the synchronous ZVOL update is preserved. At the same time, the
SPA sync thread never blocks on ZVOL related operations avoiding problems
like reported in https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=203864 .
This change is based on earlier work in the same direction: D7179 and
D14669. D7179 tried to perform ZVOL operations in the open context and that
opened races between them. D14669 uses a design very similar to this change
but with different implementation details.
This change also heavily borrows from similar code in ZoL, but there are many
differences. See:
- https://github.com/zfsonlinux/zfs/commit/a0bd735adb1b1eb81fef10b4db102ee051c4d4ff
- https://github.com/zfsonlinux/zfs/issues/3681
- https://github.com/zfsonlinux/zfs/issues/2217
P.S.
This change also fixes a bug with ZVOL and VFS rename in
dsl_dataset_promote_sync where 'oldname' was not properly set (since
rS272474).