Signed-off-by: Boyuan Zhang <boyuan.zh...@amd.com> --- src/gallium/state_trackers/va/image.c | 48 +++++++++++++++++++++++++++++------ 1 file changed, 40 insertions(+), 8 deletions(-)
diff --git a/src/gallium/state_trackers/va/image.c b/src/gallium/state_trackers/va/image.c index 3c8cc9c..1f68169 100644 --- a/src/gallium/state_trackers/va/image.c +++ b/src/gallium/state_trackers/va/image.c @@ -499,7 +499,7 @@ vlVaPutImage(VADriverContextP ctx, VASurfaceID surface, VAImageID image, VAImage *vaimage; struct pipe_sampler_view **views; enum pipe_format format; - void *data[3]; + uint8_t *data[3]; unsigned pitches[3], i, j; if (!ctx) @@ -539,7 +539,9 @@ vlVaPutImage(VADriverContextP ctx, VASurfaceID surface, VAImageID image, return VA_STATUS_ERROR_OPERATION_FAILED; } - if (format != surf->buffer->buffer_format) { + if ((format != surf->buffer->buffer_format) && + ((format != PIPE_FORMAT_YV12) || (surf->buffer->buffer_format != PIPE_FORMAT_NV12)) && + ((format != PIPE_FORMAT_IYUV) || (surf->buffer->buffer_format != PIPE_FORMAT_NV12))) { struct pipe_video_buffer *tmp_buf; struct pipe_video_buffer templat = surf->templat; @@ -581,12 +583,42 @@ vlVaPutImage(VADriverContextP ctx, VASurfaceID surface, VAImageID image, unsigned width, height; if (!views[i]) continue; vlVaVideoSurfaceSize(surf, i, &width, &height); - for (j = 0; j < views[i]->texture->array_size; ++j) { - struct pipe_box dst_box = {0, 0, j, width, height, 1}; - drv->pipe->transfer_inline_write(drv->pipe, views[i]->texture, 0, - PIPE_TRANSFER_WRITE, &dst_box, - data[i] + pitches[i] * j, - pitches[i] * views[i]->texture->array_size, 0); + if ((format == PIPE_FORMAT_YV12) || (format == PIPE_FORMAT_IYUV) && + (surf->buffer->buffer_format == PIPE_FORMAT_NV12) && (i == 1)) { + struct pipe_transfer *transfer = NULL; + uint8_t *map = NULL; + struct pipe_box dst_box_1 = {0, 0, 0, width, height, 1}; + map = drv->pipe->transfer_map(drv->pipe, + views[i]->texture, + 0, + PIPE_TRANSFER_DISCARD_RANGE, + &dst_box_1, &transfer); + if (map == NULL) + return VA_STATUS_ERROR_OPERATION_FAILED; + + bool odd = false; + for (unsigned int k = 0; k < ((vaimage->offsets[1])/2) ; k++){ + if (odd == false) { + map[k] = data[i][k/2]; + odd = true; + } + else { + map[k] = data[i+1][k/2]; + odd = false; + } + } + pipe_transfer_unmap(drv->pipe, transfer); + pipe_mutex_unlock(drv->mutex); + return VA_STATUS_SUCCESS; + } + else { + for (j = 0; j < views[i]->texture->array_size; ++j) { + struct pipe_box dst_box = {0, 0, j, width, height, 1}; + drv->pipe->transfer_inline_write(drv->pipe, views[i]->texture, 0, + PIPE_TRANSFER_WRITE, &dst_box, + data[i] + pitches[i] * j, + pitches[i] * views[i]->texture->array_size, 0); + } } } pipe_mutex_unlock(drv->mutex); -- 2.7.4 _______________________________________________ mesa-dev mailing list mesa-dev@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/mesa-dev