bdev: allow allocating custom-length buffers for bdev_io

This is required for upcoming UNMAP
implementation in bdev_virtio.

While here, also added documentation for
spdk_bdev_io_get_buf().

Change-Id: Ia769ee9b8b132f31208ae66598b29a1c9ed37312
Signed-off-by: Dariusz Stojaczyk <dariuszx.stojaczyk@intel.com>
Reviewed-on: https://review.gerrithub.io/379721
Tested-by: SPDK Automated Test System <sys_sgsw@intel.com>
Reviewed-by: Jim Harris <james.r.harris@intel.com>
Reviewed-by: Daniel Verkamp <daniel.verkamp@intel.com>
This commit is contained in:
Dariusz Stojaczyk 2017-09-22 22:59:55 +02:00 committed by Jim Harris
parent 2fe6947669
commit 3595fc5f40
8 changed files with 32 additions and 14 deletions

View File

@ -251,6 +251,9 @@ struct spdk_bdev_io {
/** bdev allocated memory associated with this request */ /** bdev allocated memory associated with this request */
void *buf; void *buf;
/** requested size of the buffer associated with this I/O */
uint64_t buf_len;
/** Callback for when buf is allocated */ /** Callback for when buf is allocated */
spdk_bdev_io_get_buf_cb get_buf_cb; spdk_bdev_io_get_buf_cb get_buf_cb;
@ -367,7 +370,20 @@ void spdk_bdev_poller_start(struct spdk_bdev_poller **ppoller,
void spdk_bdev_poller_stop(struct spdk_bdev_poller **ppoller); void spdk_bdev_poller_stop(struct spdk_bdev_poller **ppoller);
void spdk_bdev_io_get_buf(struct spdk_bdev_io *bdev_io, spdk_bdev_io_get_buf_cb cb); /**
* Allocate a buffer for given bdev_io. Allocation will happen
* only if the bdev_io has no assigned SGL yet. The buffer will be
* freed automatically on \c spdk_bdev_free_io() call. This call
* will never fail - in case of lack of memory given callback \c cb
* will be deferred until enough memory is freed.
*
* \param bdev_io I/O to allocate buffer for.
* \param cb callback to be called when the buffer is allocated
* or the bdev_io has an SGL assigned already.
* \param len size of the buffer to allocate.
*/
void spdk_bdev_io_get_buf(struct spdk_bdev_io *bdev_io, spdk_bdev_io_get_buf_cb cb, uint64_t len);
struct spdk_bdev_io *spdk_bdev_get_io(void); struct spdk_bdev_io *spdk_bdev_get_io(void);
void spdk_bdev_io_complete(struct spdk_bdev_io *bdev_io, void spdk_bdev_io_complete(struct spdk_bdev_io *bdev_io,
enum spdk_bdev_io_status status); enum spdk_bdev_io_status status);

View File

@ -244,7 +244,8 @@ static int _bdev_aio_submit_request(struct spdk_io_channel *ch, struct spdk_bdev
{ {
switch (bdev_io->type) { switch (bdev_io->type) {
case SPDK_BDEV_IO_TYPE_READ: case SPDK_BDEV_IO_TYPE_READ:
spdk_bdev_io_get_buf(bdev_io, bdev_aio_get_buf_cb); spdk_bdev_io_get_buf(bdev_io, bdev_aio_get_buf_cb,
bdev_io->u.bdev.num_blocks * bdev_io->bdev->blocklen);
return 0; return 0;
case SPDK_BDEV_IO_TYPE_WRITE: case SPDK_BDEV_IO_TYPE_WRITE:

View File

@ -230,7 +230,7 @@ spdk_bdev_io_set_buf(struct spdk_bdev_io *bdev_io, void *buf)
bdev_io->buf = buf; bdev_io->buf = buf;
bdev_io->u.bdev.iovs[0].iov_base = (void *)((unsigned long)((char *)buf + 512) & ~511UL); bdev_io->u.bdev.iovs[0].iov_base = (void *)((unsigned long)((char *)buf + 512) & ~511UL);
bdev_io->u.bdev.iovs[0].iov_len = bdev_io->u.bdev.num_blocks * bdev_io->bdev->blocklen; bdev_io->u.bdev.iovs[0].iov_len = bdev_io->buf_len;
bdev_io->get_buf_cb(bdev_io->ch->channel, bdev_io); bdev_io->get_buf_cb(bdev_io->ch->channel, bdev_io);
} }
@ -241,17 +241,14 @@ spdk_bdev_io_put_buf(struct spdk_bdev_io *bdev_io)
struct spdk_bdev_io *tmp; struct spdk_bdev_io *tmp;
void *buf; void *buf;
bdev_io_tailq_t *tailq; bdev_io_tailq_t *tailq;
uint64_t length;
struct spdk_bdev_mgmt_channel *ch; struct spdk_bdev_mgmt_channel *ch;
assert(bdev_io->u.bdev.iovcnt == 1); assert(bdev_io->u.bdev.iovcnt == 1);
length = bdev_io->u.bdev.num_blocks * bdev_io->bdev->blocklen;
buf = bdev_io->buf; buf = bdev_io->buf;
ch = spdk_io_channel_get_ctx(bdev_io->ch->mgmt_channel); ch = spdk_io_channel_get_ctx(bdev_io->ch->mgmt_channel);
if (length <= SPDK_BDEV_SMALL_BUF_MAX_SIZE) { if (bdev_io->buf_len <= SPDK_BDEV_SMALL_BUF_MAX_SIZE) {
pool = g_bdev_mgr.buf_small_pool; pool = g_bdev_mgr.buf_small_pool;
tailq = &ch->need_buf_small; tailq = &ch->need_buf_small;
} else { } else {
@ -269,9 +266,8 @@ spdk_bdev_io_put_buf(struct spdk_bdev_io *bdev_io)
} }
void void
spdk_bdev_io_get_buf(struct spdk_bdev_io *bdev_io, spdk_bdev_io_get_buf_cb cb) spdk_bdev_io_get_buf(struct spdk_bdev_io *bdev_io, spdk_bdev_io_get_buf_cb cb, uint64_t len)
{ {
uint64_t len = bdev_io->u.bdev.num_blocks * bdev_io->bdev->blocklen;
struct spdk_mempool *pool; struct spdk_mempool *pool;
bdev_io_tailq_t *tailq; bdev_io_tailq_t *tailq;
void *buf = NULL; void *buf = NULL;
@ -288,6 +284,7 @@ spdk_bdev_io_get_buf(struct spdk_bdev_io *bdev_io, spdk_bdev_io_get_buf_cb cb)
ch = spdk_io_channel_get_ctx(bdev_io->ch->mgmt_channel); ch = spdk_io_channel_get_ctx(bdev_io->ch->mgmt_channel);
bdev_io->buf_len = len;
bdev_io->get_buf_cb = cb; bdev_io->get_buf_cb = cb;
if (len <= SPDK_BDEV_SMALL_BUF_MAX_SIZE) { if (len <= SPDK_BDEV_SMALL_BUF_MAX_SIZE) {
pool = g_bdev_mgr.buf_small_pool; pool = g_bdev_mgr.buf_small_pool;

View File

@ -386,7 +386,8 @@ vbdev_lvol_submit_request(struct spdk_io_channel *ch, struct spdk_bdev_io *bdev_
switch (bdev_io->type) { switch (bdev_io->type) {
case SPDK_BDEV_IO_TYPE_READ: case SPDK_BDEV_IO_TYPE_READ:
spdk_bdev_io_get_buf(bdev_io, lvol_read); spdk_bdev_io_get_buf(bdev_io, lvol_read,
bdev_io->u.bdev.num_blocks * bdev_io->bdev->blocklen);
break; break;
case SPDK_BDEV_IO_TYPE_WRITE: case SPDK_BDEV_IO_TYPE_WRITE:
lvol_write(lvol, ch, bdev_io); lvol_write(lvol, ch, bdev_io);

View File

@ -363,7 +363,8 @@ _bdev_nvme_submit_request(struct spdk_io_channel *ch, struct spdk_bdev_io *bdev_
switch (bdev_io->type) { switch (bdev_io->type) {
case SPDK_BDEV_IO_TYPE_READ: case SPDK_BDEV_IO_TYPE_READ:
spdk_bdev_io_get_buf(bdev_io, bdev_nvme_get_buf_cb); spdk_bdev_io_get_buf(bdev_io, bdev_nvme_get_buf_cb,
bdev_io->u.bdev.num_blocks * bdev_io->bdev->blocklen);
return 0; return 0;
case SPDK_BDEV_IO_TYPE_WRITE: case SPDK_BDEV_IO_TYPE_WRITE:

View File

@ -272,7 +272,8 @@ static int _bdev_rbd_submit_request(struct spdk_io_channel *ch, struct spdk_bdev
{ {
switch (bdev_io->type) { switch (bdev_io->type) {
case SPDK_BDEV_IO_TYPE_READ: case SPDK_BDEV_IO_TYPE_READ:
spdk_bdev_io_get_buf(bdev_io, bdev_rbd_get_buf_cb); spdk_bdev_io_get_buf(bdev_io, bdev_rbd_get_buf_cb,
bdev_io->u.bdev.num_blocks * bdev_io->bdev->blocklen);
return 0; return 0;
case SPDK_BDEV_IO_TYPE_WRITE: case SPDK_BDEV_IO_TYPE_WRITE:

View File

@ -155,7 +155,8 @@ static int _bdev_virtio_submit_request(struct spdk_io_channel *ch, struct spdk_b
{ {
switch (bdev_io->type) { switch (bdev_io->type) {
case SPDK_BDEV_IO_TYPE_READ: case SPDK_BDEV_IO_TYPE_READ:
spdk_bdev_io_get_buf(bdev_io, bdev_virtio_rw); spdk_bdev_io_get_buf(bdev_io, bdev_virtio_rw,
bdev_io->u.bdev.num_blocks * bdev_io->bdev->blocklen);
return 0; return 0;
case SPDK_BDEV_IO_TYPE_WRITE: case SPDK_BDEV_IO_TYPE_WRITE:
bdev_virtio_rw(ch, bdev_io); bdev_virtio_rw(ch, bdev_io);

View File

@ -198,7 +198,7 @@ struct spdk_io_channel *spdk_lvol_get_io_channel(struct spdk_lvol *lvol)
} }
void void
spdk_bdev_io_get_buf(struct spdk_bdev_io *bdev_io, spdk_bdev_io_get_buf_cb cb) spdk_bdev_io_get_buf(struct spdk_bdev_io *bdev_io, spdk_bdev_io_get_buf_cb cb, uint64_t len)
{ {
} }