• J
    fs/writeback: use rcu_barrier() to wait for inflight wb switches going into workqueue when umount · 6644f956
    Jiufei Xue 提交于
    synchronize_rcu() didn't wait for call_rcu() callbacks, so inode wb
    switch may not go to the workqueue after synchronize_rcu(). Thus
    previous scheduled switches was not finished even flushing the
    workqueue, which will cause a NULL pointer dereferenced followed below.
    
    VFS: Busy inodes after unmount of vdd. Self-destruct in 5 seconds.  Have a nice day...
    BUG: unable to handle kernel NULL pointer dereference at 0000000000000278
    [<ffffffff8126a303>] evict+0xb3/0x180
    [<ffffffff8126a760>] iput+0x1b0/0x230
    [<ffffffff8127c690>] inode_switch_wbs_work_fn+0x3c0/0x6a0
    [<ffffffff810a5b2e>] worker_thread+0x4e/0x490
    [<ffffffff810a5ae0>] ? process_one_work+0x410/0x410
    [<ffffffff810ac056>] kthread+0xe6/0x100
    [<ffffffff8173c199>] ret_from_fork+0x39/0x50
    
    Replace the synchronize_rcu() call with a rcu_barrier() to wait for all
    pending callbacks to finish. And inc isw_nr_in_flight after call_rcu()
    in inode_switch_wbs() to make more sense.
    Suggested-by: NTejun Heo <tj@kernel.org>
    Signed-off-by: NJiufei Xue <jiufei.xue@linux.alibaba.com>
    Acked-by: NTejun Heo <tj@kernel.org>
    Reviewed-by: NJoseph Qi <joseph.qi@linux.alibaba.com>
    6644f956
fs-writeback.c 71.9 KB