diff options
author | Chris Wilson <chris@chris-wilson.co.uk> | 2012-01-11 19:51:42 +0000 |
---|---|---|
committer | Chris Wilson <chris@chris-wilson.co.uk> | 2012-01-11 19:54:12 +0000 |
commit | c64a9d0683e047a7eb041df78db746f6dd387b5e (patch) | |
tree | 94e490ae50c8545539f723c00e05f0f71dc3527c | |
parent | b82851e74d5010ee08938ee42fa44c29fed633b1 (diff) |
sna: Choose a stride for the indirect replacement
Don't blithely assume that the incoming bytes are appropriately aligned
for the destination buffer. Indeed we may be replacing the destination
bo with the shadow bytes out of another,larger, pixmap, in which case we
do need to create a stride that is appropriate for the upload an
perform the 2D copy.
Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
-rw-r--r-- | src/sna/sna_io.c | 17 |
1 files changed, 13 insertions, 4 deletions
diff --git a/src/sna/sna_io.c b/src/sna/sna_io.c index 3c17d3aa..a7d4da5f 100644 --- a/src/sna/sna_io.c +++ b/src/sna/sna_io.c @@ -820,14 +820,25 @@ indirect_replace(struct sna *sna, &box, 1); } else { uint32_t cmd, br13, *b; + int pitch; + + pitch = pixmap->drawable.width * pixmap->drawable.bitsPerPixel; + pitch = ALIGN(pitch, 32) >> 3; src_bo = kgem_create_buffer(kgem, - stride * pixmap->drawable.height, + pitch * pixmap->drawable.height, KGEM_BUFFER_WRITE, &ptr); if (!src_bo) return false; + memcpy_blt(src, ptr, pixmap->drawable.bitsPerPixel, + stride, pitch, + 0, 0, + 0, 0, + pixmap->drawable.width, + pixmap->drawable.height); + cmd = XY_SRC_COPY_BLT_CMD; br13 = bo->pitch; if (kgem->gen >= 40 && bo->tiling) { @@ -852,8 +863,6 @@ indirect_replace(struct sna *sna, _kgem_set_mode(kgem, KGEM_BLT); } - memcpy(ptr, src, stride * pixmap->drawable.height); - b = kgem->batch + kgem->nbatch; b[0] = cmd; b[1] = br13; @@ -865,7 +874,7 @@ indirect_replace(struct sna *sna, KGEM_RELOC_FENCED, 0); b[5] = 0; - b[6] = stride; + b[6] = pitch; b[7] = kgem_add_reloc(kgem, kgem->nbatch + 7, src_bo, I915_GEM_DOMAIN_RENDER << 16 | KGEM_RELOC_FENCED, |