[Piglit] [PATCH 3/3] tests: spec: tests for EXT_image_dma_buf_import

Topi Pohjolainen topi.pohjolainen at intel.com
Tue Apr 16 03:45:47 PDT 2013


These are rather simple. Without the capability of creating
textures out of the images (glEGLImageTargetTexture2DOES()), one
cannot do much with the images as such.

Extra attention should be paid to the buffer lifecycle:

   "3. Does ownership of the file descriptor pass to the EGL library?

    ANSWER: If eglCreateImageKHR is successful, EGL assumes ownership
    of the file descriptors and is responsible for closing them."

In the tests I've chosen the approach where the creator releases
its own access to the buffers as at least in Intel's case I cannot
see how the EGL driver could do it on the creators behalf.

Signed-off-by: Topi Pohjolainen <topi.pohjolainen at intel.com>
---
 tests/spec/CMakeLists.txt                          |   1 +
 .../ext_image_dma_buf_import/CMakeLists.gles1.txt  |  19 ++
 tests/spec/ext_image_dma_buf_import/CMakeLists.txt |   1 +
 tests/spec/ext_image_dma_buf_import/close_buffer.c | 116 ++++++++++
 .../spec/ext_image_dma_buf_import/create_yuv420.c  | 145 ++++++++++++
 .../ext_image_dma_buf_import/invalid_attributes.c  | 255 +++++++++++++++++++++
 .../spec/ext_image_dma_buf_import/invalid_hints.c  | 144 ++++++++++++
 .../ext_image_dma_buf_import/missing_attributes.c  | 182 +++++++++++++++
 8 files changed, 863 insertions(+)
 create mode 100644 tests/spec/ext_image_dma_buf_import/CMakeLists.gles1.txt
 create mode 100644 tests/spec/ext_image_dma_buf_import/CMakeLists.txt
 create mode 100644 tests/spec/ext_image_dma_buf_import/close_buffer.c
 create mode 100644 tests/spec/ext_image_dma_buf_import/create_yuv420.c
 create mode 100644 tests/spec/ext_image_dma_buf_import/invalid_attributes.c
 create mode 100644 tests/spec/ext_image_dma_buf_import/invalid_hints.c
 create mode 100644 tests/spec/ext_image_dma_buf_import/missing_attributes.c

diff --git a/tests/spec/CMakeLists.txt b/tests/spec/CMakeLists.txt
index a1492cc..56c0111 100644
--- a/tests/spec/CMakeLists.txt
+++ b/tests/spec/CMakeLists.txt
@@ -68,6 +68,7 @@ add_subdirectory (ext_texture_array)
 add_subdirectory (ext_texture_integer)
 add_subdirectory (arb_draw_buffers)
 add_subdirectory (oes_draw_texture)
+add_subdirectory (ext_image_dma_buf_import)
 add_subdirectory (arb_blend_func_extended)
 add_subdirectory (ext_unpack_subimage)
 add_subdirectory (arb_vertex_array_object)
diff --git a/tests/spec/ext_image_dma_buf_import/CMakeLists.gles1.txt b/tests/spec/ext_image_dma_buf_import/CMakeLists.gles1.txt
new file mode 100644
index 0000000..f6c4ea7
--- /dev/null
+++ b/tests/spec/ext_image_dma_buf_import/CMakeLists.gles1.txt
@@ -0,0 +1,19 @@
+#add_definitions(-DSOURCE_DIR="${piglit_SOURCE_DIR}/")
+
+include_directories(
+	${OPENGL_INCLUDE_PATH}
+	)
+
+link_libraries(
+	${OPENGL_gles1_LIBRARY}
+	${OPENGL_egl_LIBRARY}
+	piglitutil_gles1
+	)
+
+piglit_add_executable(ext_image_dma_buf_import-invalid_hints invalid_hints.c)
+piglit_add_executable(ext_image_dma_buf_import-invalid_attributes invalid_attributes.c)
+piglit_add_executable(ext_image_dma_buf_import-missing_attributes missing_attributes.c)
+piglit_add_executable(ext_image_dma_buf_import-close_buffer close_buffer.c)
+piglit_add_executable(ext_image_dma_buf_import-create_yuv420 create_yuv420.c)
+
+# vim: ft=cmake:
diff --git a/tests/spec/ext_image_dma_buf_import/CMakeLists.txt b/tests/spec/ext_image_dma_buf_import/CMakeLists.txt
new file mode 100644
index 0000000..144a306
--- /dev/null
+++ b/tests/spec/ext_image_dma_buf_import/CMakeLists.txt
@@ -0,0 +1 @@
+piglit_include_target_api()
diff --git a/tests/spec/ext_image_dma_buf_import/close_buffer.c b/tests/spec/ext_image_dma_buf_import/close_buffer.c
new file mode 100644
index 0000000..c31b22a
--- /dev/null
+++ b/tests/spec/ext_image_dma_buf_import/close_buffer.c
@@ -0,0 +1,116 @@
+/*
+ * Copyright © 2013 Intel Corporation
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+ * IN THE SOFTWARE.
+ */
+
+#include "piglit-util-egl.h"
+#define EGL_EGLEXT_PROTOTYPES 1
+#include <EGL/eglext.h>
+
+/**
+ * @file close_buffer.c
+ *
+ * From the EXT_image_dma_buf_import spec:
+ *
+ * "3. Does ownership of the file descriptor pass to the EGL library?
+ *
+ *   ANSWER: If eglCreateImageKHR is successful, EGL assumes ownership of the
+ *   file descriptors and is responsible for closing them."
+ */
+
+PIGLIT_GL_TEST_CONFIG_BEGIN
+
+	config.supports_gl_es_version = 10;
+
+PIGLIT_GL_TEST_CONFIG_END
+
+#define fourcc_code(a,b,c,d) ((uint32_t)(a) | ((uint32_t)(b) << 8) | \
+				((uint32_t)(c) << 16) | ((uint32_t)(d) << 24))
+#define DRM_FORMAT_ARGB8888 fourcc_code('A', 'R', '2', '4')
+
+static bool
+test_create_and_destroy(void *buf, int fd, unsigned w, unsigned h,
+			unsigned stride, unsigned offset)
+{
+	EGLImageKHR img;
+	EGLint attr[] = {
+		EGL_WIDTH, w,
+		EGL_HEIGHT, h,
+		EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		EGL_NONE
+	};
+
+	/**
+	 * The spec says:
+	 *
+	 *     "If <target> is EGL_LINUX_DMA_BUF_EXT, <dpy> must be a valid
+	 *      display, <ctx> must be EGL_NO_CONTEXT, and <buffer> must be
+	 *      NULL, cast into the type EGLClientBuffer."
+	 */
+	img = eglCreateImageKHR(eglGetCurrentDisplay(), EGL_NO_CONTEXT,
+			EGL_LINUX_DMA_BUF_EXT, (EGLClientBuffer)0, attr);
+
+	/**
+	 * Release the creator side of the buffer, EGL should have the
+	 * ownership now.
+	 */
+	piglit_destroy_dma_buf(buf);
+
+	if (!piglit_check_egl_error(EGL_SUCCESS))
+		return false;
+
+	if (!img) {
+		fprintf(stderr, "image creation succeed but returned NULL\n");
+		return false;
+	}
+
+	eglDestroyImageKHR(eglGetCurrentDisplay(), img);
+
+	return true;
+}
+
+enum piglit_result
+piglit_display(void)
+{
+	const unsigned char pixels[2 * 2 * 4];
+	void *buf;
+	unsigned stride;
+	unsigned offset;
+	int fd;
+	enum piglit_result res;
+
+	res = piglit_create_dma_buf(2, 2, 4, pixels, 2 * 4, &buf, &fd, &stride,
+				&offset);
+	if (res != PIGLIT_PASS)
+		return res;
+
+	return test_create_and_destroy(buf, fd, 2, 2, stride, offset) ?
+			PIGLIT_PASS : PIGLIT_FAIL;
+}
+
+void
+piglit_init(int argc, char **argv)
+{
+	piglit_require_extension("GL_EXT_image_dma_buf_import");
+}
diff --git a/tests/spec/ext_image_dma_buf_import/create_yuv420.c b/tests/spec/ext_image_dma_buf_import/create_yuv420.c
new file mode 100644
index 0000000..e37c613
--- /dev/null
+++ b/tests/spec/ext_image_dma_buf_import/create_yuv420.c
@@ -0,0 +1,145 @@
+/*
+ * Copyright © 2013 Intel Corporation
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+ * IN THE SOFTWARE.
+ */
+
+#include "piglit-util-egl.h"
+#define EGL_EGLEXT_PROTOTYPES 1
+#include <EGL/eglext.h>
+
+/**
+ * @file create_yuv420.c
+ *
+ * Allocates three dma buffers from via drm and creates an YUV420 formatted EGL
+ * image each buffer representing one plane.
+ */
+
+PIGLIT_GL_TEST_CONFIG_BEGIN
+
+	config.supports_gl_es_version = 10;
+
+PIGLIT_GL_TEST_CONFIG_END
+
+#define fourcc_code(a,b,c,d) ((uint32_t)(a) | ((uint32_t)(b) << 8) | \
+				((uint32_t)(c) << 16) | ((uint32_t)(d) << 24))
+#define DRM_FORMAT_YUV420 fourcc_code('Y', 'U', '1', '2')
+
+static bool
+test_create_and_destroy(unsigned w, unsigned h,
+			void *buf0, void *buf1, void *buf2,
+			int fd0, int fd1, int fd2,
+			unsigned stride0, unsigned stride1, unsigned stride2,
+			unsigned offset0, unsigned offset1, unsigned offset2)
+{
+	EGLImageKHR img;
+	EGLint attr[] = {
+		EGL_WIDTH, w,
+		EGL_HEIGHT, h,
+		EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_YUV420,
+		EGL_DMA_BUF_PLANE0_FD_EXT, fd0,
+		EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset0,
+		EGL_DMA_BUF_PLANE0_PITCH_EXT, stride0,
+		EGL_DMA_BUF_PLANE1_FD_EXT, fd1,
+		EGL_DMA_BUF_PLANE1_OFFSET_EXT, offset1,
+		EGL_DMA_BUF_PLANE1_PITCH_EXT, stride1,
+		EGL_DMA_BUF_PLANE2_FD_EXT, fd2,
+		EGL_DMA_BUF_PLANE2_OFFSET_EXT, offset2,
+		EGL_DMA_BUF_PLANE2_PITCH_EXT, stride2,
+		EGL_NONE
+	};
+
+	/**
+	 * The spec says:
+	 *
+	 *     "If <target> is EGL_LINUX_DMA_BUF_EXT, <dpy> must be a valid
+	 *      display, <ctx> must be EGL_NO_CONTEXT, and <buffer> must be
+	 *      NULL, cast into the type EGLClientBuffer."
+	 */
+	img = eglCreateImageKHR(eglGetCurrentDisplay(), EGL_NO_CONTEXT,
+			EGL_LINUX_DMA_BUF_EXT, (EGLClientBuffer)0, attr);
+
+	/**
+	 * Release the creator side of the buffers, EGL should have the
+	 * ownership now.
+	 */
+	piglit_destroy_dma_buf(buf0);
+	piglit_destroy_dma_buf(buf1);
+	piglit_destroy_dma_buf(buf2);
+
+	if (!piglit_check_egl_error(EGL_SUCCESS))
+		return false;
+
+	if (!img) {
+		fprintf(stderr, "image creation succeed but returned NULL\n");
+		return false;
+	}
+
+	eglDestroyImageKHR(eglGetCurrentDisplay(), img);
+
+	return true;
+}
+
+enum piglit_result
+piglit_display(void)
+{
+	const unsigned char pixels0[4 * 4 * 1];
+	const unsigned char pixels1[2 * 2 * 1];
+	const unsigned char pixels2[2 * 2 * 1];
+	void *buf0, *buf1, *buf2;
+	unsigned stride0, stride1, stride2;
+	unsigned offset0, offset1, offset2;
+	int fd0, fd1, fd2;
+	enum piglit_result res;
+
+	res = piglit_create_dma_buf(4, 4, 1, pixels0, 4 * 1, &buf0, &fd0,
+				&stride0, &offset0);
+	if (res != PIGLIT_PASS) {
+		fprintf(stderr, "buffer creation for Y-plane failed\n");
+		return res;
+	}
+
+	res = piglit_create_dma_buf(2, 2, 1, pixels1, 2 * 1, &buf1, &fd1,
+				&stride1, &offset1);
+	if (res != PIGLIT_PASS) {
+		fprintf(stderr, "buffer creation for U-plane failed\n");
+		piglit_destroy_dma_buf(buf0);
+		return res;
+	}
+
+	res = piglit_create_dma_buf(2, 2, 1, pixels2, 2 * 1, &buf2, &fd2,
+				&stride2, &offset2);
+	if (res != PIGLIT_PASS) {
+		fprintf(stderr, "buffer creation for V-plane failed\n");
+		piglit_destroy_dma_buf(buf0);
+		piglit_destroy_dma_buf(buf1);
+		return res;
+	}
+
+	return test_create_and_destroy(4, 4, buf0, buf1, buf2, fd0, fd1, fd2,
+			stride0, stride1, stride2, offset0, offset1, offset2) ?
+			PIGLIT_PASS : PIGLIT_FAIL;
+}
+
+void
+piglit_init(int argc, char **argv)
+{
+	piglit_require_extension("GL_EXT_image_dma_buf_import");
+}
diff --git a/tests/spec/ext_image_dma_buf_import/invalid_attributes.c b/tests/spec/ext_image_dma_buf_import/invalid_attributes.c
new file mode 100644
index 0000000..8e0108a
--- /dev/null
+++ b/tests/spec/ext_image_dma_buf_import/invalid_attributes.c
@@ -0,0 +1,255 @@
+/*
+ * Copyright © 2013 Intel Corporation
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+ * IN THE SOFTWARE.
+ */
+
+#include "piglit-util-egl.h"
+#define EGL_EGLEXT_PROTOTYPES 1
+#include <EGL/eglext.h>
+
+/**
+ * @file invalid_attributes.c
+ *
+ * From the EXT_image_dma_buf_import spec:
+ *
+ * "* If <target> is EGL_LINUX_DMA_BUF_EXT and <buffer> is not NULL, the
+ *    error EGL_BAD_PARAMETER is generated.
+ *
+ *  * If <target> is EGL_LINUX_DMA_BUF_EXT, and the EGL_LINUX_DRM_FOURCC_EXT
+ *    attribute is set to a format not supported by the EGL, EGL_BAD_MATCH
+ *    is generated.
+ *
+ *  * If <target> is EGL_LINUX_DMA_BUF_EXT, and the EGL_LINUX_DRM_FOURCC_EXT
+ *    attribute indicates a single-plane format, EGL_BAD_ATTRIBUTE is
+ *    generated if any of the EGL_DMA_BUF_PLANE1_* or EGL_DMA_BUF_PLANE2_*
+ *    attributes are specified.
+ *
+ *  * If <target> is EGL_LINUX_DMA_BUF_EXT and one or more of the values
+ *    specified for a plane's pitch or offset isn't supported by EGL,
+ *    EGL_BAD_ACCESS is generated."
+ */
+
+PIGLIT_GL_TEST_CONFIG_BEGIN
+
+	config.supports_gl_es_version = 10;
+
+PIGLIT_GL_TEST_CONFIG_END
+
+#define fourcc_code(a,b,c,d) ((uint32_t)(a) | ((uint32_t)(b) << 8) | \
+				((uint32_t)(c) << 16) | ((uint32_t)(d) << 24))
+#define DRM_FORMAT_ARGB8888 fourcc_code('A', 'R', '2', '4')
+#define DRM_FORMAT_INVALID fourcc_code('F', 'O', 'O', '0')
+
+static bool
+test_excess_attributes(int fd, unsigned w, unsigned h, unsigned stride,
+		unsigned offset)
+{
+	unsigned i;
+	const EGLint excess_attributes[][2 * 7 + 1] = {
+		{ EGL_HEIGHT, w,
+		  EGL_WIDTH, h,
+		  EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		  EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		  EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		  EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		  EGL_DMA_BUF_PLANE1_FD_EXT, fd,
+		  EGL_NONE },
+		{ EGL_HEIGHT, w,
+		  EGL_WIDTH, h,
+		  EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		  EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		  EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		  EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		  EGL_DMA_BUF_PLANE1_OFFSET_EXT, 0,
+		  EGL_NONE },
+		{ EGL_HEIGHT, w,
+		  EGL_WIDTH, h,
+		  EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		  EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		  EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		  EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		  EGL_DMA_BUF_PLANE1_PITCH_EXT, stride,
+		  EGL_NONE },
+	};
+
+	for (i = 0; i < sizeof(excess_attributes) /
+			sizeof(excess_attributes[0]); ++i) {
+		/**
+		 * The spec says:
+		 *
+		 *  "If <target> is EGL_LINUX_DMA_BUF_EXT, <dpy> must be a valid
+		 *   display, <ctx> must be EGL_NO_CONTEXT, and <buffer> must be
+		 *   NULL, cast into the type EGLClientBuffer."
+		 */
+		EGLImageKHR img = eglCreateImageKHR(eglGetCurrentDisplay(),
+				EGL_NO_CONTEXT, EGL_LINUX_DMA_BUF_EXT,
+				(EGLClientBuffer)NULL, excess_attributes[i]);
+
+		if (!piglit_check_egl_error(EGL_BAD_ATTRIBUTE)) {
+			if (img)
+				eglDestroyImageKHR(eglGetCurrentDisplay(), img);
+			return false;
+		}
+	}
+
+	return true;
+}
+
+static bool
+test_buffer_not_null(int fd, unsigned w, unsigned h, unsigned stride,
+		unsigned offset)
+{
+	EGLImageKHR img;
+	EGLint attr[] = {
+		EGL_WIDTH, w,
+		EGL_HEIGHT, h,
+		EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		EGL_NONE
+	};
+
+	/**
+	 * The spec says:
+	 *
+	 *     "If <target> is EGL_LINUX_DMA_BUF_EXT, <dpy> must be a valid
+	 *      display, <ctx> must be EGL_NO_CONTEXT, and <buffer> must be
+	 *      NULL, cast into the type EGLClientBuffer."
+	 */
+	img = eglCreateImageKHR(eglGetCurrentDisplay(), EGL_NO_CONTEXT,
+			EGL_LINUX_DMA_BUF_EXT, (EGLClientBuffer)1, attr);
+
+	if (!piglit_check_egl_error(EGL_BAD_PARAMETER)) {
+		if (img)
+			eglDestroyImageKHR(eglGetCurrentDisplay(), img);
+		return false;
+	}
+
+	return true;
+}
+
+static bool
+test_invalid_format(int fd, unsigned w, unsigned h, unsigned stride,
+		unsigned offset)
+{
+	EGLImageKHR img;
+	EGLint attr[] = {
+		EGL_WIDTH, w,
+		EGL_HEIGHT, h,
+		EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_INVALID,
+		EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		EGL_NONE
+	};
+
+	/**
+	 * The spec says:
+	 *
+	 *     "If <target> is EGL_LINUX_DMA_BUF_EXT, <dpy> must be a valid
+	 *      display, <ctx> must be EGL_NO_CONTEXT, and <buffer> must be
+	 *      NULL, cast into the type EGLClientBuffer."
+	 */
+	img = eglCreateImageKHR(eglGetCurrentDisplay(), EGL_NO_CONTEXT,
+			EGL_LINUX_DMA_BUF_EXT, (EGLClientBuffer)0, attr);
+
+	if (!piglit_check_egl_error(EGL_BAD_MATCH)) {
+		if (img)
+			eglDestroyImageKHR(eglGetCurrentDisplay(), img);
+		return false;
+	}
+
+	return true;
+}
+
+static bool
+test_pitch_zero(int fd, unsigned w, unsigned h, unsigned stride,
+		unsigned offset)
+{
+	EGLImageKHR img;
+	EGLint attr[] = {
+		EGL_WIDTH, w,
+		EGL_HEIGHT, h,
+		EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		EGL_DMA_BUF_PLANE0_PITCH_EXT, 0,
+		EGL_NONE
+	};
+
+	/**
+	 * The spec says:
+	 *
+	 *     "If <target> is EGL_LINUX_DMA_BUF_EXT, <dpy> must be a valid
+	 *      display, <ctx> must be EGL_NO_CONTEXT, and <buffer> must be
+	 *      NULL, cast into the type EGLClientBuffer."
+	 */
+	img = eglCreateImageKHR(eglGetCurrentDisplay(), EGL_NO_CONTEXT,
+			EGL_LINUX_DMA_BUF_EXT, (EGLClientBuffer)0, attr);
+
+	if (!piglit_check_egl_error(EGL_BAD_ACCESS)) {
+		if (img)
+			eglDestroyImageKHR(eglGetCurrentDisplay(), img);
+		return false;
+	}
+
+	return true;
+}
+
+/**
+ * On re-uses the buffer for all the tests. The spec says:
+ *
+ * "If <target> is EGL_LINUX_DMA_BUF_EXT and eglCreateImageKHR fails,
+ *  EGL does not retain ownership of the file descriptor and it is the
+ *  responsibility of the application to close it."
+ */
+enum piglit_result
+piglit_display(void)
+{
+	const unsigned char pixels[2 * 2 * 4];
+	void *buf;
+	unsigned stride;
+	unsigned offset;
+	int fd;
+	enum piglit_result res;
+	bool pass;
+
+	res = piglit_create_dma_buf(2, 2, 4, pixels, 2 * 4, &buf, &fd, &stride,
+				&offset);
+	if (res != PIGLIT_PASS)
+		return res;
+
+	pass = test_excess_attributes(fd, 2, 2, 2 * 4, 0);
+	pass = test_buffer_not_null(fd, 2, 2, 2 * 4, 0) && pass;
+	pass = test_invalid_format(fd, 2, 2, 2 * 4, 0) && pass;
+	pass = test_pitch_zero(fd, 2, 2, 2 * 4, 0) && pass;
+
+	piglit_destroy_dma_buf(buf);
+
+	return pass ? PIGLIT_PASS : PIGLIT_FAIL;
+}
+
+void
+piglit_init(int argc, char **argv)
+{
+	piglit_require_extension("GL_EXT_image_dma_buf_import");
+}
diff --git a/tests/spec/ext_image_dma_buf_import/invalid_hints.c b/tests/spec/ext_image_dma_buf_import/invalid_hints.c
new file mode 100644
index 0000000..1d8b10e
--- /dev/null
+++ b/tests/spec/ext_image_dma_buf_import/invalid_hints.c
@@ -0,0 +1,144 @@
+/*
+ * Copyright © 2013 Intel Corporation
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+ * IN THE SOFTWARE.
+ */
+
+#include "piglit-util-egl.h"
+#define EGL_EGLEXT_PROTOTYPES 1
+#include <EGL/eglext.h>
+
+/**
+ * @file invalid_hints.c
+ *
+ * From the EXT_image_dma_buf_import spec:
+ *
+ * "Accepted as the value for the EGL_YUV_COLOR_SPACE_HINT_EXT attribute:
+ *
+ *       EGL_ITU_REC601_EXT   0x327F
+ *       EGL_ITU_REC709_EXT   0x3280
+ *       EGL_ITU_REC2020_EXT  0x3281
+ * 
+ * Accepted as the value for the EGL_SAMPLE_RANGE_HINT_EXT attribute:
+ * 
+ *       EGL_YUV_FULL_RANGE_EXT    0x3282
+ *       EGL_YUV_NARROW_RANGE_EXT  0x3283
+ *
+ * Accepted as the value for the EGL_YUV_CHROMA_HORIZONTAL_SITING_HINT_EXT &
+ * EGL_YUV_CHROMA_VERTICAL_SITING_HINT_EXT attributes:
+ *
+ *       EGL_YUV_CHROMA_SITING_0_EXT    0x3284
+ *       EGL_YUV_CHROMA_SITING_0_5_EXT  0x3285"
+ *
+ *
+ * In order to test these, one needs to have the following in place:
+ * EGL_WIDTH, EGL_HEIGHT, EGL_LINUX_DRM_FOURCC_EXT, EGL_DMA_BUF_PLANE0_FD_EXT,
+ * EGL_DMA_BUF_PLANE0_OFFSET_EXT and EGL_DMA_BUF_PLANE0_PITCH_EXT.
+ *
+ * \see invalid_attributes.c and missing_attributes.c
+ */
+
+PIGLIT_GL_TEST_CONFIG_BEGIN
+
+	config.supports_gl_es_version = 10;
+
+PIGLIT_GL_TEST_CONFIG_END
+
+#define fourcc_code(a,b,c,d) ((uint32_t)(a) | ((uint32_t)(b) << 8) | \
+				((uint32_t)(c) << 16) | ((uint32_t)(d) << 24))
+#define DRM_FORMAT_ARGB8888 fourcc_code('A', 'R', '2', '4')
+
+static bool
+test_invalid_hint(int fd, unsigned w, unsigned h, unsigned stride,
+		unsigned offset, int hint, int val)
+{
+	EGLImageKHR img;
+	EGLint attr[] = {
+		EGL_WIDTH, w,
+		EGL_HEIGHT, h,
+		EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		hint, val,
+		EGL_NONE
+	};
+
+	/**
+	 * The spec says:
+	 *
+	 *     "If <target> is EGL_LINUX_DMA_BUF_EXT, <dpy> must be a valid
+	 *      display, <ctx> must be EGL_NO_CONTEXT, and <buffer> must be
+	 *      NULL, cast into the type EGLClientBuffer."
+	 */
+	img = eglCreateImageKHR(eglGetCurrentDisplay(), EGL_NO_CONTEXT,
+			EGL_LINUX_DMA_BUF_EXT, (EGLClientBuffer)NULL, attr);
+
+	if (!piglit_check_egl_error(EGL_BAD_ATTRIBUTE)) {
+		if (img)
+			eglDestroyImageKHR(eglGetCurrentDisplay(), img);
+		return false;
+	}
+
+	return true;
+}
+
+/**
+ * On re-uses the buffer for all the tests. The spec says:
+ *
+ * "If <target> is EGL_LINUX_DMA_BUF_EXT and eglCreateImageKHR fails,
+ *  EGL does not retain ownership of the file descriptor and it is the
+ *  responsibility of the application to close it."
+ */
+enum piglit_result
+piglit_display(void)
+{
+	const unsigned char pixels[2 * 2 * 4];
+	void *buf;
+	unsigned stride;
+	unsigned offset;
+	int fd;
+	bool pass;
+	enum piglit_result res;
+
+	res = piglit_create_dma_buf(2, 2, 4, pixels, 2 * 4, &buf, &fd, &stride,
+				&offset);
+	if (res != PIGLIT_PASS)
+		return res;
+
+	pass = test_invalid_hint(fd, 2, 2, stride, offset,
+			EGL_YUV_COLOR_SPACE_HINT_EXT, 0);
+	pass = test_invalid_hint(fd, 2, 2, stride, offset,
+			EGL_SAMPLE_RANGE_HINT_EXT, 0) && pass;
+	pass = test_invalid_hint(fd, 2, 2, stride, offset,
+			EGL_YUV_CHROMA_HORIZONTAL_SITING_HINT_EXT, 0) && pass;
+	pass = test_invalid_hint(fd, 2, 2, stride, offset,
+			EGL_YUV_CHROMA_VERTICAL_SITING_HINT_EXT, 0) && pass;
+
+	piglit_destroy_dma_buf(buf);
+
+	return pass ? PIGLIT_PASS : PIGLIT_FAIL;
+}
+
+void
+piglit_init(int argc, char **argv)
+{
+	piglit_require_extension("GL_EXT_image_dma_buf_import");
+}
diff --git a/tests/spec/ext_image_dma_buf_import/missing_attributes.c b/tests/spec/ext_image_dma_buf_import/missing_attributes.c
new file mode 100644
index 0000000..ecf4c1b
--- /dev/null
+++ b/tests/spec/ext_image_dma_buf_import/missing_attributes.c
@@ -0,0 +1,182 @@
+/*
+ * Copyright © 2013 Intel Corporation
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+ * IN THE SOFTWARE.
+ */
+
+#include "piglit-util-egl.h"
+#define EGL_EGLEXT_PROTOTYPES 1
+#include <EGL/eglext.h>
+
+/**
+ * @file missing_attributes.c
+ *
+ * From the EXT_image_dma_buf_import spec:
+ *
+ * "If <target> is EGL_LINUX_DMA_BUF_EXT, <dpy> must be a valid display, <ctx>
+ *  must be EGL_NO_CONTEXT, and <buffer> must be NULL, cast into the type
+ *  EGLClientBuffer. The details of the image is specified by the attributes
+ *  passed into eglCreateImageKHR. Required attributes and their values are as
+ *  follows:
+ *
+ *      * EGL_WIDTH & EGL_HEIGHT: The logical dimensions of the buffer in pixels
+ *
+ *      * EGL_LINUX_DRM_FOURCC_EXT: The pixel format of the buffer, as specified
+ *        by drm_fourcc.h and used as the pixel_format parameter of the
+ *        drm_mode_fb_cmd2 ioctl.
+ *
+ *      * EGL_DMA_BUF_PLANE0_FD_EXT: The dma_buf file descriptor of plane 0 of
+ *        the image.
+ *
+ *      * EGL_DMA_BUF_PLANE0_OFFSET_EXT: The offset from the start of the
+ *        dma_buf of the first sample in plane 0, in bytes.
+ *
+ *      * EGL_DMA_BUF_PLANE0_PITCH_EXT: The number of bytes between the start of
+ *        subsequent rows of samples in plane 0. May have special meaning for
+ *        non-linear formats."
+ */
+
+PIGLIT_GL_TEST_CONFIG_BEGIN
+
+	config.supports_gl_es_version = 10;
+
+PIGLIT_GL_TEST_CONFIG_END
+
+#define fourcc_code(a,b,c,d) ((uint32_t)(a) | ((uint32_t)(b) << 8) | \
+				((uint32_t)(c) << 16) | ((uint32_t)(d) << 24))
+#define DRM_FORMAT_ARGB8888 fourcc_code('A', 'R', '2', '4')
+
+static bool
+test_missing(int fd, const EGLint *attr)
+{
+	EGLImageKHR img;
+
+	/**
+	 * The spec says:
+	 *
+	 *     "If <target> is EGL_LINUX_DMA_BUF_EXT, <dpy> must be a valid
+	 *      display, <ctx> must be EGL_NO_CONTEXT, and <buffer> must be
+	 *      NULL, cast into the type EGLClientBuffer."
+	 */
+	img = eglCreateImageKHR(eglGetCurrentDisplay(), EGL_NO_CONTEXT,
+			EGL_LINUX_DMA_BUF_EXT, (EGLClientBuffer)NULL, attr);
+
+	/**
+	 * The spec says also that:
+	 *
+	 * "If <target> is EGL_LINUX_DMA_BUF_EXT, and the list of attributes is
+	 *  incomplete, EGL_BAD_PARAMETER is generated."
+	 */
+	if (!piglit_check_egl_error(EGL_BAD_PARAMETER)) {
+		if (img)
+			eglDestroyImageKHR(eglGetCurrentDisplay(), img);
+		return false;
+	}
+
+	return true;
+}
+
+static bool
+test_all(int fd, unsigned w, unsigned h, unsigned stride, unsigned offset)
+{
+	/* there are six mandatory attributes */
+	const EGLint missing_attributes[][2 * 5 + 1] = {
+		{ EGL_HEIGHT, h,
+		  EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		  EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		  EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		  EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		  EGL_NONE },
+		{ EGL_WIDTH, w,
+		  EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		  EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		  EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		  EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		  EGL_NONE },
+		{ EGL_WIDTH, w,
+		  EGL_HEIGHT, h,
+		  EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		  EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		  EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		  EGL_NONE },
+		{ EGL_WIDTH, w,
+		  EGL_HEIGHT, h,
+		  EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		  EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		  EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		  EGL_NONE },
+		{ EGL_WIDTH, w,
+		  EGL_HEIGHT, h,
+		  EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		  EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		  EGL_DMA_BUF_PLANE0_PITCH_EXT, stride,
+		  EGL_NONE },
+		{ EGL_WIDTH, w,
+		  EGL_HEIGHT, h,
+		  EGL_LINUX_DRM_FOURCC_EXT, DRM_FORMAT_ARGB8888,
+		  EGL_DMA_BUF_PLANE0_FD_EXT, fd,
+		  EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset,
+		  EGL_NONE },
+	};
+	bool pass = true;
+	unsigned i;
+
+	for (i = 0; i < sizeof(missing_attributes) /
+			sizeof(missing_attributes[0]); ++i) {
+		pass &= test_missing(fd, missing_attributes[i]);
+	}
+
+	return pass;
+}
+
+/**
+ * On re-uses the buffer for all the tests. The spec says:
+ *
+ * "If <target> is EGL_LINUX_DMA_BUF_EXT and eglCreateImageKHR fails,
+ *  EGL does not retain ownership of the file descriptor and it is the
+ *  responsibility of the application to close it."
+ */
+enum piglit_result
+piglit_display(void)
+{
+	const unsigned char pixels[2 * 2 * 4];
+	void *buf;
+	unsigned stride;
+	unsigned offset;
+	int fd;
+	enum piglit_result res;
+
+	res = piglit_create_dma_buf(2, 2, 4, pixels, 2 * 4, &buf, &fd, &stride,
+				&offset);
+	if (res != PIGLIT_PASS)
+		return res;
+
+	res = test_all(fd, 2, 2, stride, offset) ? PIGLIT_PASS : PIGLIT_FAIL;
+
+	piglit_destroy_dma_buf(buf);
+
+	return res;
+}
+
+void
+piglit_init(int argc, char **argv)
+{
+	piglit_require_extension("GL_EXT_image_dma_buf_import");
+}
-- 
1.8.1.2



More information about the Piglit mailing list