コード例 #1
0
static int workaround_fail_count(void)
{
    int i, fail_count = 0;

    /* There is a small delay after coming ot of rc6 to the correct
       render context values will get loaded by hardware (bdw,chv).
       This here ensures that we have the correct context loaded before
       we start to read values */
    wait_gpu();

    igt_debug("Address\tval\t\tmask\t\tread\t\tresult\n");

    for (i = 0; i < num_wa_regs; ++i) {
        const uint32_t val = intel_register_read(wa_regs[i].addr);
        const bool ok = (wa_regs[i].value & wa_regs[i].mask) ==
                        (val & wa_regs[i].mask);

        igt_debug("0x%05X\t0x%08X\t0x%08X\t0x%08X\t%s\n",
                  wa_regs[i].addr, wa_regs[i].value, wa_regs[i].mask,
                  val, ok ? "OK" : "FAIL");

        if (!ok) {
            igt_warn("0x%05X\t0x%08X\t0x%08X\t0x%08X\t%s\n",
                     wa_regs[i].addr, wa_regs[i].value,
                     wa_regs[i].mask,
                     val, ok ? "OK" : "FAIL");
            fail_count++;
        }
    }

    return fail_count;
}
コード例 #2
0
ファイル: igt_fb.c プロジェクト: mv0/intel-gpu-tools
/**
 * igt_create_fb_with_bo_size:
 * @fd: open i915 drm file descriptor
 * @width: width of the framebuffer in pixel
 * @height: height of the framebuffer in pixel
 * @format: drm fourcc pixel format code
 * @tiling: tiling layout of the framebuffer (as framebuffer modifier)
 * @fb: pointer to an #igt_fb structure
 * @bo_size: size of the backing bo (0 for minimum needed size)
 *
 * This function allocates a gem buffer object suitable to back a framebuffer
 * with the requested properties and then wraps it up in a drm framebuffer
 * object of the requested size. All metadata is stored in @fb.
 *
 * The backing storage of the framebuffer is filled with all zeros, i.e. black
 * for rgb pixel formats.
 *
 * Returns:
 * The kms id of the created framebuffer.
 */
unsigned int
igt_create_fb_with_bo_size(int fd, int width, int height,
			   uint32_t format, uint64_t tiling,
			   struct igt_fb *fb, unsigned bo_size)
{
	uint32_t fb_id;
	int bpp;

	memset(fb, 0, sizeof(*fb));

	bpp = igt_drm_format_to_bpp(format);

	igt_debug("%s(width=%d, height=%d, format=0x%x [bpp=%d], tiling=0x%"PRIx64", size=%d)\n",
		  __func__, width, height, format, bpp, tiling, bo_size);
	do_or_die(create_bo_for_fb(fd, width, height, bpp, tiling, bo_size,
				   &fb->gem_handle, &fb->size, &fb->stride));

	igt_debug("%s(handle=%d, pitch=%d)\n",
		  __func__, fb->gem_handle, fb->stride);

	if (tiling != LOCAL_DRM_FORMAT_MOD_NONE &&
	    tiling != LOCAL_I915_FORMAT_MOD_X_TILED) {
		do_or_die(__kms_addfb(fd, fb->gem_handle, width, height,
				      fb->stride, format, tiling,
				      LOCAL_DRM_MODE_FB_MODIFIERS, &fb_id));
	} else {
		uint32_t handles[4];
		uint32_t pitches[4];
		uint32_t offsets[4];

		memset(handles, 0, sizeof(handles));
		memset(pitches, 0, sizeof(pitches));
		memset(offsets, 0, sizeof(offsets));

		handles[0] = fb->gem_handle;
		pitches[0] = fb->stride;

		do_or_die(drmModeAddFB2(fd, width, height, format,
					handles, pitches, offsets,
					&fb_id, 0));
	}

	fb->width = width;
	fb->height = height;
	fb->tiling = tiling;
	fb->drm_format = format;
	fb->fb_id = fb_id;

	return fb_id;
}
コード例 #3
0
ファイル: igt_debugfs.c プロジェクト: joshloo/intel-gpu-tools
/**
 * igt_get_stable_obj_count:
 * @driver: fd to drm/i915 GEM driver
 *
 * This puts the driver into a stable (quiescent) state and then returns the
 * current number of gem buffer objects as reported in the i915_gem_objects
 * debugFS interface.
 */
int igt_get_stable_obj_count(int driver)
{
	int obj_count;
	gem_quiescent_gpu(driver);
	obj_count = get_object_count();
	/* The test relies on the system being in the same state before and
	 * after the test so any difference in the object count is a result of
	 * leaks during the test. gem_quiescent_gpu() mostly achieves this but
	 * on android occasionally obj_count can still change briefly.
	 * The loop ensures obj_count has remained stable over several checks
	 */
#ifdef ANDROID
	{
		int loop_count = 0;
		int prev_obj_count = obj_count;
		while (loop_count < 4) {
			usleep(200000);
			gem_quiescent_gpu(driver);
			obj_count = get_object_count();
			if (obj_count == prev_obj_count) {
				loop_count++;
			} else {
				igt_debug("loop_count=%d, obj_count=%d, prev_obj_count=%d\n",
					loop_count, obj_count, prev_obj_count);
				loop_count = 0;
				prev_obj_count = obj_count;
			}

		}
	}
#endif
	return obj_count;
}
コード例 #4
0
ファイル: gem_eio.c プロジェクト: jmb82/intel-gpu-tools
static void trigger_reset(int fd)
{
    igt_assert(i915_wedged_set());

    /* And just check the gpu is indeed running again */
    igt_debug("Checking that the GPU recovered\n");
    gem_quiescent_gpu(fd);
}
static void do_single_test(data_t *data, int x, int y)
{
	igt_display_t *display = &data->display;
	igt_pipe_crc_t *pipe_crc = data->pipe_crc;
	igt_crc_t crc, ref_crc;
	igt_plane_t *cursor;
	cairo_t *cr = igt_get_cairo_ctx(data->drm_fd, &data->primary_fb);

	igt_print_activity();

	/* Hardware test */
	igt_paint_test_pattern(cr, data->screenw, data->screenh);
	cursor_enable(data);
	cursor = igt_output_get_plane(data->output, IGT_PLANE_CURSOR);
	igt_plane_set_position(cursor, x, y);
	igt_display_commit(display);
	igt_wait_for_vblank(data->drm_fd, data->pipe);
	igt_pipe_crc_collect_crc(pipe_crc, &crc);

	if (data->flags & (TEST_DPMS | TEST_SUSPEND)) {
		igt_crc_t crc_after;

		if (data->flags & TEST_DPMS) {
			igt_debug("dpms off/on cycle\n");
			kmstest_set_connector_dpms(data->drm_fd,
						   data->output->config.connector,
						   DRM_MODE_DPMS_OFF);
			kmstest_set_connector_dpms(data->drm_fd,
						   data->output->config.connector,
						   DRM_MODE_DPMS_ON);
		}

		if (data->flags & TEST_SUSPEND)
			igt_system_suspend_autoresume();

		igt_pipe_crc_collect_crc(pipe_crc, &crc_after);
		igt_assert_crc_equal(&crc, &crc_after);
	}

	cursor_disable(data);
	igt_display_commit(display);

	/* Now render the same in software and collect crc */
	draw_cursor(cr, x, y, data->curw, data->curh);
	igt_display_commit(display);

	igt_wait_for_vblank(data->drm_fd, data->pipe);
	igt_pipe_crc_collect_crc(pipe_crc, &ref_crc);
	/* Clear screen afterwards */
	igt_assert_crc_equal(&crc, &ref_crc);

	igt_paint_color(cr, 0, 0, data->screenw, data->screenh,
			0.0, 0.0, 0.0);
}
コード例 #6
0
ファイル: gem_eio.c プロジェクト: jmb82/intel-gpu-tools
static void wedge_gpu(int fd)
{
    /* First idle the GPU then disable GPU resets before injecting a hang */
    gem_quiescent_gpu(fd);

    igt_require(i915_reset_control(false));

    igt_debug("Wedging GPU by injecting hang\n");
    igt_post_hang_ring(fd, igt_hang_ring(fd, I915_EXEC_DEFAULT));

    igt_assert(i915_reset_control(true));
}
コード例 #7
0
static void check_bo(int fd, uint32_t handle)
{
	uint32_t *map;
	int i;

	igt_debug("Verifying result\n");
	map = gem_mmap__cpu(fd, handle, 0, 4096, PROT_READ);
	gem_set_domain(fd, handle, I915_GEM_DOMAIN_CPU, 0);
	for (i = 0; i < 1024; i++)
		igt_assert_eq(map[i], i);
	munmap(map, 4096);
}
コード例 #8
0
ファイル: gem_eio.c プロジェクト: jmb82/intel-gpu-tools
static bool i915_wedged_set(void)
{
    int fd, ret;

    igt_debug("Triggering GPU reset\n");

    fd = igt_debugfs_open("i915_wedged", O_RDWR);
    igt_require(fd >= 0);

    ret = write(fd, "1\n", 2) == 2;
    close(fd);

    return ret;
}
コード例 #9
0
ファイル: gem_eio.c プロジェクト: jmb82/intel-gpu-tools
static bool i915_reset_control(bool enable)
{
    const char *path = "/sys/module/i915/parameters/reset";
    int fd, ret;

    igt_debug("%s GPU reset\n", enable ? "Enabling" : "Disabling");

    fd = open(path, O_RDWR);
    igt_require(fd >= 0);

    ret = write(fd, &"NY"[enable], 1) == 1;
    close(fd);

    return ret;
}
コード例 #10
0
/* Translate from a swizzled offset in the tiled buffer to the corresponding
 * value from the original linear buffer.
 */
static uint32_t
calculate_expected(int offset)
{
	int tile_off = offset & (tile_size - 1);
	int tile_base = offset & -tile_size;
	int tile_index = tile_base / tile_size;
	int tiles_per_row = 4*WIDTH / tile_width;

	/* base x,y values from the tile (page) index. */
	int base_y = tile_index / tiles_per_row * tile_height;
	int base_x = tile_index % tiles_per_row * (tile_width/4);

	/* x, y offsets within the tile */
	int tile_y = tile_off / tile_width;
	int tile_x = (tile_off % tile_width) / 4;

	igt_debug("%3d, %3d, %3d,%3d\n", base_x, base_y, tile_x, tile_y);
	return (base_y + tile_y) * WIDTH + base_x + tile_x;
}
コード例 #11
0
static void fill_ring(int fd, struct drm_i915_gem_execbuffer2 *execbuf)
{
	int i;

	/* The ring we've been using is 128k, and each rendering op
	 * will use at least 8 dwords:
	 *
	 * BATCH_START
	 * BATCH_START offset
	 * MI_FLUSH
	 * STORE_DATA_INDEX
	 * STORE_DATA_INDEX offset
	 * STORE_DATA_INDEX value
	 * MI_USER_INTERRUPT
	 * (padding)
	 *
	 * So iterate just a little more than that -- if we don't fill the ring
	 * doing this, we aren't likely to with this test.
	 */
	igt_debug("Executing execbuf %d times\n", 128*1024/(8*4));
	for (i = 0; i < 128*1024 / (8 * 4); i++)
		gem_execbuf(fd, execbuf);
}
コード例 #12
0
static bool exec_noop(int fd,
		      uint32_t *handles,
		      unsigned ring,
		      bool write)
{
	struct drm_i915_gem_execbuffer2 execbuf;
	struct drm_i915_gem_exec_object2 exec[3];

	memset(exec, 0, sizeof(exec));
	exec[0].handle = handles[BUSY];
	exec[1].handle = handles[TEST];
	if (write)
		exec[1].flags |= EXEC_OBJECT_WRITE;
	exec[2].handle = handles[BATCH];

	memset(&execbuf, 0, sizeof(execbuf));
	execbuf.buffers_ptr = (uintptr_t)exec;
	execbuf.buffer_count = 3;
	execbuf.flags = ring;
	igt_debug("Queuing handle for %s on ring %d\n",
		  write ? "writing" : "reading", ring & 0x7);
	return __gem_execbuf(fd, &execbuf) == 0;
}
コード例 #13
0
static int
test_read_crc_for_output(data_t *data, int pipe, igt_output_t *output,
			 unsigned flags)
{
	igt_display_t *display = &data->display;
	igt_plane_t *primary;
	drmModeModeInfo *mode;
	igt_pipe_crc_t *pipe_crc;
	igt_crc_t *crcs = NULL;
	int c, j;

	for (c = 0; c < ARRAY_SIZE(colors); c++) {
		char *crc_str;
		int n_crcs;

		igt_output_set_pipe(output, pipe);
		igt_display_commit(display);

		if (!output->valid) {
			igt_output_set_pipe(output, PIPE_ANY);
			return 0;
		}

		igt_debug("Clearing the fb with color (%.02lf,%.02lf,%.02lf)\n",
			  colors[c].r, colors[c].g, colors[c].b);

		mode = igt_output_get_mode(output);
		igt_create_color_fb(data->drm_fd,
					mode->hdisplay, mode->vdisplay,
					DRM_FORMAT_XRGB8888,
					LOCAL_DRM_FORMAT_MOD_NONE,
					colors[c].r,
					colors[c].g,
					colors[c].b,
					&data->fb);

		primary = igt_output_get_plane(output, 0);
		igt_plane_set_fb(primary, &data->fb);

		igt_display_commit(display);

		if (flags & TEST_NONBLOCK)
			pipe_crc = igt_pipe_crc_new_nonblock(pipe, INTEL_PIPE_CRC_SOURCE_AUTO);
		else
			pipe_crc = igt_pipe_crc_new(pipe, INTEL_PIPE_CRC_SOURCE_AUTO);

		igt_pipe_crc_start(pipe_crc);

		/* wait for N_CRCS vblanks and the corresponding N_CRCS CRCs */
		if (flags & TEST_NONBLOCK) {
			int i;

			for (i = 0; i < N_CRCS; i++)
				igt_wait_for_vblank(data->drm_fd, pipe);

			n_crcs = igt_pipe_crc_get_crcs(pipe_crc, N_CRCS * 3, &crcs);
			/* allow a one frame difference */
			igt_assert_lte(n_crcs, N_CRCS + 1);
			igt_assert_lte(N_CRCS, n_crcs + 1);
		} else {
			n_crcs = igt_pipe_crc_get_crcs(pipe_crc, N_CRCS, &crcs);
			igt_assert_eq(n_crcs, N_CRCS);
		}

		igt_pipe_crc_stop(pipe_crc);

		/*
		 * save the CRC in colors so it can be compared to the CRC of
		 * other fbs
		 */
		colors[c].crc = crcs[0];

		crc_str = igt_crc_to_string(&crcs[0]);
		igt_debug("CRC for this fb: %s\n", crc_str);
		free(crc_str);

		/* and ensure that they'are all equal, we haven't changed the fb */
		for (j = 0; j < (n_crcs - 1); j++)
			igt_assert_crc_equal(&crcs[j], &crcs[j + 1]);

		if (flags & TEST_SEQUENCE)
			for (j = 0; j < (n_crcs - 1); j++)
				igt_assert_eq(crcs[j].frame + 1, crcs[j + 1].frame);

		free(crcs);
		igt_pipe_crc_free(pipe_crc);
		igt_remove_fb(data->drm_fd, &data->fb);
		igt_plane_set_fb(primary, NULL);

		igt_output_set_pipe(output, PIPE_ANY);
	}

	return 1;
}
コード例 #14
0
static uint32_t busy_blt(int fd)
{
	const int gen = intel_gen(intel_get_drm_devid(fd));
	const int has_64bit_reloc = gen >= 8;
	struct drm_i915_gem_execbuffer2 execbuf;
	struct drm_i915_gem_exec_object2 object[2];
	struct drm_i915_gem_relocation_entry reloc[200], *r;
	uint32_t read, write;
	uint32_t *map;
	int factor = 100;
	int i = 0;

	memset(object, 0, sizeof(object));
	object[0].handle = gem_create(fd, 1024*1024);
	object[1].handle = gem_create(fd, 4096);

	r = memset(reloc, 0, sizeof(reloc));
	map = gem_mmap__cpu(fd, object[1].handle, 0, 4096, PROT_WRITE);
	gem_set_domain(fd, object[1].handle,
		       I915_GEM_DOMAIN_CPU, I915_GEM_DOMAIN_CPU);

#define COPY_BLT_CMD		(2<<29|0x53<<22|0x6)
#define BLT_WRITE_ALPHA		(1<<21)
#define BLT_WRITE_RGB		(1<<20)
	while (factor--) {
		/* XY_SRC_COPY */
		map[i++] = COPY_BLT_CMD | BLT_WRITE_ALPHA | BLT_WRITE_RGB;
		if (has_64bit_reloc)
			map[i-1] += 2;
		map[i++] = 0xcc << 16 | 1 << 25 | 1 << 24 | (4*1024);
		map[i++] = 0;
		map[i++] = 256 << 16 | 1024;

		r->offset = i * sizeof(uint32_t);
		r->target_handle = object[0].handle;
		r->read_domains = I915_GEM_DOMAIN_RENDER;
		r->write_domain = I915_GEM_DOMAIN_RENDER;
		r++;
		map[i++] = 0;
		if (has_64bit_reloc)
			map[i++] = 0;

		map[i++] = 0;
		map[i++] = 4096;

		r->offset = i * sizeof(uint32_t);
		r->target_handle = object[0].handle;
		r->read_domains = I915_GEM_DOMAIN_RENDER;
		r->write_domain = 0;
		r++;
		map[i++] = 0;
		if (has_64bit_reloc)
			map[i++] = 0;
	}
	map[i++] = MI_BATCH_BUFFER_END;
	igt_assert(i <= 4096/sizeof(uint32_t));
	igt_assert(r - reloc <= ARRAY_SIZE(reloc));
	munmap(map, 4096);

	object[1].relocs_ptr = (uintptr_t)reloc;
	object[1].relocation_count = r - reloc;

	memset(&execbuf, 0, sizeof(execbuf));
	execbuf.buffers_ptr = (unsigned long)object;
	execbuf.buffer_count = 2;
	if (gen >= 6)
		execbuf.flags = I915_EXEC_BLT;
	gem_execbuf(fd, &execbuf);

	__gem_busy(fd, object[0].handle, &read, &write);
	igt_assert_eq(read, 1 << write);
	igt_assert_eq(write, gen >= 6 ? I915_EXEC_BLT : I915_EXEC_RENDER);

	igt_debug("Created busy handle %d\n", object[0].handle);
	gem_close(fd, object[1].handle);
	return object[0].handle;
}