[Intel-gfx] [PATCH] tests/gem_create2: Verifying the gem_create2 ioctl

sourab.gupta at intel.com sourab.gupta at intel.com
Mon Jun 16 17:33:08 CEST 2014


From: Sourab Gupta <sourab.gupta at intel.com>

This patch adds the testcases for verifying the new gem_create2
ioctl. By means of this ioctl, we can specify number of parameters
during object creation time such as placement, cache domains,
caching, madvise, tiling etc.
These testcases include functional tests and interface tests for
testing the create2 ioctl

Signed-off-by: Sourab Gupta <sourab.gupta at intel.com>
---
 tests/Makefile.sources |   1 +
 tests/gem_create2.c    | 578 +++++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 579 insertions(+)
 create mode 100644 tests/gem_create2.c

diff --git a/tests/Makefile.sources b/tests/Makefile.sources
index b91b2b4..65c5ca4 100644
--- a/tests/Makefile.sources
+++ b/tests/Makefile.sources
@@ -23,6 +23,7 @@ TESTS_progs_M = \
 	gem_caching \
 	gem_close_race \
 	gem_concurrent_blit \
+	gem_create2 \
 	gem_cs_tlb \
 	gem_ctx_bad_exec \
 	gem_ctx_exec \
diff --git a/tests/gem_create2.c b/tests/gem_create2.c
new file mode 100644
index 0000000..a61d281
--- /dev/null
+++ b/tests/gem_create2.c
@@ -0,0 +1,578 @@
+/*
+ * Copyright © 2011 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.
+ *
+ * Authors:
+ *    Sourab Gupta <sourabgupta at gmail.com>
+ *
+ */
+
+/** @file gem_create2.c
+ *
+ * This is a test of create2 ioctl which creates bo according to various parameters.
+ *
+ *
+ * The goal is to simply ensure the basics work, and invalid input combinations
+ * are rejected.
+ */
+
+#include <stdlib.h>
+#include <sys/ioctl.h>
+#include <stdio.h>
+#include <string.h>
+#include <fcntl.h>
+#include <inttypes.h>
+#include <errno.h>
+#include <sys/stat.h>
+#include <sys/time.h>
+#include <getopt.h>
+
+#include <drm.h>
+
+#include "ioctl_wrappers.h"
+#include "drmtest.h"
+#include "intel_bufmgr.h"
+#include "intel_batchbuffer.h"
+#include "intel_io.h"
+#include "intel_chipset.h"
+#include "igt_aux.h"
+
+#define WIDTH 512
+#define CPP 4
+#define STRIDE (WIDTH*CPP)
+#define HEIGHT 128
+#define SIZE (HEIGHT*STRIDE)
+#define CLEAR(s) memset(&s, 0, sizeof(s))
+
+static drm_intel_bufmgr *bufmgr;
+static struct intel_batchbuffer *batch;
+static int cfg_count;
+
+void initialize_cfg(void);
+
+enum placement {
+	PLACEMENT_SYSTEM = I915_CREATE_PLACEMENT_SYSTEM,
+	PLACEMENT_STOLEN = I915_CREATE_PLACEMENT_STOLEN,
+};
+
+struct bo_placement {
+	enum placement place;
+	const char *name;
+}placements[] = {
+	{ PLACEMENT_SYSTEM, "PLACEMENT_SYSTEM"},
+	{ PLACEMENT_STOLEN, "PLACEMENT_STOLEN"},
+};
+
+enum cache_mode {
+	CACHING_NONE = I915_CACHING_NONE,
+	CACHING_CACHED = I915_CACHING_CACHED,
+	CACHING_DISPLAY = I915_CACHING_DISPLAY,
+};
+
+struct bo_cache {
+	enum cache_mode cache;
+	const char *name;
+} caches[] = {
+	{ CACHING_NONE, "CACHING_NONE"},
+	{ CACHING_CACHED, "CACHING_CACHED"},
+	{ CACHING_DISPLAY, "CACHING_DISPLAY"},
+};
+
+enum domain {
+	DOMAIN_CPU = I915_GEM_DOMAIN_CPU,
+	DOMAIN_GTT = I915_GEM_DOMAIN_GTT,
+};
+
+struct bo_domain {
+	enum domain domain;
+	const char *name;
+} domains[] = {
+	{ DOMAIN_CPU, "DOMAIN_CPU"},
+	{ DOMAIN_GTT, "DOMAIN_GTT"},
+};
+
+enum tiling_mode {
+	TILING_NONE = I915_TILING_NONE,
+	TILING_X = I915_TILING_X,
+	TILING_Y = I915_TILING_Y,
+};
+
+struct bo_tiling {
+	enum tiling_mode tiling;
+	const char *name;
+}tilings[] = {
+	{ TILING_NONE, "TILING_NONE"},
+	{ TILING_X, "TILING_X"},
+	{ TILING_Y, "TILING_Y"},
+};
+
+struct test_config {
+	struct bo_placement cfg_placement;
+	struct bo_cache cfg_cache;
+	struct bo_domain cfg_domain;
+	struct bo_tiling cfg_tiling;
+/* MAX_CONFIGS will change as we add more configs */
+#define MAX_CONFIGS 36
+	char name[128];
+}configs[MAX_CONFIGS];
+
+void initialize_cfg(void)
+{
+	int i, j, k, l;
+
+	cfg_count=0;
+	for (i=0;i<ARRAY_SIZE(placements);i++)
+	for (j=0;j<ARRAY_SIZE(caches);j++)
+	for (k=0;k<ARRAY_SIZE(domains);k++)
+	for (l=0;l<ARRAY_SIZE(tilings);l++)
+	{
+		configs[cfg_count].cfg_placement = placements[i];
+		configs[cfg_count].cfg_cache = caches[j];
+		configs[cfg_count].cfg_domain = domains[k];
+		configs[cfg_count].cfg_tiling = tilings[l];
+		sprintf(configs[cfg_count].name,"copy-%s-%s-%s-%s",
+			placements[i].name, caches[j].name,
+			domains[k].name, tilings[l].name);
+		cfg_count++;
+	}
+}
+
+static void verify_copy_op(drm_intel_bo *src, drm_intel_bo *dest)
+{
+	uint32_t *virt, i, ret;
+	/* Fill the src BO with dwords */
+	ret = drm_intel_gem_bo_map_gtt(src);
+	igt_assert(!ret);
+
+	virt = src->virtual;
+	for (i = 0; i < WIDTH*HEIGHT; i++)
+		virt[i] = i;
+
+	intel_copy_bo(batch, dest, src, SIZE);
+
+	ret = drm_intel_gem_bo_map_gtt(dest);
+	igt_assert(!ret);
+
+	virt = dest->virtual;
+	/* verify */
+	for (i = 0; i < WIDTH*HEIGHT; i++) {
+		if (virt[i] != i) {
+			fprintf(stderr, "Expected 0x%08x, found 0x%08x "
+					"at offset 0x%08x\n",
+					i, virt[i], i * 4);
+			igt_assert(virt[i] == i);
+		}
+	}
+
+	drm_intel_bo_unmap(src);
+	drm_intel_bo_unmap(dest);
+}
+
+static void copy_test(struct test_config *cfg)
+{
+	drm_intel_bo *src, *dest;
+	drm_intel_bo_alloc_params src_params, dest_params;
+
+	CLEAR(src_params);
+	src_params.width = WIDTH;
+	src_params.height = HEIGHT;
+	src_params.cpp = CPP;
+	src_params.tiling_mode = cfg->cfg_tiling.tiling;
+	src_params.cache_domain = cfg->cfg_domain.domain;
+	src_params.placement = cfg->cfg_placement.place;
+	src_params.caching = cfg->cfg_cache.cache;
+	src_params.madvise = I915_MADV_WILLNEED;
+	src_params.name = "src_bo";
+
+	CLEAR(dest_params);
+	dest_params.width = WIDTH;
+	dest_params.height = HEIGHT;
+	dest_params.cpp = CPP;
+	dest_params.tiling_mode = cfg->cfg_tiling.tiling;
+	dest_params.cache_domain = cfg->cfg_domain.domain;
+	dest_params.placement = cfg->cfg_placement.place;
+	dest_params.caching = cfg->cfg_cache.cache;
+	dest_params.madvise = I915_MADV_WILLNEED;
+	dest_params.name = "dest_bo";
+
+	src = drm_intel_bo_alloc_from_params(bufmgr, &src_params);
+	dest = drm_intel_bo_alloc_from_params(bufmgr, &dest_params);
+
+	igt_assert(src != NULL);
+	igt_assert(dest != NULL);
+
+	verify_copy_op(src, dest);
+
+	drm_intel_bo_unreference(src);
+	drm_intel_bo_unreference(dest);
+}
+
+static void offset_valid_test(struct test_config *cfg,
+			int src_offset,	int dest_offset)
+{
+	drm_intel_bo *src, *dest;
+	drm_intel_bo_alloc_params src_params, dest_params;
+	drm_intel_context *context;
+
+	context = drm_intel_gem_context_create(bufmgr);
+
+	CLEAR(src_params);
+	src_params.width = WIDTH;
+	src_params.height = HEIGHT;
+	src_params.cpp = CPP;
+	src_params.tiling_mode = cfg->cfg_tiling.tiling;
+	src_params.cache_domain = cfg->cfg_domain.domain;
+	src_params.placement = cfg->cfg_placement.place;
+	src_params.caching = cfg->cfg_cache.cache;
+	src_params.madvise = I915_MADV_WILLNEED;
+	src_params.context = context;
+	src_params.offset = src_offset & I915_CREATE_OFFSET_VALID;
+	src_params.name = "src_bo";
+
+	CLEAR(dest_params);
+	dest_params.width = WIDTH;
+	dest_params.height = HEIGHT;
+	dest_params.cpp = CPP;
+	dest_params.tiling_mode = cfg->cfg_tiling.tiling;
+	dest_params.cache_domain = cfg->cfg_domain.domain;
+	dest_params.placement = cfg->cfg_placement.place;
+	dest_params.caching = cfg->cfg_cache.cache;
+	dest_params.madvise = I915_MADV_WILLNEED;
+	dest_params.context = context;
+	dest_params.offset = dest_offset & I915_CREATE_OFFSET_VALID;
+	dest_params.name = "dest_bo";
+
+	src = drm_intel_bo_alloc_from_params(bufmgr, &src_params);
+	dest = drm_intel_bo_alloc_from_params(bufmgr, &dest_params);
+
+	igt_assert(src != NULL);
+	igt_assert(dest != NULL);
+
+	verify_copy_op(src, dest);
+
+	drm_intel_gem_context_destroy(context);
+
+	drm_intel_bo_unreference(src);
+	drm_intel_bo_unreference(dest);
+}
+
+static void offset_invalid_test(struct test_config *cfg, int offset)
+{
+	drm_intel_bo_alloc_params params;
+	drm_intel_context *context;
+	drm_intel_bo *bo;
+
+	context = drm_intel_gem_context_create(bufmgr);
+
+	CLEAR(params);
+	params.width = WIDTH;
+	params.height = HEIGHT;
+	params.cpp = CPP;
+	params.tiling_mode = cfg->cfg_tiling.tiling;
+	params.cache_domain = cfg->cfg_domain.domain;
+	params.placement = cfg->cfg_placement.place;
+	params.caching = cfg->cfg_cache.cache;
+	params.madvise = I915_MADV_WILLNEED;
+	params.context = context;
+	params.offset = offset & I915_CREATE_OFFSET_VALID;
+	params.name = "test bo";
+
+	bo = drm_intel_bo_alloc_from_params(bufmgr, &params);
+
+	igt_assert(bo == NULL);
+
+	drm_intel_gem_context_destroy(context);
+}
+
+static void same_offset_test(struct test_config *cfg, int offset)
+{
+	drm_intel_bo_alloc_params params;
+	drm_intel_context *context;
+	drm_intel_bo *bo, *second_bo;
+
+	context = drm_intel_gem_context_create(bufmgr);
+
+	CLEAR(params);
+	params.width = WIDTH;
+	params.height = HEIGHT;
+	params.cpp = CPP;
+	params.tiling_mode = cfg->cfg_tiling.tiling;
+	params.cache_domain = cfg->cfg_domain.domain;
+	params.placement = cfg->cfg_placement.place;
+	params.caching = cfg->cfg_cache.cache;
+	params.madvise = I915_MADV_WILLNEED;
+	params.context = context;
+	params.offset = offset & I915_CREATE_OFFSET_VALID;
+	params.name = "test bo";
+
+	bo = drm_intel_bo_alloc_from_params(bufmgr, &params);
+
+	igt_assert(bo != NULL);
+
+	second_bo = drm_intel_bo_alloc_from_params(bufmgr, &params);
+	igt_assert(second_bo == NULL);
+
+	drm_intel_gem_context_destroy(context);
+	drm_intel_bo_unreference(bo);
+}
+
+static void
+dontneed_mmap_gtt(struct test_config *cfg)
+{
+	drm_intel_bo_alloc_params params;
+	drm_intel_bo *bo;
+
+	CLEAR(params);
+	params.width = WIDTH;
+	params.height = HEIGHT;
+	params.cpp = CPP;
+	params.tiling_mode = cfg->cfg_tiling.tiling;
+	params.cache_domain = cfg->cfg_domain.domain;
+	params.placement = cfg->cfg_placement.place;
+	params.caching = cfg->cfg_cache.cache;
+	params.madvise = I915_MADV_DONTNEED;
+	params.name = "bo_dont_need";
+
+	bo = drm_intel_bo_alloc_from_params(bufmgr, &params);
+	drm_intel_gem_bo_map_gtt(bo);
+	igt_assert(bo->virtual == NULL);
+	igt_assert(errno == EFAULT);
+
+	drm_intel_bo_unreference(bo);
+}
+
+static void
+dontneed_pwrite(struct test_config *cfg)
+{
+	drm_intel_bo_alloc_params params;
+	drm_intel_bo *bo;
+	char data[32];
+	int i;
+
+	for(i=0;i<32;i++)
+		data[i]=i;
+
+	CLEAR(params);
+	params.width = WIDTH;
+	params.height = HEIGHT;
+	params.cpp = CPP;
+	params.tiling_mode = cfg->cfg_tiling.tiling;
+	params.cache_domain = cfg->cfg_domain.domain;
+	params.placement = cfg->cfg_placement.place;
+	params.caching = cfg->cfg_cache.cache;
+	params.madvise = I915_MADV_DONTNEED;
+	params.name = "bo_dont_need";
+
+	bo = drm_intel_bo_alloc_from_params(bufmgr, &params);
+
+	drm_intel_bo_subdata(bo, 0, 32, data);
+	igt_assert(errno == EFAULT);
+
+	drm_intel_bo_unreference(bo);
+}
+
+static void dontneed_exec(struct test_config *cfg)
+{
+	drm_intel_bo *src, *dest;
+	drm_intel_bo_alloc_params src_params, dest_params;
+	uint32_t *virt, i, ret, diff=0;
+
+	CLEAR(src_params);
+	src_params.width = WIDTH;
+	src_params.height = HEIGHT;
+	src_params.cpp = CPP;
+	src_params.tiling_mode = cfg->cfg_tiling.tiling;
+	src_params.cache_domain = cfg->cfg_domain.domain;
+	src_params.placement = cfg->cfg_placement.place;
+	src_params.caching = cfg->cfg_cache.cache;
+	src_params.madvise = I915_MADV_WILLNEED;
+	src_params.name = "src_bo";
+
+	CLEAR(dest_params);
+	dest_params.width = WIDTH;
+	dest_params.height = HEIGHT;
+	dest_params.cpp = CPP;
+	dest_params.tiling_mode = cfg->cfg_tiling.tiling;
+	dest_params.cache_domain = cfg->cfg_domain.domain;
+	dest_params.placement = cfg->cfg_placement.place;
+	dest_params.caching = cfg->cfg_cache.cache;
+	dest_params.madvise = I915_MADV_DONTNEED;
+	dest_params.name = "dest_bo";
+
+	src = drm_intel_bo_alloc_from_params(bufmgr, &src_params);
+	dest = drm_intel_bo_alloc_from_params(bufmgr, &dest_params);
+
+	igt_assert(src != NULL);
+	igt_assert(dest != NULL);
+
+	/* Fill the src BO with dwords */
+	ret = drm_intel_gem_bo_map_gtt(src);
+	igt_assert(!ret);
+
+	virt = src->virtual;
+	for (i = 0; i < WIDTH*HEIGHT; i++)
+		virt[i] = i;
+
+	intel_copy_bo(batch, dest, src, SIZE);
+
+	ret = drm_intel_bo_map(dest, 1);
+	igt_assert(!ret);
+
+	virt = dest->virtual;
+	/* verify */
+	for (i = 0; i < WIDTH*HEIGHT; i++) {
+		if (virt[i] != i)
+			diff = 1;
+	}
+	igt_assert(diff == 1);
+
+	drm_intel_bo_unmap(src);
+	drm_intel_bo_unmap(dest);
+
+	drm_intel_bo_unreference(src);
+	drm_intel_bo_unreference(dest);
+}
+
+static void
+stolen_mmap(struct test_config *cfg)
+{
+	drm_intel_bo_alloc_params params;
+	drm_intel_bo *bo;
+	int ret;
+
+	CLEAR(params);
+	params.width = WIDTH;
+	params.height = HEIGHT;
+	params.cpp = CPP;
+	params.tiling_mode = cfg->cfg_tiling.tiling;
+	params.cache_domain = cfg->cfg_domain.domain;
+	params.placement = I915_CREATE_PLACEMENT_STOLEN;
+	params.caching = cfg->cfg_cache.cache;
+	params.madvise = I915_MADV_WILLNEED;
+	params.name = "bo_stolen";
+
+	bo = drm_intel_bo_alloc_from_params(bufmgr, &params);
+	ret = drm_intel_bo_map(bo, 1);
+	igt_assert(ret != 0);
+
+	drm_intel_bo_unreference(bo);
+}
+
+static void
+stolen_pwrite(struct test_config *cfg)
+{
+	drm_intel_bo_alloc_params params;
+	drm_intel_bo *bo;
+	char data[32];
+	int i, ret;
+
+	for(i=0;i<32;i++)
+		data[i]=i;
+
+	CLEAR(params);
+	params.width = WIDTH;
+	params.height = HEIGHT;
+	params.cpp = CPP;
+	params.tiling_mode = cfg->cfg_tiling.tiling;
+	params.cache_domain = cfg->cfg_domain.domain;
+	params.placement = I915_CREATE_PLACEMENT_STOLEN;
+	params.caching = cfg->cfg_cache.cache;
+	params.madvise = I915_MADV_WILLNEED;
+	params.name = "bo_stolen";
+
+	bo = drm_intel_bo_alloc_from_params(bufmgr, &params);
+
+	ret = drm_intel_bo_subdata(bo, 0, 32, data);
+	igt_assert(ret != 0);
+
+	drm_intel_bo_unreference(bo);
+}
+
+igt_main
+{
+	int i, fd, gtt_size_total, gtt_size_mappable;
+	uint32_t devid;
+
+	igt_skip_on_simulation();
+
+	igt_fixture {
+		fd = drm_open_any();
+		devid = intel_get_drm_devid(fd);
+
+		drm_intel_get_aperture_sizes(fd, (size_t*)&gtt_size_total,
+				(size_t*)&gtt_size_mappable);
+		bufmgr = drm_intel_bufmgr_gem_init(fd, 4096);
+		batch = intel_batchbuffer_alloc(bufmgr, devid);
+		initialize_cfg();
+	}
+
+	/* Functional Tests - blt copy */
+	for(i=0;i<cfg_count;i++) {
+		igt_subtest(configs[i].name)
+			copy_test(&configs[i]);
+	}
+
+	/* Offset test - mappable region */
+	igt_subtest("offset-valid")
+		offset_valid_test(&configs[0], gtt_size_mappable/2,
+				(gtt_size_mappable/2 + SIZE));
+
+	/* Offset test - non mappable region */
+	igt_subtest("offset-valid")
+		offset_valid_test(&configs[0], gtt_size_mappable,
+				(gtt_size_mappable + SIZE));
+
+	/* Offset = 0 */
+	igt_subtest("offset-invalid-0")
+		offset_invalid_test(&configs[0], 0);
+
+	/*Offset = gtt total size */
+	igt_subtest("offset-invalid-gtt-size")
+		offset_invalid_test(&configs[0], gtt_size_total);
+
+	/* Same offset for two buffer objects */
+	igt_subtest("same-offset-test")
+		same_offset_test(&configs[0], gtt_size_mappable/4);
+
+	/* madvise(DONT_NEED) tests */
+	igt_subtest("dontneed-mmap-gtt")
+		dontneed_mmap_gtt(&configs[0]);
+
+	igt_subtest("dontneed-pwrite")
+		dontneed_pwrite(&configs[0]);
+
+	igt_subtest("dontneed-exec")
+		dontneed_exec(&configs[0]);
+
+	/*
+	 * stolen mem special cases - checking for non cpu mappable
+	 */
+	igt_subtest("stolen-mmap")
+		stolen_mmap(&configs[0]);
+
+	igt_subtest("stolen-pwrite")
+		stolen_pwrite(&configs[0]);
+
+	igt_fixture {
+		intel_batchbuffer_free(batch);
+		drm_intel_bufmgr_destroy(bufmgr);
+	}
+}
-- 
1.8.5.1




More information about the Intel-gfx mailing list