Commit f9e36107 authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull btrfs fixes from David Sterba:

 - regression fix for leak of transaction handle after verity rollback
   failure

 - properly reset device last error between mounts

 - improve one error handling case when checksumming bios

 - fixup confusing displayed size of space info free space

* tag 'for-5.15-rc2-tag' of git://git.kernel.org/pub/scm/linux/kernel/git/kdave/linux:
  btrfs: prevent __btrfs_dump_space_info() to underflow its free space
  btrfs: fix mount failure due to past and transient device flush error
  btrfs: fix transaction handle leak after verity rollback failure
  btrfs: replace BUG_ON() in btrfs_csum_one_bio() with proper error handling
parents 831c9bd3 0619b790
Loading
Loading
Loading
Loading
+12 −1
Original line number Diff line number Diff line
@@ -665,7 +665,18 @@ blk_status_t btrfs_csum_one_bio(struct btrfs_inode *inode, struct bio *bio,

		if (!ordered) {
			ordered = btrfs_lookup_ordered_extent(inode, offset);
			BUG_ON(!ordered); /* Logic error */
			/*
			 * The bio range is not covered by any ordered extent,
			 * must be a code logic error.
			 */
			if (unlikely(!ordered)) {
				WARN(1, KERN_WARNING
			"no ordered extent for root %llu ino %llu offset %llu\n",
				     inode->root->root_key.objectid,
				     btrfs_ino(inode), offset);
				kvfree(sums);
				return BLK_STS_IOERR;
			}
		}

		nr_sectors = BTRFS_BYTES_TO_BLKS(fs_info,
+3 −2
Original line number Diff line number Diff line
@@ -414,9 +414,10 @@ static void __btrfs_dump_space_info(struct btrfs_fs_info *fs_info,
{
	lockdep_assert_held(&info->lock);

	btrfs_info(fs_info, "space_info %llu has %llu free, is %sfull",
	/* The free space could be negative in case of overcommit */
	btrfs_info(fs_info, "space_info %llu has %lld free, is %sfull",
		   info->flags,
		   info->total_bytes - btrfs_space_info_used(info, true),
		   (s64)(info->total_bytes - btrfs_space_info_used(info, true)),
		   info->full ? "" : "not ");
	btrfs_info(fs_info,
		"space_info total=%llu, used=%llu, pinned=%llu, reserved=%llu, may_use=%llu, readonly=%llu zone_unusable=%llu",
+4 −2
Original line number Diff line number Diff line
@@ -451,7 +451,7 @@ static int del_orphan(struct btrfs_trans_handle *trans, struct btrfs_inode *inod
 */
static int rollback_verity(struct btrfs_inode *inode)
{
	struct btrfs_trans_handle *trans;
	struct btrfs_trans_handle *trans = NULL;
	struct btrfs_root *root = inode->root;
	int ret;

@@ -473,6 +473,7 @@ static int rollback_verity(struct btrfs_inode *inode)
	trans = btrfs_start_transaction(root, 2);
	if (IS_ERR(trans)) {
		ret = PTR_ERR(trans);
		trans = NULL;
		btrfs_handle_fs_error(root->fs_info, ret,
			"failed to start transaction in verity rollback %llu",
			(u64)inode->vfs_inode.i_ino);
@@ -490,8 +491,9 @@ static int rollback_verity(struct btrfs_inode *inode)
		btrfs_abort_transaction(trans, ret);
		goto out;
	}
	btrfs_end_transaction(trans);
out:
	if (trans)
		btrfs_end_transaction(trans);
	return ret;
}

+13 −0
Original line number Diff line number Diff line
@@ -1137,6 +1137,19 @@ static void btrfs_close_one_device(struct btrfs_device *device)
	atomic_set(&device->dev_stats_ccnt, 0);
	extent_io_tree_release(&device->alloc_state);

	/*
	 * Reset the flush error record. We might have a transient flush error
	 * in this mount, and if so we aborted the current transaction and set
	 * the fs to an error state, guaranteeing no super blocks can be further
	 * committed. However that error might be transient and if we unmount the
	 * filesystem and mount it again, we should allow the mount to succeed
	 * (btrfs_check_rw_degradable() should not fail) - if after mounting the
	 * filesystem again we still get flush errors, then we will again abort
	 * any transaction and set the error state, guaranteeing no commits of
	 * unsafe super blocks.
	 */
	device->last_flush_error = 0;

	/* Verify the device is back in a pristine state  */
	ASSERT(!test_bit(BTRFS_DEV_STATE_FLUSH_SENT, &device->dev_state));
	ASSERT(!test_bit(BTRFS_DEV_STATE_REPLACE_TGT, &device->dev_state));