diff options
author | aliguori <aliguori@c046a42c-6fe2-441c-8c8c-71466251a162> | 2009-04-22 20:20:00 +0000 |
---|---|---|
committer | aliguori <aliguori@c046a42c-6fe2-441c-8c8c-71466251a162> | 2009-04-22 20:20:00 +0000 |
commit | e268ca52328eb0460ae0d10b7f4313a63d5b000c (patch) | |
tree | 27a36b418653496829c54f59b31e9a2ad347b2e8 | |
parent | 94909d9fd931367a3d5fabfb7bf5439eb05568e9 (diff) |
implement qemu_blockalign (Stefano Stabellini)
this patch adds a buffer_alignment field to BlockDriverState and
implements a qemu_blockalign function that uses that field to allocate a
memory aligned buffer to be used by the block driver.
buffer_alignment is initialized to 512 but each block driver can set
a different value (at the moment none of them do).
This patch modifies ide.c, block-qcow.c, block-qcow2.c and block.c to
use qemu_blockalign instead of qemu_memalign.
There is only one place left that still uses qemu_memalign to allocate
buffers used by block drivers that is posix-aio-compat:handle_aiocb_rw
because it is not possible to get the BlockDriverState from that
function. However I think it is not important because posix-aio-compat
already deals with driver specific code so it is supposed to know its
own needs.
Signed-off-by: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
Signed-off-by: Anthony Liguori <aliguori@us.ibm.com>
git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@7229 c046a42c-6fe2-441c-8c8c-71466251a162
-rw-r--r-- | block-qcow.c | 4 | ||||
-rw-r--r-- | block-qcow2.c | 2 | ||||
-rw-r--r-- | block-raw-posix.c | 2 | ||||
-rw-r--r-- | block.c | 9 | ||||
-rw-r--r-- | block_int.h | 5 | ||||
-rw-r--r-- | hw/ide.c | 2 |
6 files changed, 18 insertions, 6 deletions
diff --git a/block-qcow.c b/block-qcow.c index b66ade35a7..fc6b809715 100644 --- a/block-qcow.c +++ b/block-qcow.c @@ -641,7 +641,7 @@ static BlockDriverAIOCB *qcow_aio_readv(BlockDriverState *bs, acb->sector_num = sector_num; acb->qiov = qiov; if (qiov->niov > 1) - acb->buf = acb->orig_buf = qemu_memalign(512, qiov->size); + acb->buf = acb->orig_buf = qemu_blockalign(bs, qiov->size); else acb->buf = (uint8_t *)qiov->iov->iov_base; acb->nb_sectors = nb_sectors; @@ -736,7 +736,7 @@ static BlockDriverAIOCB *qcow_aio_writev(BlockDriverState *bs, acb->sector_num = sector_num; acb->qiov = qiov; if (qiov->niov > 1) { - acb->buf = acb->orig_buf = qemu_memalign(512, qiov->size); + acb->buf = acb->orig_buf = qemu_blockalign(bs, qiov->size); qemu_iovec_to_buffer(qiov, acb->buf); } else { acb->buf = (uint8_t *)qiov->iov->iov_base; diff --git a/block-qcow2.c b/block-qcow2.c index 7840634b57..1f3312590c 100644 --- a/block-qcow2.c +++ b/block-qcow2.c @@ -1412,7 +1412,7 @@ static QCowAIOCB *qcow_aio_setup(BlockDriverState *bs, acb->sector_num = sector_num; acb->qiov = qiov; if (qiov->niov > 1) { - acb->buf = acb->orig_buf = qemu_memalign(512, qiov->size); + acb->buf = acb->orig_buf = qemu_blockalign(bs, qiov->size); if (is_write) qemu_iovec_to_buffer(qiov, acb->buf); } else { diff --git a/block-raw-posix.c b/block-raw-posix.c index 822839fb8f..0663c0695b 100644 --- a/block-raw-posix.c +++ b/block-raw-posix.c @@ -165,7 +165,7 @@ static int raw_open(BlockDriverState *bs, const char *filename, int flags) s->fd = fd; s->aligned_buf = NULL; if ((flags & BDRV_O_NOCACHE)) { - s->aligned_buf = qemu_memalign(512, ALIGNED_BUFFER_SIZE); + s->aligned_buf = qemu_blockalign(bs, ALIGNED_BUFFER_SIZE); if (s->aligned_buf == NULL) { ret = -errno; close(fd); @@ -362,6 +362,8 @@ int bdrv_open2(BlockDriverState *bs, const char *filename, int flags, bs->is_temporary = 0; bs->encrypted = 0; bs->valid_key = 0; + /* buffer_alignment defaulted to 512, drivers can change this value */ + bs->buffer_alignment = 512; if (flags & BDRV_O_SNAPSHOT) { BlockDriverState *bs1; @@ -1390,7 +1392,7 @@ static BlockDriverAIOCB *bdrv_aio_rw_vector(BlockDriverState *bs, acb = qemu_aio_get(bs, cb, opaque); acb->is_write = is_write; acb->qiov = qiov; - acb->bounce = qemu_memalign(512, qiov->size); + acb->bounce = qemu_blockalign(bs, qiov->size); if (!acb->bh) acb->bh = qemu_bh_new(bdrv_aio_bh_cb, acb); @@ -1640,3 +1642,8 @@ BlockDriverAIOCB *bdrv_aio_ioctl(BlockDriverState *bs, return drv->bdrv_aio_ioctl(bs, req, buf, cb, opaque); return NULL; } + +void *qemu_blockalign(BlockDriverState *bs, size_t size) +{ + return qemu_memalign((bs && bs->buffer_alignment) ? bs->buffer_alignment : 512, size); +} diff --git a/block_int.h b/block_int.h index e10b9069f2..9d119404cf 100644 --- a/block_int.h +++ b/block_int.h @@ -145,6 +145,9 @@ struct BlockDriverState { /* Whether the disk can expand beyond total_sectors */ int growable; + /* the memory alignment required for the buffers handled by this driver */ + int buffer_alignment; + /* NOTE: the following infos are only hints for real hardware drivers. They are not used by the block driver */ int cyls, heads, secs, translation; @@ -173,6 +176,8 @@ void *qemu_aio_get_pool(AIOPool *pool, BlockDriverState *bs, BlockDriverCompletionFunc *cb, void *opaque); void qemu_aio_release(void *p); +void *qemu_blockalign(BlockDriverState *bs, size_t size); + extern BlockDriverState *bdrv_first; #endif /* BLOCK_INT_H */ @@ -2788,11 +2788,11 @@ static void ide_init2(IDEState *ide_state, for(i = 0; i < 2; i++) { s = ide_state + i; - s->io_buffer = qemu_memalign(512, IDE_DMA_BUF_SECTORS*512 + 4); if (i == 0) s->bs = hd0; else s->bs = hd1; + s->io_buffer = qemu_blockalign(s->bs, IDE_DMA_BUF_SECTORS*512 + 4); if (s->bs) { bdrv_get_geometry(s->bs, &nb_sectors); bdrv_guess_geometry(s->bs, &cylinders, &heads, &secs); |