Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit abbb3b8e authored by David Sterba's avatar David Sterba
Browse files

btrfs: split write_dev_supers to two functions



There are two independent parts, one that writes the superblocks and
another that waits for completion. No functional changes, but cleanups,
reformatting and comment updates.

Signed-off-by: default avatarDavid Sterba <dsterba@suse.com>
parent 35c70103
Loading
Loading
Loading
Loading
+73 −56
Original line number Diff line number Diff line
@@ -3373,19 +3373,17 @@ struct buffer_head *btrfs_read_dev_super(struct block_device *bdev)
}

/*
 * this should be called twice, once with wait == 0 and
 * once with wait == 1.  When wait == 0 is done, all the buffer heads
 * we write are pinned.
 * Write superblock @sb to the @device. Do not wait for completion, all the
 * buffer heads we write are pinned.
 *
 * They are released when wait == 1 is done.
 * max_mirrors must be the same for both runs, and it indicates how
 * many supers on this one device should be written.
 * Write @max_mirrors copies of the superblock, where 0 means default that fit
 * the expected device size at commit time. Note that max_mirrors must be
 * same for write and wait phases.
 *
 * max_mirrors == 0 means to write them all.
 * Return number of errors when buffer head is not found or submission fails.
 */
static int write_dev_supers(struct btrfs_device *device,
			    struct btrfs_super_block *sb,
			    int wait, int max_mirrors)
			    struct btrfs_super_block *sb, int max_mirrors)
{
	struct buffer_head *bh;
	int i;
@@ -3403,37 +3401,14 @@ static int write_dev_supers(struct btrfs_device *device,
		    device->commit_total_bytes)
			break;

		if (wait) {
			bh = __find_get_block(device->bdev, bytenr / 4096,
					      BTRFS_SUPER_INFO_SIZE);
			if (!bh) {
				errors++;
				continue;
			}
			wait_on_buffer(bh);
			if (!buffer_uptodate(bh))
				errors++;

			/* drop our reference */
			brelse(bh);

			/* drop the reference from the wait == 0 run */
			brelse(bh);
			continue;
		} else {
		btrfs_set_super_bytenr(sb, bytenr);

		crc = ~(u32)0;
			crc = btrfs_csum_data((const char *)sb +
					      BTRFS_CSUM_SIZE, crc,
					      BTRFS_SUPER_INFO_SIZE -
					      BTRFS_CSUM_SIZE);
		crc = btrfs_csum_data((const char *)sb + BTRFS_CSUM_SIZE, crc,
				      BTRFS_SUPER_INFO_SIZE - BTRFS_CSUM_SIZE);
		btrfs_csum_final(crc, sb->csum);

			/*
			 * one reference for us, and we leave it for the
			 * caller
			 */
		/* One reference for us, and we leave it for the caller */
		bh = __getblk(device->bdev, bytenr / 4096,
			      BTRFS_SUPER_INFO_SIZE);
		if (!bh) {
@@ -3453,7 +3428,6 @@ static int write_dev_supers(struct btrfs_device *device,
		lock_buffer(bh);
		bh->b_end_io = btrfs_end_buffer_write_sync;
		bh->b_private = device;
		}

		/*
		 * we fua the first super.  The others we allow
@@ -3471,6 +3445,49 @@ static int write_dev_supers(struct btrfs_device *device,
	return errors < i ? 0 : -1;
}

/*
 * Wait for write completion of superblocks done by write_dev_supers,
 * @max_mirrors same for write and wait phases.
 *
 * Return number of errors when buffer head is not found or not marked up to
 * date.
 */
static int wait_dev_supers(struct btrfs_device *device, int max_mirrors)
{
	struct buffer_head *bh;
	int i;
	int errors = 0;
	u64 bytenr;

	if (max_mirrors == 0)
		max_mirrors = BTRFS_SUPER_MIRROR_MAX;

	for (i = 0; i < max_mirrors; i++) {
		bytenr = btrfs_sb_offset(i);
		if (bytenr + BTRFS_SUPER_INFO_SIZE >=
		    device->commit_total_bytes)
			break;

		bh = __find_get_block(device->bdev, bytenr / 4096,
				      BTRFS_SUPER_INFO_SIZE);
		if (!bh) {
			errors++;
			continue;
		}
		wait_on_buffer(bh);
		if (!buffer_uptodate(bh))
			errors++;

		/* drop our reference */
		brelse(bh);

		/* drop the reference from the writing run */
		brelse(bh);
	}

	return errors < i ? 0 : -1;
}

/*
 * endio for the write_dev_flush, this will wake anyone waiting
 * for the barrier when it is done
@@ -3668,7 +3685,7 @@ int write_all_supers(struct btrfs_fs_info *fs_info, int max_mirrors)
		flags = btrfs_super_flags(sb);
		btrfs_set_super_flags(sb, flags | BTRFS_HEADER_FLAG_WRITTEN);

		ret = write_dev_supers(dev, sb, 0, max_mirrors);
		ret = write_dev_supers(dev, sb, max_mirrors);
		if (ret)
			total_errors++;
	}
@@ -3691,7 +3708,7 @@ int write_all_supers(struct btrfs_fs_info *fs_info, int max_mirrors)
		if (!dev->in_fs_metadata || !dev->writeable)
			continue;

		ret = write_dev_supers(dev, sb, 1, max_mirrors);
		ret = wait_dev_supers(dev, max_mirrors);
		if (ret)
			total_errors++;
	}