1. 17 1月, 2019 1 次提交
    • F
      Btrfs: fix access to available allocation bits when starting balance · 829431a2
      Filipe Manana 提交于
      commit 5a8067c0d17feb7579db0476191417b441a8996e upstream.
      
      The available allocation bits members from struct btrfs_fs_info are
      protected by a sequence lock, and when starting balance we access them
      incorrectly in two different ways:
      
      1) In the read sequence lock loop at btrfs_balance() we use the values we
         read from fs_info->avail_*_alloc_bits and we can immediately do actions
         that have side effects and can not be undone (printing a message and
         jumping to a label). This is wrong because a retry might be needed, so
         our actions must not have side effects and must be repeatable as long
         as read_seqretry() returns a non-zero value. In other words, we were
         essentially ignoring the sequence lock;
      
      2) Right below the read sequence lock loop, we were reading the values
         from avail_metadata_alloc_bits and avail_data_alloc_bits without any
         protection from concurrent writers, that is, reading them outside of
         the read sequence lock critical section.
      
      So fix this by making sure we only read the available allocation bits
      while in a read sequence lock critical section and that what we do in the
      critical section is repeatable (has nothing that can not be undone) so
      that any eventual retry that is needed is handled properly.
      
      Fixes: de98ced9 ("Btrfs: use seqlock to protect fs_info->avail_{data, metadata, system}_alloc_bits")
      Fixes: 14506127 ("btrfs: fix a bogus warning when converting only data or metadata")
      Reviewed-by: NNikolay Borisov <nborisov@suse.com>
      Signed-off-by: NFilipe Manana <fdmanana@suse.com>
      Reviewed-by: NDavid Sterba <dsterba@suse.com>
      Signed-off-by: NDavid Sterba <dsterba@suse.com>
      Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
      829431a2
  2. 23 8月, 2018 1 次提交
    • A
      btrfs: btrfs_shrink_device should call commit transaction at the end · 801660b0
      Anand Jain 提交于
      Test case btrfs/164 reports use-after-free:
      
      [ 6712.084324] general protection fault: 0000 [#1] PREEMPT SMP
      ..
      [ 6712.195423]  btrfs_update_commit_device_size+0x75/0xf0 [btrfs]
      [ 6712.201424]  btrfs_commit_transaction+0x57d/0xa90 [btrfs]
      [ 6712.206999]  btrfs_rm_device+0x627/0x850 [btrfs]
      [ 6712.211800]  btrfs_ioctl+0x2b03/0x3120 [btrfs]
      
      Reason for this is that btrfs_shrink_device adds the resized device to
      the fs_devices::resized_devices after it has called the last commit
      transaction.
      
      So the list fs_devices::resized_devices is not empty when
      btrfs_shrink_device returns.  Now the parent function
      btrfs_rm_device calls:
      
              btrfs_close_bdev(device);
              call_rcu(&device->rcu, free_device_rcu);
      
      and then does the transactio ncommit. It goes through the
      fs_devices::resized_devices in btrfs_update_commit_device_size and
      leads to use-after-free.
      
      Fix this by making sure btrfs_shrink_device calls the last needed
      btrfs_commit_transaction before the return. This is consistent with what
      the grow counterpart does and this makes sure the on-disk state is
      persistent when the function returns.
      Reported-by: NLu Fengqi <lufq.fnst@cn.fujitsu.com>
      Tested-by: NLu Fengqi <lufq.fnst@cn.fujitsu.com>
      Signed-off-by: NAnand Jain <anand.jain@oracle.com>
      Reviewed-by: NDavid Sterba <dsterba@suse.com>
      [ update changelog ]
      Signed-off-by: NDavid Sterba <dsterba@suse.com>
      801660b0
  3. 06 8月, 2018 33 次提交
  4. 13 7月, 2018 1 次提交
  5. 30 5月, 2018 1 次提交
  6. 29 5月, 2018 3 次提交