<div dir="ltr"><div class="gmail_quote"><div dir="ltr">On Fri, Sep 9, 2016 at 10:44 AM Rob Clark <<a href="mailto:robdclark@gmail.com">robdclark@gmail.com</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Ok, so the basic problem with the YUV tests is that they currently<br>
completely ignore driver/hw pitch requirements, since the code that<br>
allocates the buffer doesn't know the pixel format, only the 'cpp'.<br>
<br>
The yuv test creates a small 4x4 yuv eglimage.  If, say, the hardware<br>
requires the pitch to be aligned to, say, 32pixels, everything is fine<br>
for the Y plane, but the subsampled U/V or U+V plane has half as many<br>
pixels.  (This did help me catch a bug in driver, not rejecting the<br>
dmabuf import with invalid pitch, but that doesn't help to get the<br>
piglit tests running.)<br>
<br>
The best approach I could come up with to fix this is to pass the<br>
fourcc all the way down to the code that creates the dmabuf (and copies<br>
src data into the dmabuf).  Unfortunately this makes the patch a bit<br>
bigger than I was hoping, and not really sure a good way to split it<br>
up.<br>
<br>
This is tested on i965 (with the intel dma-buf backend) and freedreno<br>
(with the gbm dma-buf backend).  In the gbm case, it requires new<br>
gbm format values for R8 and GR88, which is on mesa master as of<br>
this morning.  (So I bumped the gbm version dependency to 12.1.)<br>
<br>
Signed-off-by: Rob Clark <<a href="mailto:robdclark@gmail.com" target="_blank">robdclark@gmail.com</a>><br>
</blockquote><div><br></div><div>Few nitpicks below, but looks good:</div><div><br></div><div>Reviewed-by: Kristian Høgsberg <<a href="mailto:krh@bitplanet.net">krh@bitplanet.net</a>></div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">---<br>
v2: drop unneeded src_stride arg<br>
<br>
 CMakeLists.txt                                     |   2 +-<br>
 .../intel_external_sampler_only.c                  |  11 +-<br>
 .../intel_unsupported_format.c                     |  19 +-<br>
 .../ext_image_dma_buf_import/invalid_attributes.c  |  43 +++--<br>
 .../spec/ext_image_dma_buf_import/invalid_hints.c  |  23 ++-<br>
 .../ext_image_dma_buf_import/missing_attributes.c  |  25 ++-<br>
 .../ext_image_dma_buf_import/ownership_transfer.c  |  11 +-<br>
 tests/spec/ext_image_dma_buf_import/refcount.c     |  15 +-<br>
 .../spec/ext_image_dma_buf_import/sample_common.c  |  73 +++-----<br>
 .../spec/ext_image_dma_buf_import/sample_common.h  |   5 +-<br>
 tests/spec/ext_image_dma_buf_import/sample_rgb.c   |   2 +-<br>
 tests/spec/ext_image_dma_buf_import/sample_yuv.c   |  26 ++-<br>
 .../transcode-nv12-as-r8-gr88.c                    |  24 +--<br>
 tests/util/piglit-framework-gl.c                   |  14 +-<br>
 tests/util/piglit-framework-gl.h                   |  22 ++-<br>
 .../util/piglit-framework-gl/piglit_drm_dma_buf.c  | 196 ++++++++++++++++-----<br>
 .../util/piglit-framework-gl/piglit_drm_dma_buf.h  |  15 +-<br>
 .../util/piglit-framework-gl/piglit_gl_framework.h |   6 +-<br>
 18 files changed, 314 insertions(+), 218 deletions(-)<br>
<br>
diff --git a/CMakeLists.txt b/CMakeLists.txt<br>
index 536f775..4e4b5ae 100644<br>
--- a/CMakeLists.txt<br>
+++ b/CMakeLists.txt<br>
@@ -141,7 +141,7 @@ IF(${CMAKE_SYSTEM_NAME} MATCHES "Linux")<br>
        if(GBM_FOUND)<br>
                set(PIGLIT_HAS_GBM True)<br>
                add_definitions(-DPIGLIT_HAS_GBM)<br>
-               if (GBM_VERSION VERSION_EQUAL "12.0" OR GBM_VERSION VERSION_GREATER "12.0")<br>
+               if (GBM_VERSION VERSION_EQUAL "12.1" OR GBM_VERSION VERSION_GREATER "12.1")<br>
                        set(PIGLIT_HAS_GBM_BO_MAP True)<br>
                        add_definitions(-DPIGLIT_HAS_GBM_BO_MAP)<br>
                endif()<br>
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<br>
index 7743a68..de1074c 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/intel_external_sampler_only.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/intel_external_sampler_only.c<br>
@@ -21,6 +21,8 @@<br>
  * IN THE SOFTWARE.<br>
  */<br>
<br>
+#include "piglit-framework-gl/piglit_drm_dma_buf.h"<br>
+<br>
 #include "image_common.h"<br>
<br>
 /**<br>
@@ -98,21 +100,18 @@ piglit_display(void)<br>
        const unsigned w = 2;<br>
        const unsigned h = 2;<br>
        const unsigned cpp = 4;<br>
+       const unsigned fourcc = DRM_FORMAT_ARGB8888;<br>
        const unsigned char *pixels = alloca(w * h * cpp);<br>
        struct piglit_dma_buf *buf;<br>
-       unsigned stride;<br>
-       unsigned offset;<br>
-       int fd;<br>
        EGLImageKHR img;<br>
        enum piglit_result res;<br>
        bool pass = true;<br>
<br>
-       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,<br>
-                               &buf, &fd, &stride, &offset);<br>
+       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
-       img = create_image(w, h, fd, stride, offset);<br>
+       img = create_image(w, h, buf->fd, buf->stride[0], buf->offset[0]);<br>
<br>
        if (!img) {<br>
                piglit_destroy_dma_buf(buf);<br>
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<br>
index 69bb267..8373e90 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/intel_unsupported_format.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/intel_unsupported_format.c<br>
@@ -21,6 +21,8 @@<br>
  * IN THE SOFTWARE.<br>
  */<br>
<br>
+#include "piglit-framework-gl/piglit_drm_dma_buf.h"<br>
+<br>
 #include "image_common.h"<br>
<br>
 /**<br>
@@ -62,20 +64,17 @@ piglit_display(void)<br>
        const unsigned w = 2;<br>
        const unsigned h = 2;<br>
        const unsigned cpp = 4;<br>
+       const unsigned fourcc = DRM_FORMAT_ARGB8888;<br>
        const unsigned char *pixels = alloca(w * h * cpp);<br>
        struct piglit_dma_buf *buf;<br>
-       unsigned stride;<br>
-       unsigned offset;<br>
-       int fd;<br>
        EGLImageKHR img;<br>
        enum piglit_result res;<br>
<br>
-       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,<br>
-                               &buf, &fd, &stride, &offset);<br>
+       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
-       img = create_image(w, h, fd, stride, offset);<br>
+       img = create_image(w, h, buf->fd, buf->stride[0], buf->offset[0]);<br>
<br>
        if (!piglit_check_egl_error(EGL_BAD_MATCH)) {<br>
                if (img)<br>
@@ -83,14 +82,16 @@ piglit_display(void)<br>
                return PIGLIT_FAIL;<br>
        }<br>
<br>
-       piglit_destroy_dma_buf(buf);<br>
-<br>
        /**<br>
         * EGL stack can claim the ownership of the file descriptor only when it<br>
         * succeeds. Close the descriptor and check that it really wasn't closed<br>
         * by EGL.<br>
         */<br>
-       return close(fd) == 0 ? PIGLIT_PASS : PIGLIT_FAIL;<br>
+       res = close(buf->fd) == 0 ? PIGLIT_PASS : PIGLIT_FAIL;<br>
+<br>
+       piglit_destroy_dma_buf(buf);<br>
+<br>
+       return res;<br>
 }<br>
<br>
 void<br>
diff --git a/tests/spec/ext_image_dma_buf_import/invalid_attributes.c b/tests/spec/ext_image_dma_buf_import/invalid_attributes.c<br>
index b77e47b..cc0b046 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/invalid_attributes.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/invalid_attributes.c<br>
@@ -21,6 +21,8 @@<br>
  * IN THE SOFTWARE.<br>
  */<br>
<br>
+#include "piglit-framework-gl/piglit_drm_dma_buf.h"<br>
+<br>
 #include "image_common.h"<br>
<br>
 /**<br>
@@ -209,44 +211,41 @@ piglit_display(void)<br>
        const unsigned w = 2;<br>
        const unsigned h = 2;<br>
        const unsigned cpp = 4;<br>
+       const unsigned fourcc = DRM_FORMAT_ARGB8888;<br>
        const unsigned char *pixels = alloca(w * h * cpp);<br>
        struct piglit_dma_buf *buf;<br>
-       unsigned stride;<br>
-       unsigned offset;<br>
-       int fd;<br>
        enum piglit_result res;<br>
        bool pass = true;<br>
<br>
-       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,<br>
-                               &buf, &fd, &stride, &offset);<br>
+       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
-       pass = test_excess_attributes(w, h, fd, stride, offset,<br>
-                               EGL_DMA_BUF_PLANE1_FD_EXT, fd) && pass;<br>
-       pass = test_excess_attributes(w, h, fd, stride, offset,<br>
+       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0], buf->offset[0],<br>
+                               EGL_DMA_BUF_PLANE1_FD_EXT, buf->fd) && pass;<br>
+       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0], buf->offset[0],<br>
                                EGL_DMA_BUF_PLANE1_OFFSET_EXT, 0) && pass;<br>
-       pass = test_excess_attributes(w, h, fd, stride, offset,<br>
-                               EGL_DMA_BUF_PLANE1_PITCH_EXT, stride) && pass;<br>
-       pass = test_excess_attributes(w, h, fd, stride, offset,<br>
-                               EGL_DMA_BUF_PLANE2_FD_EXT, fd) && pass;<br>
-       pass = test_excess_attributes(w, h, fd, stride, offset,<br>
+       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0], buf->offset[0],<br>
+                               EGL_DMA_BUF_PLANE1_PITCH_EXT, buf->stride[0]) && pass;<br>
+       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0], buf->offset[0],<br>
+                               EGL_DMA_BUF_PLANE2_FD_EXT, buf->fd) && pass;<br>
+       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0], buf->offset[0],<br>
                                EGL_DMA_BUF_PLANE2_OFFSET_EXT, 0) && pass;<br>
-       pass = test_excess_attributes(w, h, fd, stride, offset,<br>
-                               EGL_DMA_BUF_PLANE2_PITCH_EXT, stride) && pass;<br>
-       pass = test_buffer_not_null(w, h, fd, stride, offset) && pass;<br>
-       pass = test_invalid_context(w, h, fd, stride, offset) && pass;<br>
-       pass = test_invalid_format(w, h, fd, stride, offset) && pass;<br>
-       pass = test_pitch_zero(w, h, fd, stride, offset) && pass;<br>
-<br>
-       piglit_destroy_dma_buf(buf);<br>
+       pass = test_excess_attributes(w, h, buf->fd, buf->stride[0], buf->offset[0],<br>
+                               EGL_DMA_BUF_PLANE2_PITCH_EXT, buf->stride[0]) && pass;<br>
+       pass = test_buffer_not_null(w, h, buf->fd, buf->stride[0], buf->offset[0]) && pass;<br>
+       pass = test_invalid_context(w, h, buf->fd, buf->stride[0], buf->offset[0]) && pass;<br>
+       pass = test_invalid_format(w, h, buf->fd, buf->stride[0], buf->offset[0]) && pass;<br>
+       pass = test_pitch_zero(w, h, buf->fd, buf->stride[0], buf->offset[0]) && pass;<br>
<br>
        /**<br>
         * EGL stack can claim the ownership of the file descriptor only when it<br>
         * succeeds. Close the file descriptor here and check that it really<br>
         * wasn't closed by EGL.<br>
         */<br>
-       pass = (close(fd) == 0) && pass;<br>
+       pass = (close(buf->fd) == 0) && pass;<br>
+<br>
+       piglit_destroy_dma_buf(buf);<br>
<br>
        return pass ? PIGLIT_PASS : PIGLIT_FAIL;<br>
 }<br>
diff --git a/tests/spec/ext_image_dma_buf_import/invalid_hints.c b/tests/spec/ext_image_dma_buf_import/invalid_hints.c<br>
index fa006f0..c2b43a2 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/invalid_hints.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/invalid_hints.c<br>
@@ -21,6 +21,8 @@<br>
  * IN THE SOFTWARE.<br>
  */<br>
<br>
+#include "piglit-framework-gl/piglit_drm_dma_buf.h"<br>
+<br>
 #include "image_common.h"<br>
<br>
 /**<br>
@@ -97,36 +99,33 @@ piglit_display(void)<br>
        const unsigned w = 2;<br>
        const unsigned h = 2;<br>
        const unsigned cpp = 4;<br>
+       const unsigned fourcc = DRM_FORMAT_ARGB8888;<br>
        const unsigned char *pixels = alloca(w * h * cpp);<br>
        struct piglit_dma_buf *buf;<br>
-       unsigned stride;<br>
-       unsigned offset;<br>
-       int fd;<br>
        enum piglit_result res;<br>
        bool pass = true;<br>
<br>
-       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,<br>
-                               &buf, &fd, &stride, &offset);<br>
+       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
-       pass = test_invalid_hint(w, h, fd, stride, offset,<br>
+       pass = test_invalid_hint(w, h, buf->fd, buf->stride[0], buf->offset[0],<br>
                        EGL_YUV_COLOR_SPACE_HINT_EXT, 0) && pass;<br>
-       pass = test_invalid_hint(w, h, fd, stride, offset,<br>
+       pass = test_invalid_hint(w, h, buf->fd, buf->stride[0], buf->offset[0],<br>
                        EGL_SAMPLE_RANGE_HINT_EXT, 0) && pass;<br>
-       pass = test_invalid_hint(w, h, fd, stride, offset,<br>
+       pass = test_invalid_hint(w, h, buf->fd, buf->stride[0], buf->offset[0],<br>
                        EGL_YUV_CHROMA_HORIZONTAL_SITING_HINT_EXT, 0) && pass;<br>
-       pass = test_invalid_hint(w, h, fd, stride, offset,<br>
+       pass = test_invalid_hint(w, h, buf->fd, buf->stride[0], buf->offset[0],<br>
                        EGL_YUV_CHROMA_VERTICAL_SITING_HINT_EXT, 0) && pass;<br>
<br>
-       piglit_destroy_dma_buf(buf);<br>
-<br>
        /**<br>
         * EGL stack can claim the ownership of the file descriptor only when it<br>
         * succeeds. Close the descriptor and check that it really wasn't closed<br>
         * by EGL.<br>
         */<br>
-       pass = (close(fd) == 0) && pass;<br>
+       pass = (close(buf->fd) == 0) && pass;<br>
+<br>
+       piglit_destroy_dma_buf(buf);<br>
<br>
        return pass ? PIGLIT_PASS : PIGLIT_FAIL;<br>
 }<br>
diff --git a/tests/spec/ext_image_dma_buf_import/missing_attributes.c b/tests/spec/ext_image_dma_buf_import/missing_attributes.c<br>
index d7d89e6..d16b60e 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/missing_attributes.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/missing_attributes.c<br>
@@ -21,6 +21,8 @@<br>
  * IN THE SOFTWARE.<br>
  */<br>
<br>
+#include "piglit-framework-gl/piglit_drm_dma_buf.h"<br>
+<br>
 #include "image_common.h"<br>
<br>
 /**<br>
@@ -105,47 +107,44 @@ piglit_display(void)<br>
        const unsigned w = 2;<br>
        const unsigned h = 2;<br>
        const unsigned cpp = 2;<br></blockquote><div><br></div><div>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.</div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
+       const unsigned fourcc = DRM_FORMAT_ARGB8888;<br>
        const unsigned char *pixels = alloca(w * h * cpp);<br>
        EGLint all[2 * NUM_MANDATORY_ATTRS];<br>
        EGLint missing[2 * (NUM_MANDATORY_ATTRS - 1) + 1];<br>
        struct piglit_dma_buf *buf;<br>
-       unsigned stride;<br>
-       unsigned offset;<br>
-       int fd;<br>
        enum piglit_result res;<br>
        bool pass = true;<br>
<br>
-       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,<br>
-                               &buf, &fd, &stride, &offset);<br>
+       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
-       fill_full_set(w, h, fd, offset, stride, all);<br>
+       fill_full_set(w, h, buf->fd, buf->offset[0], buf->stride[0], all);<br>
<br>
        fill_one_missing(all, missing, EGL_HEIGHT);<br>
-       pass = test_missing(fd, missing) && pass;<br>
+       pass = test_missing(buf->fd, missing) && pass;<br>
<br>
        fill_one_missing(all, missing, EGL_WIDTH);<br>
-       pass = test_missing(fd, missing) && pass;<br>
+       pass = test_missing(buf->fd, missing) && pass;<br>
<br>
        fill_one_missing(all, missing, EGL_LINUX_DRM_FOURCC_EXT);<br>
-       pass = test_missing(fd, missing) && pass;<br>
+       pass = test_missing(buf->fd, missing) && pass;<br>
<br>
        fill_one_missing(all, missing, EGL_DMA_BUF_PLANE0_FD_EXT);<br>
-       pass = test_missing(fd, missing) && pass;<br>
+       pass = test_missing(buf->fd, missing) && pass;<br>
<br>
        fill_one_missing(all, missing, EGL_DMA_BUF_PLANE0_OFFSET_EXT);<br>
-       pass = test_missing(fd, missing) && pass;<br>
+       pass = test_missing(buf->fd, missing) && pass;<br>
<br>
        fill_one_missing(all, missing, EGL_DMA_BUF_PLANE0_PITCH_EXT);<br>
-       pass = test_missing(fd, missing) && pass;<br>
+       pass = test_missing(buf->fd, missing) && pass;<br>
<br>
        /**<br>
         * EGL stack can claim the ownership of the file descriptor only when it<br>
         * succeeds. Close the file descriptor here and check that it really<br>
         * wasn't closed by EGL.<br>
         */<br>
-       pass = (close(fd) == 0) && pass;<br>
+       pass = (close(buf->fd) == 0) && pass;<br>
<br>
        piglit_destroy_dma_buf(buf);<br>
<br>
diff --git a/tests/spec/ext_image_dma_buf_import/ownership_transfer.c b/tests/spec/ext_image_dma_buf_import/ownership_transfer.c<br>
index 2da455b..be5a044 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/ownership_transfer.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/ownership_transfer.c<br>
@@ -23,6 +23,8 @@<br>
<br>
 #include <errno.h><br>
<br>
+#include "piglit-framework-gl/piglit_drm_dma_buf.h"<br>
+<br>
 #include "image_common.h"<br>
<br>
 /**<br>
@@ -113,19 +115,16 @@ piglit_display(void)<br>
        const unsigned w = 2;<br>
        const unsigned h = 2;<br>
        const unsigned cpp = 4;<br>
+       const unsigned fourcc = fourcc_code('A', 'R', '2', '4');;<br></blockquote><div><br></div><div>Why the custom fourcc? And two semicolons.</div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
        const unsigned char *pixels = alloca(w * h * cpp);<br>
        struct piglit_dma_buf *buf;<br>
-       unsigned stride;<br>
-       unsigned offset;<br>
-       int fd;<br>
        enum piglit_result res;<br>
<br>
-       res = piglit_create_dma_buf(w, h, cpp, pixels, w * cpp,<br>
-                               &buf, &fd, &stride, &offset);<br>
+       res = piglit_create_dma_buf(w, h, fourcc, pixels, &buf);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
-       return test_create_and_destroy(w, h, buf, fd, stride, offset);<br>
+       return test_create_and_destroy(w, h, buf, buf->fd, buf->stride[0], buf->offset[0]);<br>
 }<br>
<br>
 void<br>
diff --git a/tests/spec/ext_image_dma_buf_import/refcount.c b/tests/spec/ext_image_dma_buf_import/refcount.c<br>
index 5b14cdd..bc15ff5 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/refcount.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/refcount.c<br>
@@ -21,6 +21,8 @@<br>
  * IN THE SOFTWARE.<br>
  */<br>
<br>
+#include "piglit-framework-gl/piglit_drm_dma_buf.h"<br>
+<br>
 #include "sample_common.h"<br>
 #include "image_common.h"<br>
<br>
@@ -57,8 +59,6 @@ piglit_display(void)<br>
        int cpp = 4;<br>
        enum piglit_result res;<br>
        struct piglit_dma_buf *buf;<br>
-       unsigned stride, offset;<br>
-       int fd;<br>
        EGLImageKHR img1, img2;<br>
        GLuint tex1, tex2;<br>
        /* Scale up factor for drawing the texture to the screen. */<br>
@@ -67,22 +67,19 @@ piglit_display(void)<br>
        int i;<br>
        GLubyte *expected;<br>
<br>
-       res = piglit_create_dma_buf(w, h, cpp, src, w * cpp,<br>
-                                   &buf, &fd, &stride, &offset);<br>
+       res = piglit_create_dma_buf(w, h, fourcc, src, &buf);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
-       res = egl_image_for_dma_buf_fd(dup(fd), fourcc, w, h, stride, offset,<br>
-                                      &img1);<br>
+       res = egl_image_for_dma_buf_fd(buf, dup(buf->fd), fourcc, &img1);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
-       res = egl_image_for_dma_buf_fd(dup(fd), fourcc, w, h, stride, offset,<br>
-                                      &img2);<br>
+       res = egl_image_for_dma_buf_fd(buf, dup(buf->fd), fourcc, &img2);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
-       close(fd);<br>
+       close(buf->fd);<br>
<br>
        res = texture_for_egl_image(img1, &tex1);<br>
        if (res != PIGLIT_PASS)<br>
diff --git a/tests/spec/ext_image_dma_buf_import/sample_common.c b/tests/spec/ext_image_dma_buf_import/sample_common.c<br>
index c5aa1e1..2f586c7 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/sample_common.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/sample_common.c<br>
@@ -23,6 +23,8 @@<br>
<br>
 #include <unistd.h><br>
<br>
+#include "piglit-framework-gl/piglit_drm_dma_buf.h"<br>
+<br>
 #include "image_common.h"<br>
 #include "sample_common.h"<br>
<br>
@@ -105,47 +107,46 @@ sample_tex(GLuint tex, unsigned x, unsigned y, unsigned w, unsigned h)<br>
 }<br>
<br>
 enum piglit_result<br>
-egl_image_for_dma_buf_fd(int fd, int fourcc, int w, int h,<br>
-                        unsigned stride, unsigned offset, EGLImageKHR *out_img)<br>
+egl_image_for_dma_buf_fd(struct piglit_dma_buf *buf, int fd, int fourcc, EGLImageKHR *out_img)<br>
 {<br>
        EGLint error;<br>
        EGLImageKHR img;<br>
        EGLint attr_packed[] = {<br>
-               EGL_WIDTH, w,<br>
-               EGL_HEIGHT, h,<br>
+               EGL_WIDTH, buf->w,<br>
+               EGL_HEIGHT, buf->h,<br>
                EGL_LINUX_DRM_FOURCC_EXT, fourcc,<br>
                EGL_DMA_BUF_PLANE0_FD_EXT, fd,<br>
-               EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,<br>
-               EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,<br>
+               EGL_DMA_BUF_PLANE0_OFFSET_EXT, buf->offset[0],<br>
+               EGL_DMA_BUF_PLANE0_PITCH_EXT, buf->stride[0],<br>
                EGL_NONE<br>
        };<br>
<br>
        EGLint attr_nv12[] = {<br>
-               EGL_WIDTH, w,<br>
-               EGL_HEIGHT, h,<br>
+               EGL_WIDTH, buf->w,<br>
+               EGL_HEIGHT, buf->h,<br>
                EGL_LINUX_DRM_FOURCC_EXT, fourcc,<br>
                EGL_DMA_BUF_PLANE0_FD_EXT, fd,<br>
-               EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,<br>
-               EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,<br>
+               EGL_DMA_BUF_PLANE0_OFFSET_EXT, buf->offset[0],<br>
+               EGL_DMA_BUF_PLANE0_PITCH_EXT, buf->stride[0],<br>
                EGL_DMA_BUF_PLANE1_FD_EXT, fd,<br>
-               EGL_DMA_BUF_PLANE1_OFFSET_EXT, offset + h * stride,<br>
-               EGL_DMA_BUF_PLANE1_PITCH_EXT, stride,<br>
+               EGL_DMA_BUF_PLANE1_OFFSET_EXT, buf->offset[1],<br>
+               EGL_DMA_BUF_PLANE1_PITCH_EXT, buf->stride[1],<br>
                EGL_NONE<br>
        };<br>
<br>
        EGLint attr_yuv420[] = {<br>
-               EGL_WIDTH, w,<br>
-               EGL_HEIGHT, h,<br>
+               EGL_WIDTH, buf->w,<br>
+               EGL_HEIGHT, buf->h,<br>
                EGL_LINUX_DRM_FOURCC_EXT, fourcc,<br>
                EGL_DMA_BUF_PLANE0_FD_EXT, fd,<br>
-               EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,<br>
-               EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,<br>
+               EGL_DMA_BUF_PLANE0_OFFSET_EXT, buf->offset[0],<br>
+               EGL_DMA_BUF_PLANE0_PITCH_EXT, buf->stride[0],<br>
                EGL_DMA_BUF_PLANE1_FD_EXT, fd,<br>
-               EGL_DMA_BUF_PLANE1_OFFSET_EXT, offset + h * stride,<br>
-               EGL_DMA_BUF_PLANE1_PITCH_EXT, stride,<br>
+               EGL_DMA_BUF_PLANE1_OFFSET_EXT, buf->offset[1],<br>
+               EGL_DMA_BUF_PLANE1_PITCH_EXT, buf->stride[1],<br>
                EGL_DMA_BUF_PLANE2_FD_EXT, fd,<br>
-               EGL_DMA_BUF_PLANE2_OFFSET_EXT, offset + h * stride + w / 2,<br>
-               EGL_DMA_BUF_PLANE2_PITCH_EXT, stride,<br>
+               EGL_DMA_BUF_PLANE2_OFFSET_EXT, buf->offset[2],<br>
+               EGL_DMA_BUF_PLANE2_PITCH_EXT, buf->stride[2],<br>
                EGL_NONE<br>
        };<br>
<br>
@@ -191,21 +192,22 @@ egl_image_for_dma_buf_fd(int fd, int fourcc, int w, int h,<br>
 }<br>
<br>
 static enum piglit_result<br>
-sample_buffer(void *buf, int fd, int fourcc, unsigned w, unsigned h,<br>
-             unsigned stride, unsigned offset)<br>
+sample_buffer(struct piglit_dma_buf *buf, int fourcc)<br>
 {<br>
        enum piglit_result res;<br>
        EGLImageKHR img;<br>
        GLuint tex;<br>
+       int w = buf->w;<br>
+       int h = buf->h;<br>
<br>
-       res = egl_image_for_dma_buf_fd(fd, fourcc, w, h, stride, offset, &img);<br>
+       res = egl_image_for_dma_buf_fd(buf, buf->fd, fourcc, &img);<br>
<br>
        /* Release the creator side of the buffer. */<br>
        piglit_destroy_dma_buf(buf);<br>
<br>
        if (!img) {<br>
                /* Close the descriptor also, EGL does not have ownership */<br>
-               close(fd);<br>
+               close(buf->fd);<br>
        }<br>
<br>
        if (res != PIGLIT_PASS)<br>
@@ -225,32 +227,15 @@ destroy:<br>
 }<br>
<br>
 enum piglit_result<br>
-dma_buf_create_and_sample_32bpp(unsigned w, unsigned h, unsigned cpp,<br>
+dma_buf_create_and_sample_32bpp(unsigned w, unsigned h,<br>
                                int fourcc, const unsigned char *src)<br>
 {<br>
        struct piglit_dma_buf *buf;<br>
-       unsigned stride, offset;<br>
-       int fd;<br>
        enum piglit_result res;<br>
<br>
-       unsigned buffer_height;<br>
-<br>
-       switch (fourcc) {<br>
-       case DRM_FORMAT_NV12:<br>
-       case DRM_FORMAT_YUV420:<br>
-       case DRM_FORMAT_YVU420:<br>
-               buffer_height = h * 3 / 2;<br>
-               break;<br>
-       default:<br>
-               buffer_height = h;<br>
-               break;<br>
-       }<br>
-<br>
-       res = piglit_create_dma_buf(w, buffer_height,<br>
-                                   cpp, src, w * cpp, &buf, &fd, &stride,<br>
-                                   &offset);<br>
+       res = piglit_create_dma_buf(w, h, fourcc, src, &buf);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
-       return sample_buffer(buf, fd, fourcc, w, h, stride, offset);<br>
+       return sample_buffer(buf, fourcc);<br>
 }<br>
diff --git a/tests/spec/ext_image_dma_buf_import/sample_common.h b/tests/spec/ext_image_dma_buf_import/sample_common.h<br>
index db2ff82..36a5bb5 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/sample_common.h<br>
+++ b/tests/spec/ext_image_dma_buf_import/sample_common.h<br>
@@ -32,12 +32,11 @@<br>
  * sample it using a shader program.<br>
  */<br>
 enum piglit_result<br>
-dma_buf_create_and_sample_32bpp(unsigned w, unsigned h, unsigned cpp,<br>
+dma_buf_create_and_sample_32bpp(unsigned w, unsigned h,<br>
                                int fourcc, const unsigned char *src);<br>
<br>
 enum piglit_result<br>
-egl_image_for_dma_buf_fd(int fd, int fourcc, int w, int h,<br>
-                        unsigned stride, unsigned offset, EGLImageKHR *out_img);<br>
+egl_image_for_dma_buf_fd(struct piglit_dma_buf *buf, int fd, int fourcc, EGLImageKHR *out_img);<br>
<br>
 enum piglit_result<br>
 texture_for_egl_image(EGLImageKHR img, GLuint *out_tex);<br>
diff --git a/tests/spec/ext_image_dma_buf_import/sample_rgb.c b/tests/spec/ext_image_dma_buf_import/sample_rgb.c<br>
index af9b39f..b659717 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/sample_rgb.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/sample_rgb.c<br>
@@ -59,7 +59,7 @@ piglit_display(void)<br>
<br>
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);<br>
<br>
-       res = dma_buf_create_and_sample_32bpp(2, 2, 4, fourcc, src);<br>
+       res = dma_buf_create_and_sample_32bpp(2, 2, fourcc, src);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
diff --git a/tests/spec/ext_image_dma_buf_import/sample_yuv.c b/tests/spec/ext_image_dma_buf_import/sample_yuv.c<br>
index 1fb8de6..a314bc5 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/sample_yuv.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/sample_yuv.c<br>
@@ -45,26 +45,38 @@ enum piglit_result<br>
 piglit_display(void)<br>
 {<br>
        static const unsigned char nv12[] = {<br>
+               /* Y */<br>
                 50,  70,  90, 110,<br>
                 50,  70,  90, 110,<br>
                 50,  70,  90, 110,<br>
                 50,  70,  90, 110,<br>
+               /* UV */<br>
                120, 130, 140, 130,<br>
-               120, 160, 140, 160<br>
+               120, 160, 140, 160,<br>
        }, yuv420[] = {<br>
+               /* Y */<br>
                 50,  70,  90, 110,<br>
                 50,  70,  90, 110,<br>
                 50,  70,  90, 110,<br>
                 50,  70,  90, 110,<br>
-               120, 140, 130, 130,<br>
-               120, 140, 160, 160<br>
+               /* U */<br>
+               120, 140,<br>
+               120, 140,<br>
+               /* V */<br>
+               130, 130,<br>
+               160, 160,<br>
        }, yvu420[] = {<br>
+               /* Y */<br>
                 50,  70,  90, 110,<br>
                 50,  70,  90, 110,<br>
                 50,  70,  90, 110,<br>
                 50,  70,  90, 110,<br>
-               130, 130, 120, 140,<br>
-               160, 160, 120, 140,<br>
+               /* V */<br>
+               130, 130,<br>
+               160, 160,<br>
+               /* U */<br>
+               120, 140,<br>
+               120, 140,<br>
        };<br>
<br>
        static const unsigned char expected[4 * 4 * 4] = {<br>
@@ -78,7 +90,7 @@ piglit_display(void)<br>
                 90,  79, 111, 255,<br>
                114, 103, 135, 255,<br>
<br>
-                92,  16,  25, 255,<br>
+                92,  16,  25, 255,<br>
                115,  39,  48, 255,<br>
                138,  55, 111, 255,<br>
                161,  78, 135, 255,<br>
@@ -108,7 +120,7 @@ piglit_display(void)<br>
<br>
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);<br>
<br>
-       res = dma_buf_create_and_sample_32bpp(4, 4, 1, fourcc, t);<br>
+       res = dma_buf_create_and_sample_32bpp(4, 4, fourcc, t);<br>
        if (res != PIGLIT_PASS)<br>
                return res;<br>
<br>
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<br>
index 31c27e6..f968539 100644<br>
--- a/tests/spec/ext_image_dma_buf_import/transcode-nv12-as-r8-gr88.c<br>
+++ b/tests/spec/ext_image_dma_buf_import/transcode-nv12-as-r8-gr88.c<br>
@@ -33,6 +33,8 @@<br>
  * and GR88 DRM formats.<br>
  */<br>
<br>
+#include "piglit-framework-gl/piglit_drm_dma_buf.h"<br>
+<br>
 #include "image_common.h"<br>
<br>
 #define WINDOW_WIDTH 4<br>
@@ -77,26 +79,20 @@ static const uint8_t v_data[] = {<br>
 };<br>
<br>
 static GLuint<br>
-create_dma_buf_texture(uint32_t width, uint32_t height,<br>
-                      uint32_t cpp, uint32_t stride,<br>
-                      uint32_t drm_fourcc, const void *pixels)<br>
+create_dma_buf_texture(uint32_t width, uint32_t height, uint32_t fourcc,<br>
+                      const void *pixels)<br>
 {<br>
        EGLDisplay dpy = eglGetCurrentDisplay();<br>
<br>
        enum piglit_result result = PIGLIT_PASS;<br>
<br>
        struct piglit_dma_buf *dma_buf;<br>
-       int dma_buf_fd;<br>
-       uint32_t dma_buf_offset;<br>
-       uint32_t dma_buf_stride;<br>
        EGLImageKHR image;<br>
        EGLint image_attrs[13];<br>
        GLuint tex;<br>
        int i;<br>
<br>
-       result = piglit_create_dma_buf(width, height, cpp, pixels, stride,<br>
-                                      &dma_buf, &dma_buf_fd, &dma_buf_stride,<br>
-                                      &dma_buf_offset);<br>
+       result = piglit_create_dma_buf(width, height, fourcc, pixels, &dma_buf);<br>
<br>
        if (result != PIGLIT_PASS) {<br>
                piglit_loge("failed to create dma_buf");<br>
@@ -105,17 +101,17 @@ create_dma_buf_texture(uint32_t width, uint32_t height,<br>
<br>
        i = 0;<br>
        image_attrs[i++] = EGL_LINUX_DRM_FOURCC_EXT;<br>
-       image_attrs[i++] = drm_fourcc;<br>
+       image_attrs[i++] = fourcc;<br>
        image_attrs[i++] = EGL_WIDTH;<br>
        image_attrs[i++] = width;<br>
        image_attrs[i++] = EGL_HEIGHT;<br>
        image_attrs[i++] = height;<br>
        image_attrs[i++] = EGL_DMA_BUF_PLANE0_FD_EXT;<br>
-       image_attrs[i++] = dma_buf_fd;<br>
+       image_attrs[i++] = dma_buf->fd;<br>
        image_attrs[i++] = EGL_DMA_BUF_PLANE0_PITCH_EXT;<br>
-       image_attrs[i++] = dma_buf_stride;<br>
+       image_attrs[i++] = dma_buf->stride[0];<br>
        image_attrs[i++] = EGL_DMA_BUF_PLANE0_OFFSET_EXT;<br>
-       image_attrs[i++] = dma_buf_offset;<br>
+       image_attrs[i++] = dma_buf->offset[0];<br>
        image_attrs[i++] = EGL_NONE;<br>
<br>
<br>
@@ -191,12 +187,10 @@ create_textures(GLuint *r8_tex, GLuint *gr88_tex, float **ref_rgba_image)<br>
<br>
        glActiveTexture(GL_TEXTURE0);<br>
        *r8_tex = create_dma_buf_texture(width, height,<br>
-                                        /*cpp*/ 1, /*stride*/ width,<br>
                                         DRM_FORMAT_R8, r8_pixels);<br>
<br>
        glActiveTexture(GL_TEXTURE1);<br>
        *gr88_tex = create_dma_buf_texture(width / 2, height / 2,<br>
-                                          /*cpp*/ 2, /*stride*/ width,<br>
                                           DRM_FORMAT_GR88, gr88_pixels);<br>
 }<br>
<br>
diff --git a/tests/util/piglit-framework-gl.c b/tests/util/piglit-framework-gl.c<br>
index 9748ddf..1c25f2c 100644<br>
--- a/tests/util/piglit-framework-gl.c<br>
+++ b/tests/util/piglit-framework-gl.c<br>
@@ -265,22 +265,14 @@ piglit_set_reshape_func(void (*func)(int w, int h))<br>
                gl_fw->set_reshape_func(gl_fw, func);<br>
 }<br>
<br>
-<br>
 enum piglit_result<br>
-piglit_create_dma_buf(unsigned w, unsigned h, unsigned cpp,<br>
-                     const void *src_data, unsigned src_stride,<br>
-                     struct piglit_dma_buf **buf, int *fd,<br>
-                     unsigned *stride, unsigned *offset)<br>
+piglit_create_dma_buf(unsigned w, unsigned h, unsigned fourcc,<br>
+                     const void *src_data, struct piglit_dma_buf **buf)<br>
 {<br>
-       *fd = 0;<br>
-       *stride = 0;<br>
-       *offset = 0;<br>
-<br>
        if (!gl_fw->create_dma_buf)<br>
                return PIGLIT_SKIP;<br>
<br>
-       return gl_fw->create_dma_buf(w, h, cpp, src_data, src_stride, buf, fd,<br>
-                               stride, offset);<br>
+       return gl_fw->create_dma_buf(w, h, fourcc, src_data, buf);<br>
 }<br>
<br>
 void<br>
diff --git a/tests/util/piglit-framework-gl.h b/tests/util/piglit-framework-gl.h<br>
index 81c1a5e..ecf5b5c 100644<br>
--- a/tests/util/piglit-framework-gl.h<br>
+++ b/tests/util/piglit-framework-gl.h<br>
@@ -310,16 +310,22 @@ struct piglit_dma_buf;<br>
  * given data (src_data). Different hardware may have different alignment<br>
  * constraints and hence one can specify one stride for the source and get<br>
  * another for the final buffer to be given further to EGL.<br>
- * An opaque handle, file descriptor, stride and offset for the buffer are only<br>
- * returned upon success indicated by the return value PIGLIT_PASS, otherwise<br>
- * no buffer is created. In case the framework simply does not support dma<br>
- * buffers, the return value is PIGLIT_SKIP instead of PIGLIT_FAIL.<br>
+ *<br>
+ * The src stride is inferred from the width and the fourcc.  For planar<br>
+ * YUV formats, for example, the U and V planes for YV12/YU12 have half the<br>
+ * src_stride.<br>
+ *<br>
+ * The resulting per-plane stride and offset, which may be different than<br>
+ * the src_stride due to hw constraints, are in the returned buf object.<br>
+ *<br>
+ * An buf handle is only returned upon success indicated by the return value<br>
+ * PIGLIT_PASS, otherwise no buffer is created. In case the framework simply<br>
+ * does not support dma buffers, the return value is PIGLIT_SKIP instead of<br>
+ * PIGLIT_FAIL.<br>
  */<br>
 enum piglit_result<br>
-piglit_create_dma_buf(unsigned w, unsigned h, unsigned cpp,<br>
-                     const void *src_data, unsigned src_stride,<br>
-                     struct piglit_dma_buf **buf, int *fd,<br>
-                     unsigned *stride, unsigned *offset);<br>
+piglit_create_dma_buf(unsigned w, unsigned h, unsigned fourcc,<br>
+                     const void *src_data, struct piglit_dma_buf **buf);<br>
<br>
 /**<br>
  * Release all the resources allocated for the designated buffer. If the given<br>
diff --git a/tests/util/piglit-framework-gl/piglit_drm_dma_buf.c b/tests/util/piglit-framework-gl/piglit_drm_dma_buf.c<br>
index 3d1dc24..8e87b25 100644<br>
--- a/tests/util/piglit-framework-gl/piglit_drm_dma_buf.c<br>
+++ b/tests/util/piglit-framework-gl/piglit_drm_dma_buf.c<br>
@@ -23,6 +23,7 @@<br>
<br>
 #include "piglit-util-gl.h"<br>
 #include "piglit_drm_dma_buf.h"<br>
+#include "drm_fourcc.h"<br>
 #ifdef HAVE_LIBDRM_INTEL<br>
 #include <libdrm/intel_bufmgr.h><br>
 #endif<br>
@@ -41,21 +42,13 @@<br>
<br>
 #define ALIGN(value, alignment) (((value) + alignment - 1) & ~(alignment - 1))<br>
<br>
-struct piglit_dma_buf {<br>
-       unsigned w;<br>
-       unsigned h;<br>
-       unsigned stride;<br>
-       int fd;<br>
-       void *priv;<br>
-};<br>
-<br>
 struct piglit_drm_driver {<br>
        int fd;<br>
        char *name;<br>
<br>
        bool<br>
        (*create)(unsigned w, unsigned h, unsigned cpp,<br>
-                 const unsigned char *src_data, unsigned src_stride,<br>
+                 const unsigned char *src_data,<br>
                  struct piglit_dma_buf *buf);<br>
<br>
        bool<br>
@@ -133,23 +126,55 @@ piglit_intel_bufmgr_get(void)<br>
 }<br>
<br>
 static bool<br>
-piglit_intel_buf_create(unsigned w, unsigned h, unsigned cpp,<br>
-                       const unsigned char *src_data, unsigned src_stride,<br>
-                       struct piglit_dma_buf *buf)<br>
+piglit_intel_buf_create(unsigned w, unsigned h, unsigned fourcc,<br>
+                       const unsigned char *src_data, struct piglit_dma_buf *buf)<br>
 {<br>
        unsigned i;<br>
        drm_intel_bo *bo;<br>
-       unsigned stride = ALIGN(w * cpp, 4);<br>
        drm_intel_bufmgr *mgr = piglit_intel_bufmgr_get();<br>
+       unsigned stride, src_stride, cpp;<br>
+       unsigned buf_h = h;<br>
<br>
        if (!mgr || h % 2)<br>
                return false;<br>
<br>
-       bo = drm_intel_bo_alloc(mgr, "piglit_dma_buf", h * stride, 4096);<br>
+       switch (fourcc) {<br>
+       case DRM_FORMAT_R8:<br>
+               cpp = 1;<br>
+               break;<br>
+       case DRM_FORMAT_GR88:<br>
+       case DRM_FORMAT_RG88:<br>
+               cpp = 2;<br>
+               break;<br>
+       case DRM_FORMAT_XRGB8888:<br>
+       case DRM_FORMAT_XBGR8888:<br>
+       case DRM_FORMAT_RGBX8888:<br>
+       case DRM_FORMAT_BGRX8888:<br>
+       case DRM_FORMAT_ARGB8888:<br>
+       case DRM_FORMAT_ABGR8888:<br>
+       case DRM_FORMAT_RGBA8888:<br>
+       case DRM_FORMAT_BGRA8888:<br>
+               cpp = 4;<br>
+               break;<br>
+       case DRM_FORMAT_NV12:<br>
+       case DRM_FORMAT_YUV420:<br>
+       case DRM_FORMAT_YVU420:<br>
+               cpp = 1;<br>
+               buf_h = h * 3 / 2;<br>
+               break;<br>
+       default:<br>
+               fprintf(stderr, "invalid fourcc: %.4s\n", (char *)&fourcc);<br>
+               return false;<br>
+       }<br>
+<br>
+       src_stride = cpp * w;<br>
+       stride = ALIGN(w * cpp, 4);<br>
+<br>
+       bo = drm_intel_bo_alloc(mgr, "piglit_dma_buf", buf_h * stride, 4096);<br>
        if (!bo)<br>
                return false;<br>
<br>
-       for (i = 0; i < h; ++i) {<br>
+       for (i = 0; i < buf_h; ++i) {<br>
                if (drm_intel_bo_subdata(bo, i * stride, w * cpp,<br>
                        src_data + i * src_stride)) {<br>
                        drm_intel_bo_unreference(bo);<br>
@@ -159,10 +184,27 @@ piglit_intel_buf_create(unsigned w, unsigned h, unsigned cpp,<br>
<br>
        buf->w = w;<br>
        buf->h = h;<br>
-       buf->stride = stride;<br>
+       buf->offset[0] = 0;<br>
+       buf->stride[0] = stride;<br>
        buf->fd = 0;<br>
        buf->priv = bo;<br>
<br>
+       switch (fourcc) {<br>
+       case DRM_FORMAT_NV12:<br>
+               buf->offset[1] = stride * h;<br>
+               buf->stride[1] = stride;<br>
+               break;<br>
+       case DRM_FORMAT_YUV420:<br>
+       case DRM_FORMAT_YVU420:<br>
+               buf->offset[1] = stride * h;<br>
+               buf->stride[1] = stride / 2;<br>
+               buf->offset[2] = buf->offset[1] + (stride * h / 2 / 2);<br>
+               buf->stride[2] = stride / 2;<br>
+               break;<br>
+       default:<br>
+               break;<br>
+       }<br>
+<br>
        return true;<br>
 }<br>
<br>
@@ -201,9 +243,8 @@ piglit_gbm_get(void)<br>
 }<br>
<br>
 static bool<br>
-piglit_gbm_buf_create(unsigned w, unsigned h, unsigned cpp,<br>
-                       const unsigned char *src_data, unsigned src_stride,<br>
-                       struct piglit_dma_buf *buf)<br>
+piglit_gbm_buf_create(unsigned w, unsigned h, unsigned fourcc,<br>
+                       const unsigned char *src_data, struct piglit_dma_buf *buf)<br>
 {<br>
        unsigned i;<br>
        struct gbm_bo *bo;<br>
@@ -212,28 +253,73 @@ piglit_gbm_buf_create(unsigned w, unsigned h, unsigned cpp,<br>
        void *dst_data;<br>
        void *map_data = NULL;<br>
        enum gbm_bo_format format;<br>
+       unsigned cpp = 0, src_stride;<br>
+       unsigned buf_w = w;<br>
+       unsigned buf_h = h;<br>
<br>
-       if (!gbm || h % 2)<br>
+       if (!gbm || h % 2 || w % 2)<br>
                return false;<br>
<br>
-       /* It would be nice if we took in a fourcc instead of a cpp */<br>
-       switch (cpp) {<br>
-       case 1:<br>
-               format = GBM_FORMAT_C8;<br>
+       switch (fourcc) {<br>
+       case DRM_FORMAT_R8:<br>
+               format = GBM_FORMAT_R8;<br>
+               cpp = 1;<br>
+               src_stride = cpp * w;<br>
+               break;<br>
+       case DRM_FORMAT_GR88:<br>
+       case DRM_FORMAT_RG88:<br>
+               format = GBM_FORMAT_GR88;<br>
+               cpp = 2;<br>
+               src_stride = cpp * w;<br>
                break;<br>
-       case 4:<br>
+       case DRM_FORMAT_XRGB8888:<br>
+       case DRM_FORMAT_XBGR8888:<br>
+       case DRM_FORMAT_RGBX8888:<br>
+       case DRM_FORMAT_BGRX8888:<br>
+       case DRM_FORMAT_ARGB8888:<br>
+       case DRM_FORMAT_ABGR8888:<br>
+       case DRM_FORMAT_RGBA8888:<br>
+       case DRM_FORMAT_BGRA8888:<br>
                format = GBM_BO_FORMAT_ARGB8888;<br>
+               cpp = 4;<br>
+               src_stride = cpp * w;<br>
+               break;<br>
+       /* For YUV formats, the U/V planes might have a greater relative<br>
+        * pitch.  For example, if the driver needs pitch aligned to 32<br>
+        * pixels, for a 4x4 YUV image, the stride of both the Y and U/V<br>
+        * planes will be 32 bytes.  Not 32 for Y and 16 for U/V.  To<br>
+        * account for this, use a 2cpp format with half the width.  For<br>
+        * hardware that only has stride requirements in bytes (rather<br>
+        * than pixels) this will work out the same.  For hardware that<br>
+        * has pitch alignment requirements in pixels, this will give an<br>
+        * overly conservative alignment for Y but a sufficient alignment<br>
+        * for U/V.<br>
+        */<br>
+       case DRM_FORMAT_NV12:<br>
+               format = GBM_FORMAT_GR88;<br>
+               buf_w = w / 2;<br>
+               buf_h = h * 3 / 2;<br>
+               src_stride = w;<br>
+               cpp = 1;<br>
+               break;<br>
+       case DRM_FORMAT_YUV420:<br>
+       case DRM_FORMAT_YVU420:<br>
+               format = GBM_FORMAT_GR88;<br>
+               buf_w = w / 2;<br>
+               buf_h = h * 2;    /* U/V not interleaved */<br>
+               src_stride = w;<br>
+               cpp = 1;<br>
                break;<br>
        default:<br>
-               fprintf(stderr, "Unknown cpp %d\n", cpp);<br>
+               fprintf(stderr, "invalid fourcc: %.4s\n", (char *)&fourcc);<br>
                return false;<br>
        }<br>
<br>
-       bo = gbm_bo_create(gbm, w, h, format, GBM_BO_USE_RENDERING);<br>
+       bo = gbm_bo_create(gbm, buf_w, buf_h, format, GBM_BO_USE_RENDERING);<br>
        if (!bo)<br>
                return false;<br>
<br>
-       dst_data = gbm_bo_map(bo, 0, 0, w, h, GBM_BO_TRANSFER_WRITE,<br>
+       dst_data = gbm_bo_map(bo, 0, 0, buf_w, buf_h, GBM_BO_TRANSFER_WRITE,<br>
                              &dst_stride, &map_data);<br>
        if (!dst_data) {<br>
                fprintf(stderr, "Failed to map GBM bo\n");<br>
@@ -241,18 +327,49 @@ piglit_gbm_buf_create(unsigned w, unsigned h, unsigned cpp,<br>
                return NULL;<br>
        }<br>
<br>
+       buf->w = w;<br>
+       buf->h = h;<br>
+       buf->offset[0] = 0;<br>
+       buf->stride[0] = dst_stride;<br>
+       buf->fd = -1;<br>
+       buf->priv = bo;<br>
+<br>
        for (i = 0; i < h; ++i) {<br>
                memcpy((char *)dst_data + i * dst_stride,<br>
                       src_data + i * src_stride,<br>
                       w * cpp);<br>
        }<br>
+<br>
+       switch (fourcc) {<br>
+       case DRM_FORMAT_NV12:<br>
+               buf->offset[1] = dst_stride * h;<br>
+               buf->stride[1] = dst_stride;<br>
+               for (i = 0; i < h/2; ++i) {<br>
+                       memcpy(((char *)dst_data + buf->offset[1]) + i * buf->stride[1],<br>
+                               (src_data + (w*h)) + i * src_stride, w);<br>
+               }<br>
+               break;<br>
+       case DRM_FORMAT_YUV420:<br>
+       case DRM_FORMAT_YVU420:<br>
+               buf->offset[1] = dst_stride * h;<br>
+               buf->stride[1] = dst_stride / 2;<br>
+               for (i = 0; i < h/2; ++i) {<br>
+                       memcpy(((char *)dst_data + buf->offset[1]) + i * buf->stride[1],<br>
+                               (src_data + (w*h)) + i * src_stride / 2, w / 2);<br>
+               }<br>
+               buf->offset[2] = buf->offset[1] + (dst_stride * h / 2 / 2);<br>
+               buf->stride[2] = dst_stride / 2;<br>
+               for (i = 0; i < h/2; ++i) {<br>
+                       memcpy(((char *)dst_data + buf->offset[2]) + i * buf->stride[2],<br>
+                               (src_data + (w*h) + (w*h/4)) + i * src_stride / 2, w / 2);<br>
+               }<br>
+               break;<br>
+       default:<br>
+               break;<br>
+       }<br>
+<br>
        gbm_bo_unmap(bo, map_data);<br>
<br>
-       buf->w = w;<br>
-       buf->h = h;<br>
-       buf->stride = dst_stride;<br>
-       buf->fd = 0;<br>
-       buf->priv = bo;<br>
<br>
        return true;<br>
 }<br>
@@ -290,7 +407,7 @@ piglit_drm_get_driver(void)<br>
        if (drv.fd == -1) {<br>
                drv.fd = open("/dev/dri/card0", O_RDWR);<br>
                if (drv.fd == -1) {<br>
-                       fprintf(stderr, "error: failed to open /dev/dri/renderD128 and "<br>
+                       fprintf(stderr, "error: failed to open /dev/dri/renderD128 or "<br>
                                "/dev/dri/card0\n");<br>
                        goto fail;<br>
<br>
@@ -352,10 +469,8 @@ piglit_drm_get_driver(void)<br>
 }<br>
<br>
 enum piglit_result<br>
-piglit_drm_create_dma_buf(unsigned w, unsigned h, unsigned cpp,<br>
-                       const void *src_data, unsigned src_stride,<br>
-                       struct piglit_dma_buf **buf, int *fd,<br>
-                       unsigned *stride, unsigned *offset)<br>
+piglit_drm_create_dma_buf(unsigned w, unsigned h, unsigned fourcc,<br>
+                       const void *src_data,  struct piglit_dma_buf **buf)<br>
 {<br>
        struct piglit_dma_buf *drm_buf;<br>
        const struct piglit_drm_driver *drv = piglit_drm_get_driver();<br>
@@ -367,7 +482,7 @@ piglit_drm_create_dma_buf(unsigned w, unsigned h, unsigned cpp,<br>
        if (!drm_buf)<br>
                return PIGLIT_FAIL;<br>
<br>
-       if (!drv->create(w, h, cpp, src_data, src_stride, drm_buf)) {<br>
+       if (!drv->create(w, h, fourcc, src_data, drm_buf)) {<br>
                free(drm_buf);<br>
                return PIGLIT_FAIL;<br>
        }<br>
@@ -378,9 +493,6 @@ piglit_drm_create_dma_buf(unsigned w, unsigned h, unsigned cpp,<br>
        }<br>
<br>
        *buf = drm_buf;<br>
-       *fd = drm_buf->fd;<br>
-       *stride = drm_buf->stride;<br>
-       *offset = 0;<br>
<br>
        return PIGLIT_PASS;<br>
 }<br>
diff --git a/tests/util/piglit-framework-gl/piglit_drm_dma_buf.h b/tests/util/piglit-framework-gl/piglit_drm_dma_buf.h<br>
index 2c72eca..5872df9 100644<br>
--- a/tests/util/piglit-framework-gl/piglit_drm_dma_buf.h<br>
+++ b/tests/util/piglit-framework-gl/piglit_drm_dma_buf.h<br>
@@ -23,13 +23,18 @@<br>
 #ifndef PIGLIT_DRM_DMA_BUF_H<br>
 #define PIGLIT_DRM_DMA_BUF_H<br>
<br>
-struct piglit_dma_buf;<br>
+struct piglit_dma_buf {<br>
+       unsigned w;<br>
+       unsigned h;<br>
+       unsigned offset[3];<br>
+       unsigned stride[3];<br>
+       int fd;<br>
+       void *priv;<br>
+};<br>
<br>
 enum piglit_result<br>
-piglit_drm_create_dma_buf(unsigned w, unsigned h, unsigned cpp,<br>
-                         const void *src_data, unsigned src_stride,<br>
-                         struct piglit_dma_buf **buf, int *fd,<br>
-                         unsigned *stride, unsigned *offset);<br>
+piglit_drm_create_dma_buf(unsigned w, unsigned h, unsigned fourcc,<br>
+                       const void *src_data,  struct piglit_dma_buf **buf);<br>
<br>
 void<br>
 piglit_drm_destroy_dma_buf(struct piglit_dma_buf *buf);<br>
diff --git a/tests/util/piglit-framework-gl/piglit_gl_framework.h b/tests/util/piglit-framework-gl/piglit_gl_framework.h<br>
index 97fecca..aad565e 100644<br>
--- a/tests/util/piglit-framework-gl/piglit_gl_framework.h<br>
+++ b/tests/util/piglit-framework-gl/piglit_gl_framework.h<br>
@@ -73,10 +73,8 @@ struct piglit_gl_framework {<br>
        (*destroy)(struct piglit_gl_framework *gl_fw);<br>
<br>
        enum piglit_result<br>
-       (*create_dma_buf)(unsigned w, unsigned h, unsigned cpp,<br>
-                         const void *src_data, unsigned src_stride,<br>
-                         struct piglit_dma_buf **buf, int *fd,<br>
-                         unsigned *stride, unsigned *offset);<br>
+       (*create_dma_buf)(unsigned w, unsigned h, unsigned fourcc,<br>
+                         const void *src_data, struct piglit_dma_buf **buf);<br>
<br>
        void<br>
        (*destroy_dma_buf)(struct piglit_dma_buf *buf);<br>
--<br>
2.7.4<br>
<br>
</blockquote></div></div>