• Qu Wenruo's avatar
    btrfs: repair super block num_devices automatically · d201238c
    Qu Wenruo authored
    [BUG]
    There is a report that a btrfs has a bad super block num devices.
    
    This makes btrfs to reject the fs completely.
    
      BTRFS error (device sdd3): super_num_devices 3 mismatch with num_devices 2 found here
      BTRFS error (device sdd3): failed to read chunk tree: -22
      BTRFS error (device sdd3): open_ctree failed
    
    [CAUSE]
    During btrfs device removal, chunk tree and super block num devs are
    updated in two different transactions:
    
      btrfs_rm_device()
      |- btrfs_rm_dev_item(device)
      |  |- trans = btrfs_start_transaction()
      |  |  Now we got transaction X
      |  |
      |  |- btrfs_del_item()
      |  |  Now device item is removed from chunk tree
      |  |
      |  |- btrfs_commit_transaction()
      |     Transaction X got committed, super num devs untouched,
      |     but device item removed from chunk tree.
      |     (AKA, super num devs is already incorrect)
      |
      |- cur_devices->num_devices--;
      |- cur_devices->total_devices--;
      |- btrfs_set_super_num_devices()
         All those operations are not in transaction X, thus it will
         only be written back to disk in next transaction.
    
    So after the transaction X in btrfs_rm_dev_item() committed, but before
    transaction X+1 (which can be minutes away), a power loss happen, then
    we got the super num mismatch.
    
    This has been fixed by commit bbac5869 ("btrfs: remove device item
    and update super block in the same transaction").
    
    [FIX]
    Make the super_num_devices check less strict, converting it from a hard
    error to a warning, and reset the value to a correct one for the current
    or next transaction commit.
    
    As the number of device items is the critical information where the
    super block num_devices is only a cached value (and also useful for
    cross checking), it's safe to automatically update it. Other device
    related problems like missing device are handled after that and may
    require other means to resolve, like degraded mount. With this fix,
    potentially affected filesystems won't fail mount and require the manual
    repair by btrfs check.
    Reported-by: default avatarLuca Béla Palkovics <luca.bela.palkovics@gmail.com>
    Link: https://lore.kernel.org/linux-btrfs/CA+8xDSpvdm_U0QLBAnrH=zqDq_cWCOH5TiV46CKmp3igr44okQ@mail.gmail.com/
    CC: stable@vger.kernel.org # 4.14+
    Signed-off-by: default avatarQu Wenruo <wqu@suse.com>
    Reviewed-by: default avatarDavid Sterba <dsterba@suse.com>
    Signed-off-by: default avatarDavid Sterba <dsterba@suse.com>
    d201238c
volumes.c 224 KB