• Brian Foster's avatar
    xfs: replace global xfslogd wq with per-mount wq · 78c931b8
    Brian Foster authored
    The xfslogd workqueue is a global, single-job workqueue for buffer ioend
    processing. This means we allow for a single work item at a time for all
    possible XFS mounts on a system. fsstress testing in loopback XFS over
    XFS configurations has reproduced xfslogd deadlocks due to the single
    threaded nature of the queue and dependencies introduced between the
    separate XFS instances by online discard (-o discard).
    
    Discard over a loopback device converts the discard request to a hole
    punch (fallocate) on the underlying file. Online discard requests are
    issued synchronously and from xfslogd context in XFS, hence the xfslogd
    workqueue is blocked in the upper fs waiting on a hole punch request to
    be servied in the lower fs. If the lower fs issues I/O that depends on
    xfslogd to complete, both filesystems end up hung indefinitely. This is
    reproduced reliabily by generic/013 on XFS->loop->XFS test devices with
    the '-o discard' mount option.
    
    Further, docker implementations appear to use this kind of configuration
    for container instance filesystems by default (container fs->dm->
    loop->base fs) and therefore are subject to this deadlock when running
    on XFS.
    
    Replace the global xfslogd workqueue with a per-mount variant. This
    guarantees each mount access to a single worker and prevents deadlocks
    due to inter-fs dependencies introduced by discard. Since the queue is
    only responsible for buffer iodone processing at this point in time,
    rename xfslogd to xfs-buf.
    Signed-off-by: default avatarBrian Foster <bfoster@redhat.com>
    Reviewed-by: default avatarDave Chinner <dchinner@redhat.com>
    Signed-off-by: default avatarDave Chinner <david@fromorbit.com>
    78c931b8
xfs_super.c 48.4 KB