Commit 6b7609b6 authored by Seth Howell's avatar Seth Howell Committed by Jim Harris
Browse files

bdev.c: encapsulate members of spdk_bdev_part.



Change-Id: Ia3d04905d319c075a12726ca85c3aa1d3135db44
Signed-off-by: default avatarSeth Howell <seth.howell@intel.com>
Reviewed-on: https://review.gerrithub.io/417176


Tested-by: default avatarSPDK Automated Test System <sys_sgsw@intel.com>
Reviewed-by: default avatarJim Harris <james.r.harris@intel.com>
Reviewed-by: default avatarBen Walker <benjamin.walker@intel.com>
Reviewed-by: default avatarShuhei Matsumoto <shuhei.matsumoto.xt@hitachi.com>
parent 575a4025
Loading
Loading
Loading
Loading
+5 −0
Original line number Diff line number Diff line
@@ -35,6 +35,11 @@ on each call. This allows multiple callers to query I/O statistics without confl
with each other. Existing users will need to adjust their code to record the previous
I/O statistics to calculate the delta between calls.

A new public header file bdev_module.h has been introduced to facilitate the development
of new bdev modules. This header includes an interface for the spdk_bdev_part and
spdk_bdev_part_base objects to enable the creation of multiple virtual bdevs on top of a
single base bdev.

### Env

The spdk_mem_map_translate() function now takes a size parameter to indicate the size of
+58 −3
Original line number Diff line number Diff line
@@ -736,10 +736,24 @@ uint32_t spdk_bdev_part_base_get_ref(struct spdk_bdev_part_base *part_base);
typedef void (*spdk_bdev_part_base_free_fn)(void *ctx);

struct spdk_bdev_part {
	/* Entry into the module's global list of bdev parts */
	TAILQ_ENTRY(spdk_bdev_part)	tailq;

	/**
	 * Fields that are used internally by part.c These fields should only
	 * be accessed from a module using any pertinent get and set methods.
	 */
	struct bdev_part_internal_fields {

		/* This part's corresponding bdev object. Not to be confused with the base bdev */
		struct spdk_bdev		bdev;

		/* The base to which this part belongs */
		struct spdk_bdev_part_base	*base;

		/* number of blocks from the start of the base bdev to the start of this part */
		uint64_t			offset_blocks;
	TAILQ_ENTRY(spdk_bdev_part)	tailq;
	} internal;
};

struct spdk_bdev_part_channel {
@@ -830,6 +844,47 @@ int spdk_bdev_part_construct(struct spdk_bdev_part *part, struct spdk_bdev_part_
 */
void spdk_bdev_part_submit_request(struct spdk_bdev_part_channel *ch, struct spdk_bdev_io *bdev_io);

/**
 * Return a pointer to this part's spdk_bdev.
 *
 * \param part An spdk_bdev_part object.
 *
 * \return A pointer to this part's spdk_bdev object.
 */
struct spdk_bdev *spdk_bdev_part_get_bdev(struct spdk_bdev_part *part);

/**
 * Return a pointer to this part's base.
 *
 * \param part An spdk_bdev_part object.
 *
 * \return A pointer to this part's spdk_bdev_part_base object.
 */
struct spdk_bdev_part_base *spdk_bdev_part_get_base(struct spdk_bdev_part *part);

/**
 * Return a pointer to this part's base bdev.
 *
 * The return value of this function is equivalent to calling
 * spdk_bdev_part_base_get_bdev on this part's base.
 *
 * \param part An spdk_bdev_part object.
 *
 * \return A pointer to the bdev belonging to this part's base.
 */
struct spdk_bdev *spdk_bdev_part_get_base_bdev(struct spdk_bdev_part *part);

/**
 * Return this part's offset from the beginning of the base bdev.
 *
 * This function should not be called in the I/O path. Any block
 * translations to I/O will be handled in spdk_bdev_part_submit_request.
 *
 * \param part An spdk_bdev_part object.
 *
 * \return the block offset of this part from it's underlying bdev.
 */
uint64_t spdk_bdev_part_get_offset_blocks(struct spdk_bdev_part *part);

/*
 * Macro used to register module for later initialization.
+3 −3
Original line number Diff line number Diff line
@@ -113,7 +113,7 @@ spdk_vbdev_inject_error(char *name, uint32_t io_type, uint32_t error_type, uint3
	}

	TAILQ_FOREACH(part, &g_error_disks, tailq) {
		if (bdev == &part->bdev) {
		if (bdev == spdk_bdev_part_get_bdev(part)) {
			error_disk = (struct error_disk *)part;
			break;
		}
@@ -206,7 +206,7 @@ static int
vbdev_error_destruct(void *ctx)
{
	struct error_disk *error_disk = ctx;
	struct spdk_bdev *base_bdev = spdk_bdev_part_base_get_bdev(error_disk->part.base);
	struct spdk_bdev *base_bdev = spdk_bdev_part_get_base_bdev(&error_disk->part);
	int rc;

	rc = vbdev_error_config_remove(base_bdev->name);
@@ -221,7 +221,7 @@ static int
vbdev_error_dump_info_json(void *ctx, struct spdk_json_write_ctx *w)
{
	struct error_disk *error_disk = ctx;
	struct spdk_bdev *base_bdev = spdk_bdev_part_base_get_bdev(error_disk->part.base);
	struct spdk_bdev *base_bdev = spdk_bdev_part_get_base_bdev(&error_disk->part);

	spdk_json_write_name(w, "error_disk");
	spdk_json_write_object_begin(w);
+5 −3
Original line number Diff line number Diff line
@@ -193,10 +193,12 @@ static int
vbdev_gpt_dump_info_json(void *ctx, struct spdk_json_write_ctx *w)
{
	struct gpt_disk *gpt_disk = SPDK_CONTAINEROF(ctx, struct gpt_disk, part);
	struct gpt_base *gpt_base = spdk_bdev_part_base_get_ctx(gpt_disk->part.base);
	struct spdk_bdev *part_base_bdev = spdk_bdev_part_base_get_bdev(gpt_disk->part.base);
	struct spdk_bdev_part_base *base_bdev = spdk_bdev_part_get_base(&gpt_disk->part);
	struct gpt_base *gpt_base = spdk_bdev_part_base_get_ctx(base_bdev);
	struct spdk_bdev *part_base_bdev = spdk_bdev_part_base_get_bdev(base_bdev);
	struct spdk_gpt *gpt = &gpt_base->gpt;
	struct spdk_gpt_partition_entry *gpt_entry = &gpt->partitions[gpt_disk->partition_index];
	uint64_t offset_blocks = spdk_bdev_part_get_offset_blocks(&gpt_disk->part);

	spdk_json_write_name(w, "gpt");
	spdk_json_write_object_begin(w);
@@ -205,7 +207,7 @@ vbdev_gpt_dump_info_json(void *ctx, struct spdk_json_write_ctx *w)
	spdk_json_write_string(w, spdk_bdev_get_name(part_base_bdev));

	spdk_json_write_name(w, "offset_blocks");
	spdk_json_write_uint64(w, gpt_disk->part.offset_blocks);
	spdk_json_write_uint64(w, offset_blocks);

	spdk_json_write_name(w, "partition_type_guid");
	write_guid(w, &gpt_entry->part_type_guid);
+56 −32
Original line number Diff line number Diff line
@@ -107,9 +107,9 @@ spdk_bdev_part_free_cb(void *io_device)
	struct spdk_bdev_part_base *base;

	assert(part);
	assert(part->base);
	assert(part->internal.base);

	base = part->base;
	base = part->internal.base;

	TAILQ_REMOVE(base->tailq, part, tailq);

@@ -118,8 +118,8 @@ spdk_bdev_part_free_cb(void *io_device)
		spdk_bdev_part_base_free(base);
	}

	spdk_bdev_destruct_done(&part->bdev, 0);
	free(part->bdev.name);
	spdk_bdev_destruct_done(&part->internal.bdev, 0);
	free(part->internal.bdev.name);
	free(part);
}

@@ -139,8 +139,8 @@ spdk_bdev_part_base_hotremove(struct spdk_bdev *base_bdev, struct bdev_part_tail
	struct spdk_bdev_part *part, *tmp;

	TAILQ_FOREACH_SAFE(part, tailq, tailq, tmp) {
		if (part->base->bdev == base_bdev) {
			spdk_bdev_unregister(&part->bdev, NULL, NULL);
		if (part->internal.base->bdev == base_bdev) {
			spdk_bdev_unregister(&part->internal.bdev, NULL, NULL);
		}
	}
}
@@ -150,7 +150,7 @@ spdk_bdev_part_io_type_supported(void *_part, enum spdk_bdev_io_type io_type)
{
	struct spdk_bdev_part *part = _part;

	return part->base->bdev->fn_table->io_type_supported(part->base->bdev, io_type);
	return part->internal.base->bdev->fn_table->io_type_supported(part->internal.base->bdev, io_type);
}

static struct spdk_io_channel *
@@ -161,6 +161,30 @@ spdk_bdev_part_get_io_channel(void *_part)
	return spdk_get_io_channel(part);
}

struct spdk_bdev *
spdk_bdev_part_get_bdev(struct spdk_bdev_part *part)
{
	return &part->internal.bdev;
}

struct spdk_bdev_part_base *
spdk_bdev_part_get_base(struct spdk_bdev_part *part)
{
	return part->internal.base;
}

struct spdk_bdev *
spdk_bdev_part_get_base_bdev(struct spdk_bdev_part *part)
{
	return part->internal.base->bdev;
}

uint64_t
spdk_bdev_part_get_offset_blocks(struct spdk_bdev_part *part)
{
	return part->internal.offset_blocks;
}

static void
spdk_bdev_part_complete_io(struct spdk_bdev_io *bdev_io, bool success, void *cb_arg)
{
@@ -176,38 +200,38 @@ spdk_bdev_part_submit_request(struct spdk_bdev_part_channel *ch, struct spdk_bde
{
	struct spdk_bdev_part *part = ch->part;
	struct spdk_io_channel *base_ch = ch->base_ch;
	struct spdk_bdev_desc *base_desc = part->base->desc;
	struct spdk_bdev_desc *base_desc = part->internal.base->desc;
	uint64_t offset;
	int rc = 0;

	/* Modify the I/O to adjust for the offset within the base bdev. */
	switch (bdev_io->type) {
	case SPDK_BDEV_IO_TYPE_READ:
		offset = bdev_io->u.bdev.offset_blocks + part->offset_blocks;
		offset = bdev_io->u.bdev.offset_blocks + part->internal.offset_blocks;
		rc = spdk_bdev_readv_blocks(base_desc, base_ch, bdev_io->u.bdev.iovs,
					    bdev_io->u.bdev.iovcnt, offset,
					    bdev_io->u.bdev.num_blocks, spdk_bdev_part_complete_io,
					    bdev_io);
		break;
	case SPDK_BDEV_IO_TYPE_WRITE:
		offset = bdev_io->u.bdev.offset_blocks + part->offset_blocks;
		offset = bdev_io->u.bdev.offset_blocks + part->internal.offset_blocks;
		rc = spdk_bdev_writev_blocks(base_desc, base_ch, bdev_io->u.bdev.iovs,
					     bdev_io->u.bdev.iovcnt, offset,
					     bdev_io->u.bdev.num_blocks, spdk_bdev_part_complete_io,
					     bdev_io);
		break;
	case SPDK_BDEV_IO_TYPE_WRITE_ZEROES:
		offset = bdev_io->u.bdev.offset_blocks + part->offset_blocks;
		offset = bdev_io->u.bdev.offset_blocks + part->internal.offset_blocks;
		rc = spdk_bdev_write_zeroes_blocks(base_desc, base_ch, offset, bdev_io->u.bdev.num_blocks,
						   spdk_bdev_part_complete_io, bdev_io);
		break;
	case SPDK_BDEV_IO_TYPE_UNMAP:
		offset = bdev_io->u.bdev.offset_blocks + part->offset_blocks;
		offset = bdev_io->u.bdev.offset_blocks + part->internal.offset_blocks;
		rc = spdk_bdev_unmap_blocks(base_desc, base_ch, offset, bdev_io->u.bdev.num_blocks,
					    spdk_bdev_part_complete_io, bdev_io);
		break;
	case SPDK_BDEV_IO_TYPE_FLUSH:
		offset = bdev_io->u.bdev.offset_blocks + part->offset_blocks;
		offset = bdev_io->u.bdev.offset_blocks + part->internal.offset_blocks;
		rc = spdk_bdev_flush_blocks(base_desc, base_ch, offset, bdev_io->u.bdev.num_blocks,
					    spdk_bdev_part_complete_io, bdev_io);
		break;
@@ -232,13 +256,13 @@ spdk_bdev_part_channel_create_cb(void *io_device, void *ctx_buf)
	struct spdk_bdev_part_channel *ch = ctx_buf;

	ch->part = part;
	ch->base_ch = spdk_bdev_get_io_channel(part->base->desc);
	ch->base_ch = spdk_bdev_get_io_channel(part->internal.base->desc);
	if (ch->base_ch == NULL) {
		return -1;
	}

	if (part->base->ch_create_cb) {
		return part->base->ch_create_cb(io_device, ctx_buf);
	if (part->internal.base->ch_create_cb) {
		return part->internal.base->ch_create_cb(io_device, ctx_buf);
	} else {
		return 0;
	}
@@ -250,8 +274,8 @@ spdk_bdev_part_channel_destroy_cb(void *io_device, void *ctx_buf)
	struct spdk_bdev_part *part = (struct spdk_bdev_part *)io_device;
	struct spdk_bdev_part_channel *ch = ctx_buf;

	if (part->base->ch_destroy_cb) {
		part->base->ch_destroy_cb(io_device, ctx_buf);
	if (part->internal.base->ch_destroy_cb) {
		part->internal.base->ch_destroy_cb(io_device, ctx_buf);
	}
	spdk_put_io_channel(ch->base_ch);
}
@@ -303,20 +327,20 @@ spdk_bdev_part_construct(struct spdk_bdev_part *part, struct spdk_bdev_part_base
			 char *name, uint64_t offset_blocks, uint64_t num_blocks,
			 char *product_name)
{
	part->bdev.name = name;
	part->bdev.blocklen = base->bdev->blocklen;
	part->bdev.blockcnt = num_blocks;
	part->offset_blocks = offset_blocks;

	part->bdev.write_cache = base->bdev->write_cache;
	part->bdev.need_aligned_buffer = base->bdev->need_aligned_buffer;
	part->bdev.product_name = product_name;
	part->bdev.ctxt = part;
	part->bdev.module = base->module;
	part->bdev.fn_table = base->fn_table;
	part->internal.bdev.name = name;
	part->internal.bdev.blocklen = base->bdev->blocklen;
	part->internal.bdev.blockcnt = num_blocks;
	part->internal.offset_blocks = offset_blocks;

	part->internal.bdev.write_cache = base->bdev->write_cache;
	part->internal.bdev.need_aligned_buffer = base->bdev->need_aligned_buffer;
	part->internal.bdev.product_name = product_name;
	part->internal.bdev.ctxt = part;
	part->internal.bdev.module = base->module;
	part->internal.bdev.fn_table = base->fn_table;

	__sync_fetch_and_add(&base->ref, 1);
	part->base = base;
	part->internal.base = base;

	if (!base->claimed) {
		int rc;
@@ -324,7 +348,7 @@ spdk_bdev_part_construct(struct spdk_bdev_part *part, struct spdk_bdev_part_base
		rc = spdk_bdev_module_claim_bdev(base->bdev, base->desc, base->module);
		if (rc) {
			SPDK_ERRLOG("could not claim bdev %s\n", spdk_bdev_get_name(base->bdev));
			free(part->bdev.name);
			free(part->internal.bdev.name);
			return -1;
		}
		base->claimed = true;
@@ -333,7 +357,7 @@ spdk_bdev_part_construct(struct spdk_bdev_part *part, struct spdk_bdev_part_base
	spdk_io_device_register(part, spdk_bdev_part_channel_create_cb,
				spdk_bdev_part_channel_destroy_cb,
				base->channel_size);
	spdk_vbdev_register(&part->bdev, &base->bdev, 1);
	spdk_vbdev_register(&part->internal.bdev, &base->bdev, 1);
	TAILQ_INSERT_TAIL(base->tailq, part, tailq);

	return 0;
Loading