• Michal Hocko's avatar
    btrfs: Prevent from early transaction abort · d1b5c567
    Michal Hocko authored
    Btrfs relies on GFP_NOFS allocation when committing the transaction but
    this allocation context is rather weak wrt. reclaim capabilities. The
    page allocator currently tries hard to not fail these allocations if
    they are small (<=PAGE_ALLOC_COSTLY_ORDER) so this is not a problem
    currently but there is an attempt to move away from the default no-fail
    behavior and allow these allocation to fail more eagerly. And this would
    lead to a pre-mature transaction abort as follows:
    
    [   55.328093] Call Trace:
    [   55.328890]  [<ffffffff8154e6f0>] dump_stack+0x4f/0x7b
    [   55.330518]  [<ffffffff8108fa28>] ? console_unlock+0x334/0x363
    [   55.332738]  [<ffffffff8110873e>] __alloc_pages_nodemask+0x81d/0x8d4
    [   55.334910]  [<ffffffff81100752>] pagecache_get_page+0x10e/0x20c
    [   55.336844]  [<ffffffffa007d916>] alloc_extent_buffer+0xd0/0x350 [btrfs]
    [   55.338973]  [<ffffffffa0059d8c>] btrfs_find_create_tree_block+0x15/0x17 [btrfs]
    [   55.341329]  [<ffffffffa004f728>] btrfs_alloc_tree_block+0x18c/0x405 [btrfs]
    [   55.343566]  [<ffffffffa003fa34>] split_leaf+0x1e4/0x6a6 [btrfs]
    [   55.345577]  [<ffffffffa0040567>] btrfs_search_slot+0x671/0x831 [btrfs]
    [   55.347679]  [<ffffffff810682d7>] ? get_parent_ip+0xe/0x3e
    [   55.349434]  [<ffffffffa0041cb2>] btrfs_insert_empty_items+0x5d/0xa8 [btrfs]
    [   55.351681]  [<ffffffffa004ecfb>] __btrfs_run_delayed_refs+0x7a6/0xf35 [btrfs]
    [   55.353979]  [<ffffffffa00512ea>] btrfs_run_delayed_refs+0x6e/0x226 [btrfs]
    [   55.356212]  [<ffffffffa0060e21>] ? start_transaction+0x192/0x534 [btrfs]
    [   55.358378]  [<ffffffffa0060e21>] ? start_transaction+0x192/0x534 [btrfs]
    [   55.360626]  [<ffffffffa0060221>] btrfs_commit_transaction+0x4c/0xaba [btrfs]
    [   55.362894]  [<ffffffffa0060e21>] ? start_transaction+0x192/0x534 [btrfs]
    [   55.365221]  [<ffffffffa0073428>] btrfs_sync_file+0x29c/0x310 [btrfs]
    [   55.367273]  [<ffffffff81186808>] vfs_fsync_range+0x8f/0x9e
    [   55.369047]  [<ffffffff81186833>] vfs_fsync+0x1c/0x1e
    [   55.370654]  [<ffffffff81186869>] do_fsync+0x34/0x4e
    [   55.372246]  [<ffffffff81186ab3>] SyS_fsync+0x10/0x14
    [   55.373851]  [<ffffffff81554f97>] system_call_fastpath+0x12/0x6f
    [   55.381070] BTRFS: error (device hdb1) in btrfs_run_delayed_refs:2821: errno=-12 Out of memory
    [   55.382431] BTRFS warning (device hdb1): Skipping commit of aborted transaction.
    [   55.382433] BTRFS warning (device hdb1): cleanup_transaction:1692: Aborting unused transaction(IO failure).
    [   55.384280] ------------[ cut here ]------------
    [   55.384312] WARNING: CPU: 0 PID: 3010 at fs/btrfs/delayed-ref.c:438 btrfs_select_ref_head+0xd9/0xfe [btrfs]()
    [...]
    [   55.384337] Call Trace:
    [   55.384353]  [<ffffffff8154e6f0>] dump_stack+0x4f/0x7b
    [   55.384357]  [<ffffffff8107f717>] ? down_trylock+0x2d/0x37
    [   55.384359]  [<ffffffff81046977>] warn_slowpath_common+0xa1/0xbb
    [   55.384398]  [<ffffffffa00a1d6b>] ? btrfs_select_ref_head+0xd9/0xfe [btrfs]
    [   55.384400]  [<ffffffff81046a34>] warn_slowpath_null+0x1a/0x1c
    [   55.384423]  [<ffffffffa00a1d6b>] btrfs_select_ref_head+0xd9/0xfe [btrfs]
    [   55.384446]  [<ffffffffa004e5f7>] ? __btrfs_run_delayed_refs+0xa2/0xf35 [btrfs]
    [   55.384455]  [<ffffffffa004e600>] __btrfs_run_delayed_refs+0xab/0xf35 [btrfs]
    [   55.384476]  [<ffffffffa00512ea>] btrfs_run_delayed_refs+0x6e/0x226 [btrfs]
    [   55.384499]  [<ffffffffa0060e21>] ? start_transaction+0x192/0x534 [btrfs]
    [   55.384521]  [<ffffffffa0060e21>] ? start_transaction+0x192/0x534 [btrfs]
    [   55.384543]  [<ffffffffa0060221>] btrfs_commit_transaction+0x4c/0xaba [btrfs]
    [   55.384565]  [<ffffffffa0060e21>] ? start_transaction+0x192/0x534 [btrfs]
    [   55.384588]  [<ffffffffa0073428>] btrfs_sync_file+0x29c/0x310 [btrfs]
    [   55.384591]  [<ffffffff81186808>] vfs_fsync_range+0x8f/0x9e
    [   55.384592]  [<ffffffff81186833>] vfs_fsync+0x1c/0x1e
    [   55.384593]  [<ffffffff81186869>] do_fsync+0x34/0x4e
    [   55.384594]  [<ffffffff81186ab3>] SyS_fsync+0x10/0x14
    [   55.384595]  [<ffffffff81554f97>] system_call_fastpath+0x12/0x6f
    [...]
    [   55.384608] ---[ end trace c29799da1d4dd621 ]---
    [   55.437323] BTRFS info (device hdb1): forced readonly
    [   55.438815] BTRFS info (device hdb1): delayed_refs has NO entry
    
    Fix this by being explicit about the no-fail behavior of this allocation
    path and use __GFP_NOFAIL.
    Signed-off-by: default avatarMichal Hocko <mhocko@suse.com>
    Signed-off-by: default avatarChris Mason <clm@fb.com>
    d1b5c567
extent_io.c 142 KB