diff options
Diffstat (limited to 'softmmu')
-rw-r--r-- | softmmu/dma-helpers.c | 38 |
1 files changed, 26 insertions, 12 deletions
diff --git a/softmmu/dma-helpers.c b/softmmu/dma-helpers.c index 7d766a5e89..b0be156479 100644 --- a/softmmu/dma-helpers.c +++ b/softmmu/dma-helpers.c @@ -19,7 +19,7 @@ /* #define DEBUG_IOMMU */ MemTxResult dma_memory_set(AddressSpace *as, dma_addr_t addr, - uint8_t c, dma_addr_t len) + uint8_t c, dma_addr_t len, MemTxAttrs attrs) { dma_barrier(as, DMA_DIRECTION_FROM_DEVICE); @@ -31,8 +31,7 @@ MemTxResult dma_memory_set(AddressSpace *as, dma_addr_t addr, memset(fillbuf, c, FILLBUF_SIZE); while (len > 0) { l = len < FILLBUF_SIZE ? len : FILLBUF_SIZE; - error |= address_space_write(as, addr, MEMTXATTRS_UNSPECIFIED, - fillbuf, l); + error |= address_space_write(as, addr, attrs, fillbuf, l); len -= l; addr += l; } @@ -144,7 +143,8 @@ static void dma_blk_cb(void *opaque, int ret) while (dbs->sg_cur_index < dbs->sg->nsg) { cur_addr = dbs->sg->sg[dbs->sg_cur_index].base + dbs->sg_cur_byte; cur_len = dbs->sg->sg[dbs->sg_cur_index].len - dbs->sg_cur_byte; - mem = dma_memory_map(dbs->sg->as, cur_addr, &cur_len, dbs->dir); + mem = dma_memory_map(dbs->sg->as, cur_addr, &cur_len, dbs->dir, + MEMTXATTRS_UNSPECIFIED); /* * Make reads deterministic in icount mode. Windows sometimes issues * disk read requests with overlapping SGs. It leads @@ -294,11 +294,14 @@ BlockAIOCB *dma_blk_write(BlockBackend *blk, } -static uint64_t dma_buf_rw(uint8_t *ptr, int32_t len, QEMUSGList *sg, - DMADirection dir) +static MemTxResult dma_buf_rw(void *buf, int32_t len, uint64_t *residp, + QEMUSGList *sg, DMADirection dir, + MemTxAttrs attrs) { + uint8_t *ptr = buf; uint64_t resid; int sg_cur_index; + MemTxResult res = MEMTX_OK; resid = sg->size; sg_cur_index = 0; @@ -306,23 +309,34 @@ static uint64_t dma_buf_rw(uint8_t *ptr, int32_t len, QEMUSGList *sg, while (len > 0) { ScatterGatherEntry entry = sg->sg[sg_cur_index++]; int32_t xfer = MIN(len, entry.len); - dma_memory_rw(sg->as, entry.base, ptr, xfer, dir); + res |= dma_memory_rw(sg->as, entry.base, ptr, xfer, dir, attrs); ptr += xfer; len -= xfer; resid -= xfer; } - return resid; + if (residp) { + *residp = resid; + } + return res; } -uint64_t dma_buf_read(uint8_t *ptr, int32_t len, QEMUSGList *sg) +uint64_t dma_buf_read(void *ptr, int32_t len, QEMUSGList *sg, MemTxAttrs attrs) { - return dma_buf_rw(ptr, len, sg, DMA_DIRECTION_FROM_DEVICE); + uint64_t resid; + + dma_buf_rw(ptr, len, &resid, sg, DMA_DIRECTION_FROM_DEVICE, attrs); + + return resid; } -uint64_t dma_buf_write(uint8_t *ptr, int32_t len, QEMUSGList *sg) +uint64_t dma_buf_write(void *ptr, int32_t len, QEMUSGList *sg, MemTxAttrs attrs) { - return dma_buf_rw(ptr, len, sg, DMA_DIRECTION_TO_DEVICE); + uint64_t resid; + + dma_buf_rw(ptr, len, &resid, sg, DMA_DIRECTION_TO_DEVICE, attrs); + + return resid; } void dma_acct_start(BlockBackend *blk, BlockAcctCookie *cookie, |