[Piglit] [PATCH v2] dmabuf: fix YUV tests for drivers other than intel

Kristian Høgsberg hoegsberg at gmail.com
Fri Sep 9 18:30:59 UTC 2016


On Fri, Sep 9, 2016 at 10:44 AM Rob Clark <robdclark at gmail.com> wrote:

> Ok, so the basic problem with the YUV tests is that they currently
> completely ignore driver/hw pitch requirements, since the code that
> allocates the buffer doesn't know the pixel format, only the 'cpp'.
>
> The yuv test creates a small 4x4 yuv eglimage.  If, say, the hardware
> requires the pitch to be aligned to, say, 32pixels, everything is fine
> for the Y plane, but the subsampled U/V or U+V plane has half as many
> pixels.  (This did help me catch a bug in driver, not rejecting the
> dmabuf import with invalid pitch, but that doesn't help to get the
> piglit tests running.)
>
> The best approach I could come up with to fix this is to pass the
> fourcc all the way down to the code that creates the dmabuf (and copies
> src data into the dmabuf).  Unfortunately this makes the patch a bit
> bigger than I was hoping, and not really sure a good way to split it
> up.
>
> This is tested on i965 (with the intel dma-buf backend) and freedreno
> (with the gbm dma-buf backend).  In the gbm case, it requires new
> gbm format values for R8 and GR88, which is on mesa master as of
> this morning.  (So I bumped the gbm version dependency to 12.1.)
>
> Signed-off-by: Rob Clark <robdclark at gmail.com>
>

Few nitpicks below, but looks good:

Reviewed-by: Kristian Høgsberg <krh at bitplanet.net>


> ---
> v2: drop unneeded src_stride arg
>
>  CMakeLists.txt                                     |   2 +-
>  .../intel_external_sampler_only.c                  |  11 +-
>  .../intel_unsupported_format.c                     |  19 +-
>  .../ext_image_dma_buf_import/invalid_attributes.c  |  43 +++--
>  .../spec/ext_image_dma_buf_import/invalid_hints.c  |  23 ++-
>  .../ext_image_dma_buf_import/missing_attributes.c  |  25 ++-
>  .../ext_image_dma_buf_import/ownership_transfer.c  |  11 +-
>  tests/spec/ext_image_dma_buf_import/refcount.c     |  15 +-
>  .../spec/ext_image_dma_buf_import/sample_common.c  |  73 +++-----
>  .../spec/ext_image_dma_buf_import/sample_common.h  |   5 +-
>  tests/spec/ext_image_dma_buf_import/sample_rgb.c   |   2 +-
>  tests/spec/ext_image_dma_buf_import/sample_yuv.c   |  26 ++-
>  .../transcode-nv12-as-r8-gr88.c                    |  24 +--
>  tests/util/piglit-framework-gl.c                   |  14 +-
>  tests/util/piglit-framework-gl.h                   |  22 ++-
>  .../util/piglit-framework-gl/piglit_drm_dma_buf.c  | 196
> ++++++++++++++++-----
>  .../util/piglit-framework-gl/piglit_drm_dma_buf.h  |  15 +-
>  .../util/piglit-framework-gl/piglit_gl_framework.h |   6 +-
>  18 files changed, 314 insertions(+), 218 deletions(-)
>
> diff --git a/CMakeLists.txt b/CMakeLists.txt
> index 536f775..4e4b5ae 100644
> --- a/CMakeLists.txt
> +++ b/CMakeLists.txt
> @@ -141,7 +141,7 @@ IF(${CMAKE_SYSTEM_NAME} MATCHES "Linux")
>         if(GBM_FOUND)
>                 set(PIGLIT_HAS_GBM True)
>                 add_definitions(-DPIGLIT_HAS_GBM)
> -               if (GBM_VERSION VERSION_EQUAL "12.0" OR GBM_VERSION
> VERSION_GREATER "12.0")
> +               if (GBM_VERSION VERSION_EQUAL "12.1" OR GBM_VERSION
> VERSION_GREATER "12.1")
>                         set(PIGLIT_HAS_GBM_BO_MAP True)
>                         add_definitions(-DPIGLIT_HAS_GBM_BO_MAP)
>                 endif()
> diff --git
> a/tests/spec/ext_image_dma_buf_import/intel_external_sampler_only.c
> b/tests/spec/ext_image_dma_buf_import/intel_external_sampler_only.c
> index 7743a68..de1074c 100644
> --- a/tests/spec/ext_image_dma_buf_import/intel_external_sampler_only.c
> +++ b/tests/spec/ext_image_dma_buf_import/intel_external_sampler_only.c
> @@ -21,6 +21,8 @@
>   * IN THE SOFTWARE.
>   */
>
> +#include "piglit-framework-gl/piglit_drm_dma_buf.h"
> +
>  #include "image_common.h"
>
>  /**
> @@ -98,21 +100,18 @@ piglit_display(void)
>         const unsigned w = 2;
>         const unsigned h = 2;
>         const unsigned cpp = 4;
> +       const unsigned fourcc = DRM_FORMAT_ARGB8888;
>         const unsigned char *pixels = alloca(w * h * cpp);
>         struct piglit_dma_buf *buf;
> -       unsigned stride;
> -       unsigned offset;
> -       int fd;
>         EGLImageKHR img;
>         enum piglit_result res;
>         bool pass = true;
>
> -       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,
> -                               &buf, &fd, &stride, &offset);
> +       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> -       img = create_image(w, h, fd, stride, offset);
> +       img = create_image(w, h, buf->fd, buf->stride[0], buf->offset[0]);
>
>         if (!img) {
>                 piglit_destroy_dma_buf(buf);
> diff --git
> a/tests/spec/ext_image_dma_buf_import/intel_unsupported_format.c
> b/tests/spec/ext_image_dma_buf_import/intel_unsupported_format.c
> index 69bb267..8373e90 100644
> --- a/tests/spec/ext_image_dma_buf_import/intel_unsupported_format.c
> +++ b/tests/spec/ext_image_dma_buf_import/intel_unsupported_format.c
> @@ -21,6 +21,8 @@
>   * IN THE SOFTWARE.
>   */
>
> +#include "piglit-framework-gl/piglit_drm_dma_buf.h"
> +
>  #include "image_common.h"
>
>  /**
> @@ -62,20 +64,17 @@ piglit_display(void)
>         const unsigned w = 2;
>         const unsigned h = 2;
>         const unsigned cpp = 4;
> +       const unsigned fourcc = DRM_FORMAT_ARGB8888;
>         const unsigned char *pixels = alloca(w * h * cpp);
>         struct piglit_dma_buf *buf;
> -       unsigned stride;
> -       unsigned offset;
> -       int fd;
>         EGLImageKHR img;
>         enum piglit_result res;
>
> -       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,
> -                               &buf, &fd, &stride, &offset);
> +       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> -       img = create_image(w, h, fd, stride, offset);
> +       img = create_image(w, h, buf->fd, buf->stride[0], buf->offset[0]);
>
>         if (!piglit_check_egl_error(EGL_BAD_MATCH)) {
>                 if (img)
> @@ -83,14 +82,16 @@ piglit_display(void)
>                 return PIGLIT_FAIL;
>         }
>
> -       piglit_destroy_dma_buf(buf);
> -
>         /**
>          * EGL stack can claim the ownership of the file descriptor only
> when it
>          * succeeds. Close the descriptor and check that it really wasn't
> closed
>          * by EGL.
>          */
> -       return close(fd) == 0 ? PIGLIT_PASS : PIGLIT_FAIL;
> +       res = close(buf->fd) == 0 ? PIGLIT_PASS : PIGLIT_FAIL;
> +
> +       piglit_destroy_dma_buf(buf);
> +
> +       return res;
>  }
>
>  void
> diff --git a/tests/spec/ext_image_dma_buf_import/invalid_attributes.c
> b/tests/spec/ext_image_dma_buf_import/invalid_attributes.c
> index b77e47b..cc0b046 100644
> --- a/tests/spec/ext_image_dma_buf_import/invalid_attributes.c
> +++ b/tests/spec/ext_image_dma_buf_import/invalid_attributes.c
> @@ -21,6 +21,8 @@
>   * IN THE SOFTWARE.
>   */
>
> +#include "piglit-framework-gl/piglit_drm_dma_buf.h"
> +
>  #include "image_common.h"
>
>  /**
> @@ -209,44 +211,41 @@ piglit_display(void)
>         const unsigned w = 2;
>         const unsigned h = 2;
>         const unsigned cpp = 4;
> +       const unsigned fourcc = DRM_FORMAT_ARGB8888;
>         const unsigned char *pixels = alloca(w * h * cpp);
>         struct piglit_dma_buf *buf;
> -       unsigned stride;
> -       unsigned offset;
> -       int fd;
>         enum piglit_result res;
>         bool pass = true;
>
> -       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,
> -                               &buf, &fd, &stride, &offset);
> +       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> -       pass = test_excess_attributes(w, h, fd, stride, offset,
> -                               EGL_DMA_BUF_PLANE1_FD_EXT, fd) && pass;
> -       pass = test_excess_attributes(w, h, fd, stride, offset,
> +       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0],
> buf->offset[0],
> +                               EGL_DMA_BUF_PLANE1_FD_EXT, buf->fd) &&
> pass;
> +       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0],
> buf->offset[0],
>                                 EGL_DMA_BUF_PLANE1_OFFSET_EXT, 0) && pass;
> -       pass = test_excess_attributes(w, h, fd, stride, offset,
> -                               EGL_DMA_BUF_PLANE1_PITCH_EXT, stride) &&
> pass;
> -       pass = test_excess_attributes(w, h, fd, stride, offset,
> -                               EGL_DMA_BUF_PLANE2_FD_EXT, fd) && pass;
> -       pass = test_excess_attributes(w, h, fd, stride, offset,
> +       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0],
> buf->offset[0],
> +                               EGL_DMA_BUF_PLANE1_PITCH_EXT,
> buf->stride[0]) && pass;
> +       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0],
> buf->offset[0],
> +                               EGL_DMA_BUF_PLANE2_FD_EXT, buf->fd) &&
> pass;
> +       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0],
> buf->offset[0],
>                                 EGL_DMA_BUF_PLANE2_OFFSET_EXT, 0) && pass;
> -       pass = test_excess_attributes(w, h, fd, stride, offset,
> -                               EGL_DMA_BUF_PLANE2_PITCH_EXT, stride) &&
> pass;
> -       pass = test_buffer_not_null(w, h, fd, stride, offset) && pass;
> -       pass = test_invalid_context(w, h, fd, stride, offset) && pass;
> -       pass = test_invalid_format(w, h, fd, stride, offset) && pass;
> -       pass = test_pitch_zero(w, h, fd, stride, offset) && pass;
> -
> -       piglit_destroy_dma_buf(buf);
> +       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0],
> buf->offset[0],
> +                               EGL_DMA_BUF_PLANE2_PITCH_EXT,
> buf->stride[0]) && pass;
> +       pass = test_buffer_not_null(w, h, buf->fd, buf->stride[0],
> buf->offset[0]) && pass;
> +       pass = test_invalid_context(w, h, buf->fd, buf->stride[0],
> buf->offset[0]) && pass;
> +       pass = test_invalid_format(w, h, buf->fd, buf->stride[0],
> buf->offset[0]) && pass;
> +       pass = test_pitch_zero(w, h, buf->fd, buf->stride[0],
> buf->offset[0]) && pass;
>
>         /**
>          * EGL stack can claim the ownership of the file descriptor only
> when it
>          * succeeds. Close the file descriptor here and check that it
> really
>          * wasn't closed by EGL.
>          */
> -       pass = (close(fd) == 0) && pass;
> +       pass = (close(buf->fd) == 0) && pass;
> +
> +       piglit_destroy_dma_buf(buf);
>
>         return pass ? PIGLIT_PASS : PIGLIT_FAIL;
>  }
> diff --git a/tests/spec/ext_image_dma_buf_import/invalid_hints.c
> b/tests/spec/ext_image_dma_buf_import/invalid_hints.c
> index fa006f0..c2b43a2 100644
> --- a/tests/spec/ext_image_dma_buf_import/invalid_hints.c
> +++ b/tests/spec/ext_image_dma_buf_import/invalid_hints.c
> @@ -21,6 +21,8 @@
>   * IN THE SOFTWARE.
>   */
>
> +#include "piglit-framework-gl/piglit_drm_dma_buf.h"
> +
>  #include "image_common.h"
>
>  /**
> @@ -97,36 +99,33 @@ piglit_display(void)
>         const unsigned w = 2;
>         const unsigned h = 2;
>         const unsigned cpp = 4;
> +       const unsigned fourcc = DRM_FORMAT_ARGB8888;
>         const unsigned char *pixels = alloca(w * h * cpp);
>         struct piglit_dma_buf *buf;
> -       unsigned stride;
> -       unsigned offset;
> -       int fd;
>         enum piglit_result res;
>         bool pass = true;
>
> -       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,
> -                               &buf, &fd, &stride, &offset);
> +       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> -       pass = test_invalid_hint(w, h, fd, stride, offset,
> +       pass = test_invalid_hint(w, h, buf->fd, buf->stride[0],
> buf->offset[0],
>                         EGL_YUV_COLOR_SPACE_HINT_EXT, 0) && pass;
> -       pass = test_invalid_hint(w, h, fd, stride, offset,
> +       pass = test_invalid_hint(w, h, buf->fd, buf->stride[0],
> buf->offset[0],
>                         EGL_SAMPLE_RANGE_HINT_EXT, 0) && pass;
> -       pass = test_invalid_hint(w, h, fd, stride, offset,
> +       pass = test_invalid_hint(w, h, buf->fd, buf->stride[0],
> buf->offset[0],
>                         EGL_YUV_CHROMA_HORIZONTAL_SITING_HINT_EXT, 0) &&
> pass;
> -       pass = test_invalid_hint(w, h, fd, stride, offset,
> +       pass = test_invalid_hint(w, h, buf->fd, buf->stride[0],
> buf->offset[0],
>                         EGL_YUV_CHROMA_VERTICAL_SITING_HINT_EXT, 0) &&
> pass;
>
> -       piglit_destroy_dma_buf(buf);
> -
>         /**
>          * EGL stack can claim the ownership of the file descriptor only
> when it
>          * succeeds. Close the descriptor and check that it really wasn't
> closed
>          * by EGL.
>          */
> -       pass = (close(fd) == 0) && pass;
> +       pass = (close(buf->fd) == 0) && pass;
> +
> +       piglit_destroy_dma_buf(buf);
>
>         return pass ? PIGLIT_PASS : PIGLIT_FAIL;
>  }
> diff --git a/tests/spec/ext_image_dma_buf_import/missing_attributes.c
> b/tests/spec/ext_image_dma_buf_import/missing_attributes.c
> index d7d89e6..d16b60e 100644
> --- a/tests/spec/ext_image_dma_buf_import/missing_attributes.c
> +++ b/tests/spec/ext_image_dma_buf_import/missing_attributes.c
> @@ -21,6 +21,8 @@
>   * IN THE SOFTWARE.
>   */
>
> +#include "piglit-framework-gl/piglit_drm_dma_buf.h"
> +
>  #include "image_common.h"
>
>  /**
> @@ -105,47 +107,44 @@ piglit_display(void)
>         const unsigned w = 2;
>         const unsigned h = 2;
>         const unsigned cpp = 2;
>

I don't know if this was an issue with the existing test, but cpp = 2
doesn't match ARGB8888. Probably doesn't matter for this test, but looks
weird.


> +       const unsigned fourcc = DRM_FORMAT_ARGB8888;
>         const unsigned char *pixels = alloca(w * h * cpp);
>         EGLint all[2 * NUM_MANDATORY_ATTRS];
>         EGLint missing[2 * (NUM_MANDATORY_ATTRS - 1) + 1];
>         struct piglit_dma_buf *buf;
> -       unsigned stride;
> -       unsigned offset;
> -       int fd;
>         enum piglit_result res;
>         bool pass = true;
>
> -       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,
> -                               &buf, &fd, &stride, &offset);
> +       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> -       fill_full_set(w, h, fd, offset, stride, all);
> +       fill_full_set(w, h, buf->fd, buf->offset[0], buf->stride[0], all);
>
>         fill_one_missing(all, missing, EGL_HEIGHT);
> -       pass = test_missing(fd, missing) && pass;
> +       pass = test_missing(buf->fd, missing) && pass;
>
>         fill_one_missing(all, missing, EGL_WIDTH);
> -       pass = test_missing(fd, missing) && pass;
> +       pass = test_missing(buf->fd, missing) && pass;
>
>         fill_one_missing(all, missing, EGL_LINUX_DRM_FOURCC_EXT);
> -       pass = test_missing(fd, missing) && pass;
> +       pass = test_missing(buf->fd, missing) && pass;
>
>         fill_one_missing(all, missing, EGL_DMA_BUF_PLANE0_FD_EXT);
> -       pass = test_missing(fd, missing) && pass;
> +       pass = test_missing(buf->fd, missing) && pass;
>
>         fill_one_missing(all, missing, EGL_DMA_BUF_PLANE0_OFFSET_EXT);
> -       pass = test_missing(fd, missing) && pass;
> +       pass = test_missing(buf->fd, missing) && pass;
>
>         fill_one_missing(all, missing, EGL_DMA_BUF_PLANE0_PITCH_EXT);
> -       pass = test_missing(fd, missing) && pass;
> +       pass = test_missing(buf->fd, missing) && pass;
>
>         /**
>          * EGL stack can claim the ownership of the file descriptor only
> when it
>          * succeeds. Close the file descriptor here and check that it
> really
>          * wasn't closed by EGL.
>          */
> -       pass = (close(fd) == 0) && pass;
> +       pass = (close(buf->fd) == 0) && pass;
>
>         piglit_destroy_dma_buf(buf);
>
> diff --git a/tests/spec/ext_image_dma_buf_import/ownership_transfer.c
> b/tests/spec/ext_image_dma_buf_import/ownership_transfer.c
> index 2da455b..be5a044 100644
> --- a/tests/spec/ext_image_dma_buf_import/ownership_transfer.c
> +++ b/tests/spec/ext_image_dma_buf_import/ownership_transfer.c
> @@ -23,6 +23,8 @@
>
>  #include <errno.h>
>
> +#include "piglit-framework-gl/piglit_drm_dma_buf.h"
> +
>  #include "image_common.h"
>
>  /**
> @@ -113,19 +115,16 @@ piglit_display(void)
>         const unsigned w = 2;
>         const unsigned h = 2;
>         const unsigned cpp = 4;
> +       const unsigned fourcc = fourcc_code('A', 'R', '2', '4');;
>

Why the custom fourcc? And two semicolons.


>         const unsigned char *pixels = alloca(w * h * cpp);
>         struct piglit_dma_buf *buf;
> -       unsigned stride;
> -       unsigned offset;
> -       int fd;
>         enum piglit_result res;
>
> -       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,
> -                               &buf, &fd, &stride, &offset);
> +       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> -       return test_create_and_destroy(w, h, buf, fd, stride, offset);
> +       return test_create_and_destroy(w, h, buf, buf->fd, buf->stride[0],
> buf->offset[0]);
>  }
>
>  void
> diff --git a/tests/spec/ext_image_dma_buf_import/refcount.c
> b/tests/spec/ext_image_dma_buf_import/refcount.c
> index 5b14cdd..bc15ff5 100644
> --- a/tests/spec/ext_image_dma_buf_import/refcount.c
> +++ b/tests/spec/ext_image_dma_buf_import/refcount.c
> @@ -21,6 +21,8 @@
>   * IN THE SOFTWARE.
>   */
>
> +#include "piglit-framework-gl/piglit_drm_dma_buf.h"
> +
>  #include "sample_common.h"
>  #include "image_common.h"
>
> @@ -57,8 +59,6 @@ piglit_display(void)
>         int cpp = 4;
>         enum piglit_result res;
>         struct piglit_dma_buf *buf;
> -       unsigned stride, offset;
> -       int fd;
>         EGLImageKHR img1, img2;
>         GLuint tex1, tex2;
>         /* Scale up factor for drawing the texture to the screen. */
> @@ -67,22 +67,19 @@ piglit_display(void)
>         int i;
>         GLubyte *expected;
>
> -       res = piglit_create_dma_buf(w, h, cpp, src, w * cpp,
> -                                   &buf, &fd, &stride, &offset);
> +       res = piglit_create_dma_buf(w, h, fourcc, src, &buf);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> -       res = egl_image_for_dma_buf_fd(dup(fd), fourcc, w, h, stride,
> offset,
> -                                      &img1);
> +       res = egl_image_for_dma_buf_fd(buf, dup(buf->fd), fourcc, &img1);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> -       res = egl_image_for_dma_buf_fd(dup(fd), fourcc, w, h, stride,
> offset,
> -                                      &img2);
> +       res = egl_image_for_dma_buf_fd(buf, dup(buf->fd), fourcc, &img2);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> -       close(fd);
> +       close(buf->fd);
>
>         res = texture_for_egl_image(img1, &tex1);
>         if (res != PIGLIT_PASS)
> diff --git a/tests/spec/ext_image_dma_buf_import/sample_common.c
> b/tests/spec/ext_image_dma_buf_import/sample_common.c
> index c5aa1e1..2f586c7 100644
> --- a/tests/spec/ext_image_dma_buf_import/sample_common.c
> +++ b/tests/spec/ext_image_dma_buf_import/sample_common.c
> @@ -23,6 +23,8 @@
>
>  #include <unistd.h>
>
> +#include "piglit-framework-gl/piglit_drm_dma_buf.h"
> +
>  #include "image_common.h"
>  #include "sample_common.h"
>
> @@ -105,47 +107,46 @@ sample_tex(GLuint tex, unsigned x, unsigned y,
> unsigned w, unsigned h)
>  }
>
>  enum piglit_result
> -egl_image_for_dma_buf_fd(int fd, int fourcc, int w, int h,
> -                        unsigned stride, unsigned offset, EGLImageKHR
> *out_img)
> +egl_image_for_dma_buf_fd(struct piglit_dma_buf *buf, int fd, int fourcc,
> EGLImageKHR *out_img)
>  {
>         EGLint error;
>         EGLImageKHR img;
>         EGLint attr_packed[] = {
> -               EGL_WIDTH, w,
> -               EGL_HEIGHT, h,
> +               EGL_WIDTH, buf->w,
> +               EGL_HEIGHT, buf->h,
>                 EGL_LINUX_DRM_FOURCC_EXT, fourcc,
>                 EGL_DMA_BUF_PLANE0_FD_EXT, fd,
> -               EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
> -               EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
> +               EGL_DMA_BUF_PLANE0_OFFSET_EXT, buf->offset[0],
> +               EGL_DMA_BUF_PLANE0_PITCH_EXT, buf->stride[0],
>                 EGL_NONE
>         };
>
>         EGLint attr_nv12[] = {
> -               EGL_WIDTH, w,
> -               EGL_HEIGHT, h,
> +               EGL_WIDTH, buf->w,
> +               EGL_HEIGHT, buf->h,
>                 EGL_LINUX_DRM_FOURCC_EXT, fourcc,
>                 EGL_DMA_BUF_PLANE0_FD_EXT, fd,
> -               EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
> -               EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
> +               EGL_DMA_BUF_PLANE0_OFFSET_EXT, buf->offset[0],
> +               EGL_DMA_BUF_PLANE0_PITCH_EXT, buf->stride[0],
>                 EGL_DMA_BUF_PLANE1_FD_EXT, fd,
> -               EGL_DMA_BUF_PLANE1_OFFSET_EXT, offset + h * stride,
> -               EGL_DMA_BUF_PLANE1_PITCH_EXT, stride,
> +               EGL_DMA_BUF_PLANE1_OFFSET_EXT, buf->offset[1],
> +               EGL_DMA_BUF_PLANE1_PITCH_EXT, buf->stride[1],
>                 EGL_NONE
>         };
>
>         EGLint attr_yuv420[] = {
> -               EGL_WIDTH, w,
> -               EGL_HEIGHT, h,
> +               EGL_WIDTH, buf->w,
> +               EGL_HEIGHT, buf->h,
>                 EGL_LINUX_DRM_FOURCC_EXT, fourcc,
>                 EGL_DMA_BUF_PLANE0_FD_EXT, fd,
> -               EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
> -               EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
> +               EGL_DMA_BUF_PLANE0_OFFSET_EXT, buf->offset[0],
> +               EGL_DMA_BUF_PLANE0_PITCH_EXT, buf->stride[0],
>                 EGL_DMA_BUF_PLANE1_FD_EXT, fd,
> -               EGL_DMA_BUF_PLANE1_OFFSET_EXT, offset + h * stride,
> -               EGL_DMA_BUF_PLANE1_PITCH_EXT, stride,
> +               EGL_DMA_BUF_PLANE1_OFFSET_EXT, buf->offset[1],
> +               EGL_DMA_BUF_PLANE1_PITCH_EXT, buf->stride[1],
>                 EGL_DMA_BUF_PLANE2_FD_EXT, fd,
> -               EGL_DMA_BUF_PLANE2_OFFSET_EXT, offset + h * stride + w / 2,
> -               EGL_DMA_BUF_PLANE2_PITCH_EXT, stride,
> +               EGL_DMA_BUF_PLANE2_OFFSET_EXT, buf->offset[2],
> +               EGL_DMA_BUF_PLANE2_PITCH_EXT, buf->stride[2],
>                 EGL_NONE
>         };
>
> @@ -191,21 +192,22 @@ egl_image_for_dma_buf_fd(int fd, int fourcc, int w,
> int h,
>  }
>
>  static enum piglit_result
> -sample_buffer(void *buf, int fd, int fourcc, unsigned w, unsigned h,
> -             unsigned stride, unsigned offset)
> +sample_buffer(struct piglit_dma_buf *buf, int fourcc)
>  {
>         enum piglit_result res;
>         EGLImageKHR img;
>         GLuint tex;
> +       int w = buf->w;
> +       int h = buf->h;
>
> -       res = egl_image_for_dma_buf_fd(fd, fourcc, w, h, stride, offset,
> &img);
> +       res = egl_image_for_dma_buf_fd(buf, buf->fd, fourcc, &img);
>
>         /* Release the creator side of the buffer. */
>         piglit_destroy_dma_buf(buf);
>
>         if (!img) {
>                 /* Close the descriptor also, EGL does not have ownership
> */
> -               close(fd);
> +               close(buf->fd);
>         }
>
>         if (res != PIGLIT_PASS)
> @@ -225,32 +227,15 @@ destroy:
>  }
>
>  enum piglit_result
> -dma_buf_create_and_sample_32bpp(unsigned w, unsigned h, unsigned cpp,
> +dma_buf_create_and_sample_32bpp(unsigned w, unsigned h,
>                                 int fourcc, const unsigned char *src)
>  {
>         struct piglit_dma_buf *buf;
> -       unsigned stride, offset;
> -       int fd;
>         enum piglit_result res;
>
> -       unsigned buffer_height;
> -
> -       switch (fourcc) {
> -       case DRM_FORMAT_NV12:
> -       case DRM_FORMAT_YUV420:
> -       case DRM_FORMAT_YVU420:
> -               buffer_height = h * 3 / 2;
> -               break;
> -       default:
> -               buffer_height = h;
> -               break;
> -       }
> -
> -       res = piglit_create_dma_buf(w, buffer_height,
> -                                   cpp, src, w * cpp, &buf, &fd, &stride,
> -                                   &offset);
> +       res = piglit_create_dma_buf(w, h, fourcc, src, &buf);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> -       return sample_buffer(buf, fd, fourcc, w, h, stride, offset);
> +       return sample_buffer(buf, fourcc);
>  }
> diff --git a/tests/spec/ext_image_dma_buf_import/sample_common.h
> b/tests/spec/ext_image_dma_buf_import/sample_common.h
> index db2ff82..36a5bb5 100644
> --- a/tests/spec/ext_image_dma_buf_import/sample_common.h
> +++ b/tests/spec/ext_image_dma_buf_import/sample_common.h
> @@ -32,12 +32,11 @@
>   * sample it using a shader program.
>   */
>  enum piglit_result
> -dma_buf_create_and_sample_32bpp(unsigned w, unsigned h, unsigned cpp,
> +dma_buf_create_and_sample_32bpp(unsigned w, unsigned h,
>                                 int fourcc, const unsigned char *src);
>
>  enum piglit_result
> -egl_image_for_dma_buf_fd(int fd, int fourcc, int w, int h,
> -                        unsigned stride, unsigned offset, EGLImageKHR
> *out_img);
> +egl_image_for_dma_buf_fd(struct piglit_dma_buf *buf, int fd, int fourcc,
> EGLImageKHR *out_img);
>
>  enum piglit_result
>  texture_for_egl_image(EGLImageKHR img, GLuint *out_tex);
> diff --git a/tests/spec/ext_image_dma_buf_import/sample_rgb.c
> b/tests/spec/ext_image_dma_buf_import/sample_rgb.c
> index af9b39f..b659717 100644
> --- a/tests/spec/ext_image_dma_buf_import/sample_rgb.c
> +++ b/tests/spec/ext_image_dma_buf_import/sample_rgb.c
> @@ -59,7 +59,7 @@ piglit_display(void)
>
>         glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
>
> -       res = dma_buf_create_and_sample_32bpp(2, 2, 4, fourcc, src);
> +       res = dma_buf_create_and_sample_32bpp(2, 2, fourcc, src);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> diff --git a/tests/spec/ext_image_dma_buf_import/sample_yuv.c
> b/tests/spec/ext_image_dma_buf_import/sample_yuv.c
> index 1fb8de6..a314bc5 100644
> --- a/tests/spec/ext_image_dma_buf_import/sample_yuv.c
> +++ b/tests/spec/ext_image_dma_buf_import/sample_yuv.c
> @@ -45,26 +45,38 @@ enum piglit_result
>  piglit_display(void)
>  {
>         static const unsigned char nv12[] = {
> +               /* Y */
>                  50,  70,  90, 110,
>                  50,  70,  90, 110,
>                  50,  70,  90, 110,
>                  50,  70,  90, 110,
> +               /* UV */
>                 120, 130, 140, 130,
> -               120, 160, 140, 160
> +               120, 160, 140, 160,
>         }, yuv420[] = {
> +               /* Y */
>                  50,  70,  90, 110,
>                  50,  70,  90, 110,
>                  50,  70,  90, 110,
>                  50,  70,  90, 110,
> -               120, 140, 130, 130,
> -               120, 140, 160, 160
> +               /* U */
> +               120, 140,
> +               120, 140,
> +               /* V */
> +               130, 130,
> +               160, 160,
>         }, yvu420[] = {
> +               /* Y */
>                  50,  70,  90, 110,
>                  50,  70,  90, 110,
>                  50,  70,  90, 110,
>                  50,  70,  90, 110,
> -               130, 130, 120, 140,
> -               160, 160, 120, 140,
> +               /* V */
> +               130, 130,
> +               160, 160,
> +               /* U */
> +               120, 140,
> +               120, 140,
>         };
>
>         static const unsigned char expected[4 * 4 * 4] = {
> @@ -78,7 +90,7 @@ piglit_display(void)
>                  90,  79, 111, 255,
>                 114, 103, 135, 255,
>
> -                92,  16,  25, 255,
> +                92,  16,  25, 255,
>                 115,  39,  48, 255,
>                 138,  55, 111, 255,
>                 161,  78, 135, 255,
> @@ -108,7 +120,7 @@ piglit_display(void)
>
>         glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
>
> -       res = dma_buf_create_and_sample_32bpp(4, 4, 1, fourcc, t);
> +       res = dma_buf_create_and_sample_32bpp(4, 4, fourcc, t);
>         if (res != PIGLIT_PASS)
>                 return res;
>
> diff --git
> a/tests/spec/ext_image_dma_buf_import/transcode-nv12-as-r8-gr88.c
> b/tests/spec/ext_image_dma_buf_import/transcode-nv12-as-r8-gr88.c
> index 31c27e6..f968539 100644
> --- a/tests/spec/ext_image_dma_buf_import/transcode-nv12-as-r8-gr88.c
> +++ b/tests/spec/ext_image_dma_buf_import/transcode-nv12-as-r8-gr88.c
> @@ -33,6 +33,8 @@
>   * and GR88 DRM formats.
>   */
>
> +#include "piglit-framework-gl/piglit_drm_dma_buf.h"
> +
>  #include "image_common.h"
>
>  #define WINDOW_WIDTH 4
> @@ -77,26 +79,20 @@ static const uint8_t v_data[] = {
>  };
>
>  static GLuint
> -create_dma_buf_texture(uint32_t width, uint32_t height,
> -                      uint32_t cpp, uint32_t stride,
> -                      uint32_t drm_fourcc, const void *pixels)
> +create_dma_buf_texture(uint32_t width, uint32_t height, uint32_t fourcc,
> +                      const void *pixels)
>  {
>         EGLDisplay dpy = eglGetCurrentDisplay();
>
>         enum piglit_result result = PIGLIT_PASS;
>
>         struct piglit_dma_buf *dma_buf;
> -       int dma_buf_fd;
> -       uint32_t dma_buf_offset;
> -       uint32_t dma_buf_stride;
>         EGLImageKHR image;
>         EGLint image_attrs[13];
>         GLuint tex;
>         int i;
>
> -       result = piglit_create_dma_buf(width, height, cpp, pixels, stride,
> -                                      &dma_buf, &dma_buf_fd,
> &dma_buf_stride,
> -                                      &dma_buf_offset);
> +       result = piglit_create_dma_buf(width, height, fourcc, pixels,
> &dma_buf);
>
>         if (result != PIGLIT_PASS) {
>                 piglit_loge("failed to create dma_buf");
> @@ -105,17 +101,17 @@ create_dma_buf_texture(uint32_t width, uint32_t
> height,
>
>         i = 0;
>         image_attrs[i++] = EGL_LINUX_DRM_FOURCC_EXT;
> -       image_attrs[i++] = drm_fourcc;
> +       image_attrs[i++] = fourcc;
>         image_attrs[i++] = EGL_WIDTH;
>         image_attrs[i++] = width;
>         image_attrs[i++] = EGL_HEIGHT;
>         image_attrs[i++] = height;
>         image_attrs[i++] = EGL_DMA_BUF_PLANE0_FD_EXT;
> -       image_attrs[i++] = dma_buf_fd;
> +       image_attrs[i++] = dma_buf->fd;
>         image_attrs[i++] = EGL_DMA_BUF_PLANE0_PITCH_EXT;
> -       image_attrs[i++] = dma_buf_stride;
> +       image_attrs[i++] = dma_buf->stride[0];
>         image_attrs[i++] = EGL_DMA_BUF_PLANE0_OFFSET_EXT;
> -       image_attrs[i++] = dma_buf_offset;
> +       image_attrs[i++] = dma_buf->offset[0];
>         image_attrs[i++] = EGL_NONE;
>
>
> @@ -191,12 +187,10 @@ create_textures(GLuint *r8_tex, GLuint *gr88_tex,
> float **ref_rgba_image)
>
>         glActiveTexture(GL_TEXTURE0);
>         *r8_tex = create_dma_buf_texture(width, height,
> -                                        /*cpp*/ 1, /*stride*/ width,
>                                          DRM_FORMAT_R8, r8_pixels);
>
>         glActiveTexture(GL_TEXTURE1);
>         *gr88_tex = create_dma_buf_texture(width / 2, height / 2,
> -                                          /*cpp*/ 2, /*stride*/ width,
>                                            DRM_FORMAT_GR88, gr88_pixels);
>  }
>
> diff --git a/tests/util/piglit-framework-gl.c
> b/tests/util/piglit-framework-gl.c
> index 9748ddf..1c25f2c 100644
> --- a/tests/util/piglit-framework-gl.c
> +++ b/tests/util/piglit-framework-gl.c
> @@ -265,22 +265,14 @@ piglit_set_reshape_func(void (*func)(int w, int h))
>                 gl_fw->set_reshape_func(gl_fw, func);
>  }
>
> -
>  enum piglit_result
> -piglit_create_dma_buf(unsigned w, unsigned h, unsigned cpp,
> -                     const void *src_data, unsigned src_stride,
> -                     struct piglit_dma_buf **buf, int *fd,
> -                     unsigned *stride, unsigned *offset)
> +piglit_create_dma_buf(unsigned w, unsigned h, unsigned fourcc,
> +                     const void *src_data, struct piglit_dma_buf **buf)
>  {
> -       *fd = 0;
> -       *stride = 0;
> -       *offset = 0;
> -
>         if (!gl_fw->create_dma_buf)
>                 return PIGLIT_SKIP;
>
> -       return gl_fw->create_dma_buf(w, h, cpp, src_data, src_stride, buf,
> fd,
> -                               stride, offset);
> +       return gl_fw->create_dma_buf(w, h, fourcc, src_data, buf);
>  }
>
>  void
> diff --git a/tests/util/piglit-framework-gl.h
> b/tests/util/piglit-framework-gl.h
> index 81c1a5e..ecf5b5c 100644
> --- a/tests/util/piglit-framework-gl.h
> +++ b/tests/util/piglit-framework-gl.h
> @@ -310,16 +310,22 @@ struct piglit_dma_buf;
>   * given data (src_data). Different hardware may have different alignment
>   * constraints and hence one can specify one stride for the source and get
>   * another for the final buffer to be given further to EGL.
> - * An opaque handle, file descriptor, stride and offset for the buffer
> are only
> - * returned upon success indicated by the return value PIGLIT_PASS,
> otherwise
> - * no buffer is created. In case the framework simply does not support dma
> - * buffers, the return value is PIGLIT_SKIP instead of PIGLIT_FAIL.
> + *
> + * The src stride is inferred from the width and the fourcc.  For planar
> + * YUV formats, for example, the U and V planes for YV12/YU12 have half
> the
> + * src_stride.
> + *
> + * The resulting per-plane stride and offset, which may be different than
> + * the src_stride due to hw constraints, are in the returned buf object.
> + *
> + * An buf handle is only returned upon success indicated by the return
> value
> + * PIGLIT_PASS, otherwise no buffer is created. In case the framework
> simply
> + * does not support dma buffers, the return value is PIGLIT_SKIP instead
> of
> + * PIGLIT_FAIL.
>   */
>  enum piglit_result
> -piglit_create_dma_buf(unsigned w, unsigned h, unsigned cpp,
> -                     const void *src_data, unsigned src_stride,
> -                     struct piglit_dma_buf **buf, int *fd,
> -                     unsigned *stride, unsigned *offset);
> +piglit_create_dma_buf(unsigned w, unsigned h, unsigned fourcc,
> +                     const void *src_data, struct piglit_dma_buf **buf);
>
>  /**
>   * Release all the resources allocated for the designated buffer. If the
> given
> diff --git a/tests/util/piglit-framework-gl/piglit_drm_dma_buf.c
> b/tests/util/piglit-framework-gl/piglit_drm_dma_buf.c
> index 3d1dc24..8e87b25 100644
> --- a/tests/util/piglit-framework-gl/piglit_drm_dma_buf.c
> +++ b/tests/util/piglit-framework-gl/piglit_drm_dma_buf.c
> @@ -23,6 +23,7 @@
>
>  #include "piglit-util-gl.h"
>  #include "piglit_drm_dma_buf.h"
> +#include "drm_fourcc.h"
>  #ifdef HAVE_LIBDRM_INTEL
>  #include <libdrm/intel_bufmgr.h>
>  #endif
> @@ -41,21 +42,13 @@
>
>  #define ALIGN(value, alignment) (((value) + alignment - 1) & ~(alignment
> - 1))
>
> -struct piglit_dma_buf {
> -       unsigned w;
> -       unsigned h;
> -       unsigned stride;
> -       int fd;
> -       void *priv;
> -};
> -
>  struct piglit_drm_driver {
>         int fd;
>         char *name;
>
>         bool
>         (*create)(unsigned w, unsigned h, unsigned cpp,
> -                 const unsigned char *src_data, unsigned src_stride,
> +                 const unsigned char *src_data,
>                   struct piglit_dma_buf *buf);
>
>         bool
> @@ -133,23 +126,55 @@ piglit_intel_bufmgr_get(void)
>  }
>
>  static bool
> -piglit_intel_buf_create(unsigned w, unsigned h, unsigned cpp,
> -                       const unsigned char *src_data, unsigned src_stride,
> -                       struct piglit_dma_buf *buf)
> +piglit_intel_buf_create(unsigned w, unsigned h, unsigned fourcc,
> +                       const unsigned char *src_data, struct
> piglit_dma_buf *buf)
>  {
>         unsigned i;
>         drm_intel_bo *bo;
> -       unsigned stride = ALIGN(w * cpp, 4);
>         drm_intel_bufmgr *mgr = piglit_intel_bufmgr_get();
> +       unsigned stride, src_stride, cpp;
> +       unsigned buf_h = h;
>
>         if (!mgr || h % 2)
>                 return false;
>
> -       bo = drm_intel_bo_alloc(mgr, "piglit_dma_buf", h * stride, 4096);
> +       switch (fourcc) {
> +       case DRM_FORMAT_R8:
> +               cpp = 1;
> +               break;
> +       case DRM_FORMAT_GR88:
> +       case DRM_FORMAT_RG88:
> +               cpp = 2;
> +               break;
> +       case DRM_FORMAT_XRGB8888:
> +       case DRM_FORMAT_XBGR8888:
> +       case DRM_FORMAT_RGBX8888:
> +       case DRM_FORMAT_BGRX8888:
> +       case DRM_FORMAT_ARGB8888:
> +       case DRM_FORMAT_ABGR8888:
> +       case DRM_FORMAT_RGBA8888:
> +       case DRM_FORMAT_BGRA8888:
> +               cpp = 4;
> +               break;
> +       case DRM_FORMAT_NV12:
> +       case DRM_FORMAT_YUV420:
> +       case DRM_FORMAT_YVU420:
> +               cpp = 1;
> +               buf_h = h * 3 / 2;
> +               break;
> +       default:
> +               fprintf(stderr, "invalid fourcc: %.4s\n", (char *)&fourcc);
> +               return false;
> +       }
> +
> +       src_stride = cpp * w;
> +       stride = ALIGN(w * cpp, 4);
> +
> +       bo = drm_intel_bo_alloc(mgr, "piglit_dma_buf", buf_h * stride,
> 4096);
>         if (!bo)
>                 return false;
>
> -       for (i = 0; i < h; ++i) {
> +       for (i = 0; i < buf_h; ++i) {
>                 if (drm_intel_bo_subdata(bo, i * stride, w * cpp,
>                         src_data + i * src_stride)) {
>                         drm_intel_bo_unreference(bo);
> @@ -159,10 +184,27 @@ piglit_intel_buf_create(unsigned w, unsigned h,
> unsigned cpp,
>
>         buf->w = w;
>         buf->h = h;
> -       buf->stride = stride;
> +       buf->offset[0] = 0;
> +       buf->stride[0] = stride;
>         buf->fd = 0;
>         buf->priv = bo;
>
> +       switch (fourcc) {
> +       case DRM_FORMAT_NV12:
> +               buf->offset[1] = stride * h;
> +               buf->stride[1] = stride;
> +               break;
> +       case DRM_FORMAT_YUV420:
> +       case DRM_FORMAT_YVU420:
> +               buf->offset[1] = stride * h;
> +               buf->stride[1] = stride / 2;
> +               buf->offset[2] = buf->offset[1] + (stride * h / 2 / 2);
> +               buf->stride[2] = stride / 2;
> +               break;
> +       default:
> +               break;
> +       }
> +
>         return true;
>  }
>
> @@ -201,9 +243,8 @@ piglit_gbm_get(void)
>  }
>
>  static bool
> -piglit_gbm_buf_create(unsigned w, unsigned h, unsigned cpp,
> -                       const unsigned char *src_data, unsigned src_stride,
> -                       struct piglit_dma_buf *buf)
> +piglit_gbm_buf_create(unsigned w, unsigned h, unsigned fourcc,
> +                       const unsigned char *src_data, struct
> piglit_dma_buf *buf)
>  {
>         unsigned i;
>         struct gbm_bo *bo;
> @@ -212,28 +253,73 @@ piglit_gbm_buf_create(unsigned w, unsigned h,
> unsigned cpp,
>         void *dst_data;
>         void *map_data = NULL;
>         enum gbm_bo_format format;
> +       unsigned cpp = 0, src_stride;
> +       unsigned buf_w = w;
> +       unsigned buf_h = h;
>
> -       if (!gbm || h % 2)
> +       if (!gbm || h % 2 || w % 2)
>                 return false;
>
> -       /* It would be nice if we took in a fourcc instead of a cpp */
> -       switch (cpp) {
> -       case 1:
> -               format = GBM_FORMAT_C8;
> +       switch (fourcc) {
> +       case DRM_FORMAT_R8:
> +               format = GBM_FORMAT_R8;
> +               cpp = 1;
> +               src_stride = cpp * w;
> +               break;
> +       case DRM_FORMAT_GR88:
> +       case DRM_FORMAT_RG88:
> +               format = GBM_FORMAT_GR88;
> +               cpp = 2;
> +               src_stride = cpp * w;
>                 break;
> -       case 4:
> +       case DRM_FORMAT_XRGB8888:
> +       case DRM_FORMAT_XBGR8888:
> +       case DRM_FORMAT_RGBX8888:
> +       case DRM_FORMAT_BGRX8888:
> +       case DRM_FORMAT_ARGB8888:
> +       case DRM_FORMAT_ABGR8888:
> +       case DRM_FORMAT_RGBA8888:
> +       case DRM_FORMAT_BGRA8888:
>                 format = GBM_BO_FORMAT_ARGB8888;
> +               cpp = 4;
> +               src_stride = cpp * w;
> +               break;
> +       /* For YUV formats, the U/V planes might have a greater relative
> +        * pitch.  For example, if the driver needs pitch aligned to 32
> +        * pixels, for a 4x4 YUV image, the stride of both the Y and U/V
> +        * planes will be 32 bytes.  Not 32 for Y and 16 for U/V.  To
> +        * account for this, use a 2cpp format with half the width.  For
> +        * hardware that only has stride requirements in bytes (rather
> +        * than pixels) this will work out the same.  For hardware that
> +        * has pitch alignment requirements in pixels, this will give an
> +        * overly conservative alignment for Y but a sufficient alignment
> +        * for U/V.
> +        */
> +       case DRM_FORMAT_NV12:
> +               format = GBM_FORMAT_GR88;
> +               buf_w = w / 2;
> +               buf_h = h * 3 / 2;
> +               src_stride = w;
> +               cpp = 1;
> +               break;
> +       case DRM_FORMAT_YUV420:
> +       case DRM_FORMAT_YVU420:
> +               format = GBM_FORMAT_GR88;
> +               buf_w = w / 2;
> +               buf_h = h * 2;    /* U/V not interleaved */
> +               src_stride = w;
> +               cpp = 1;
>                 break;
>         default:
> -               fprintf(stderr, "Unknown cpp %d\n", cpp);
> +               fprintf(stderr, "invalid fourcc: %.4s\n", (char *)&fourcc);
>                 return false;
>         }
>
> -       bo = gbm_bo_create(gbm, w, h, format, GBM_BO_USE_RENDERING);
> +       bo = gbm_bo_create(gbm, buf_w, buf_h, format,
> GBM_BO_USE_RENDERING);
>         if (!bo)
>                 return false;
>
> -       dst_data = gbm_bo_map(bo, 0, 0, w, h, GBM_BO_TRANSFER_WRITE,
> +       dst_data = gbm_bo_map(bo, 0, 0, buf_w, buf_h,
> GBM_BO_TRANSFER_WRITE,
>                               &dst_stride, &map_data);
>         if (!dst_data) {
>                 fprintf(stderr, "Failed to map GBM bo\n");
> @@ -241,18 +327,49 @@ piglit_gbm_buf_create(unsigned w, unsigned h,
> unsigned cpp,
>                 return NULL;
>         }
>
> +       buf->w = w;
> +       buf->h = h;
> +       buf->offset[0] = 0;
> +       buf->stride[0] = dst_stride;
> +       buf->fd = -1;
> +       buf->priv = bo;
> +
>         for (i = 0; i < h; ++i) {
>                 memcpy((char *)dst_data + i * dst_stride,
>                        src_data + i * src_stride,
>                        w * cpp);
>         }
> +
> +       switch (fourcc) {
> +       case DRM_FORMAT_NV12:
> +               buf->offset[1] = dst_stride * h;
> +               buf->stride[1] = dst_stride;
> +               for (i = 0; i < h/2; ++i) {
> +                       memcpy(((char *)dst_data + buf->offset[1]) + i *
> buf->stride[1],
> +                               (src_data + (w*h)) + i * src_stride, w);
> +               }
> +               break;
> +       case DRM_FORMAT_YUV420:
> +       case DRM_FORMAT_YVU420:
> +               buf->offset[1] = dst_stride * h;
> +               buf->stride[1] = dst_stride / 2;
> +               for (i = 0; i < h/2; ++i) {
> +                       memcpy(((char *)dst_data + buf->offset[1]) + i *
> buf->stride[1],
> +                               (src_data + (w*h)) + i * src_stride / 2, w
> / 2);
> +               }
> +               buf->offset[2] = buf->offset[1] + (dst_stride * h / 2 / 2);
> +               buf->stride[2] = dst_stride / 2;
> +               for (i = 0; i < h/2; ++i) {
> +                       memcpy(((char *)dst_data + buf->offset[2]) + i *
> buf->stride[2],
> +                               (src_data + (w*h) + (w*h/4)) + i *
> src_stride / 2, w / 2);
> +               }
> +               break;
> +       default:
> +               break;
> +       }
> +
>         gbm_bo_unmap(bo, map_data);
>
> -       buf->w = w;
> -       buf->h = h;
> -       buf->stride = dst_stride;
> -       buf->fd = 0;
> -       buf->priv = bo;
>
>         return true;
>  }
> @@ -290,7 +407,7 @@ piglit_drm_get_driver(void)
>         if (drv.fd == -1) {
>                 drv.fd = open("/dev/dri/card0", O_RDWR);
>                 if (drv.fd == -1) {
> -                       fprintf(stderr, "error: failed to open
> /dev/dri/renderD128 and "
> +                       fprintf(stderr, "error: failed to open
> /dev/dri/renderD128 or "
>                                 "/dev/dri/card0\n");
>                         goto fail;
>
> @@ -352,10 +469,8 @@ piglit_drm_get_driver(void)
>  }
>
>  enum piglit_result
> -piglit_drm_create_dma_buf(unsigned w, unsigned h, unsigned cpp,
> -                       const void *src_data, unsigned src_stride,
> -                       struct piglit_dma_buf **buf, int *fd,
> -                       unsigned *stride, unsigned *offset)
> +piglit_drm_create_dma_buf(unsigned w, unsigned h, unsigned fourcc,
> +                       const void *src_data,  struct piglit_dma_buf **buf)
>  {
>         struct piglit_dma_buf *drm_buf;
>         const struct piglit_drm_driver *drv = piglit_drm_get_driver();
> @@ -367,7 +482,7 @@ piglit_drm_create_dma_buf(unsigned w, unsigned h,
> unsigned cpp,
>         if (!drm_buf)
>                 return PIGLIT_FAIL;
>
> -       if (!drv->create(w, h, cpp, src_data, src_stride, drm_buf)) {
> +       if (!drv->create(w, h, fourcc, src_data, drm_buf)) {
>                 free(drm_buf);
>                 return PIGLIT_FAIL;
>         }
> @@ -378,9 +493,6 @@ piglit_drm_create_dma_buf(unsigned w, unsigned h,
> unsigned cpp,
>         }
>
>         *buf = drm_buf;
> -       *fd = drm_buf->fd;
> -       *stride = drm_buf->stride;
> -       *offset = 0;
>
>         return PIGLIT_PASS;
>  }
> diff --git a/tests/util/piglit-framework-gl/piglit_drm_dma_buf.h
> b/tests/util/piglit-framework-gl/piglit_drm_dma_buf.h
> index 2c72eca..5872df9 100644
> --- a/tests/util/piglit-framework-gl/piglit_drm_dma_buf.h
> +++ b/tests/util/piglit-framework-gl/piglit_drm_dma_buf.h
> @@ -23,13 +23,18 @@
>  #ifndef PIGLIT_DRM_DMA_BUF_H
>  #define PIGLIT_DRM_DMA_BUF_H
>
> -struct piglit_dma_buf;
> +struct piglit_dma_buf {
> +       unsigned w;
> +       unsigned h;
> +       unsigned offset[3];
> +       unsigned stride[3];
> +       int fd;
> +       void *priv;
> +};
>
>  enum piglit_result
> -piglit_drm_create_dma_buf(unsigned w, unsigned h, unsigned cpp,
> -                         const void *src_data, unsigned src_stride,
> -                         struct piglit_dma_buf **buf, int *fd,
> -                         unsigned *stride, unsigned *offset);
> +piglit_drm_create_dma_buf(unsigned w, unsigned h, unsigned fourcc,
> +                       const void *src_data,  struct piglit_dma_buf
> **buf);
>
>  void
>  piglit_drm_destroy_dma_buf(struct piglit_dma_buf *buf);
> diff --git a/tests/util/piglit-framework-gl/piglit_gl_framework.h
> b/tests/util/piglit-framework-gl/piglit_gl_framework.h
> index 97fecca..aad565e 100644
> --- a/tests/util/piglit-framework-gl/piglit_gl_framework.h
> +++ b/tests/util/piglit-framework-gl/piglit_gl_framework.h
> @@ -73,10 +73,8 @@ struct piglit_gl_framework {
>         (*destroy)(struct piglit_gl_framework *gl_fw);
>
>         enum piglit_result
> -       (*create_dma_buf)(unsigned w, unsigned h, unsigned cpp,
> -                         const void *src_data, unsigned src_stride,
> -                         struct piglit_dma_buf **buf, int *fd,
> -                         unsigned *stride, unsigned *offset);
> +       (*create_dma_buf)(unsigned w, unsigned h, unsigned fourcc,
> +                         const void *src_data, struct piglit_dma_buf
> **buf);
>
>         void
>         (*destroy_dma_buf)(struct piglit_dma_buf *buf);
> --
> 2.7.4
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.freedesktop.org/archives/piglit/attachments/20160909/26f50998/attachment-0001.html>


More information about the Piglit mailing list