diff options
author | Daniel Vetter <daniel.vetter@ffwll.ch> | 2013-09-04 14:08:10 +0200 |
---|---|---|
committer | Daniel Vetter <daniel.vetter@ffwll.ch> | 2013-09-04 14:08:10 +0200 |
commit | 52221651ab2bd2994a9e1d97f717ade432430c91 (patch) | |
tree | 98a420f886a80b148eb95ccede17892180494fb7 | |
parent | 0550092c9a6440536c6070cdc447ed83f3062896 (diff) |
tests/gem_pipe_control_store_loop: Add subtest for reused buffers
This exercises the slightly faulty kernel w/a that Eric fixed in
commit e844b990b1df9242bb91b7d490552f3198946838
Author: Eric Anholt <eric@anholt.net>
Date: Tue Jul 31 15:35:01 2012 -0700
drm/i915: Don't forget to apply SNB PIPE_CONTROL GTT workaround.
If a buffer that was the target of a PIPE_CONTROL from userland was a
reused one that hadn't been evicted which had not previously had this
workaround applied, then the early return for a correct
presumed_offset in this function meant we would not bind it into the
GTT and the write would land somewhere else.
Fixes reproducible failures with GL_EXT_timer_query usage in apitrace,
and I also expect it to fix the intermittent OQ issues on snb that
danvet's been working on.
Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=48019
Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=52932
Signed-off-by: Eric Anholt <eric@anholt.net>
Reviewed-by: Chris Wilson <chris@chris-wilson.co.uk>
Reviewed-by: Carl Worth <cworth@cworth.org>
Tested-by: Carl Worth <cworth@cworth.org>
Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
-rw-r--r-- | tests/gem_pipe_control_store_loop.c | 101 |
1 files changed, 56 insertions, 45 deletions
diff --git a/tests/gem_pipe_control_store_loop.c b/tests/gem_pipe_control_store_loop.c index b87e9435..9759d87c 100644 --- a/tests/gem_pipe_control_store_loop.c +++ b/tests/gem_pipe_control_store_loop.c @@ -63,7 +63,7 @@ uint32_t devid; /* Like the store dword test, but we create new command buffers each time */ static void -store_pipe_control_loop(void) +store_pipe_control_loop(bool preuse_buffer) { int i, val = 0; uint32_t *buf; @@ -78,6 +78,29 @@ store_pipe_control_loop(void) igt_fail(-1); } + if (preuse_buffer) { + BEGIN_BATCH(6); + OUT_BATCH(XY_COLOR_BLT_CMD | COLOR_BLT_WRITE_ALPHA | XY_COLOR_BLT_WRITE_RGB); + OUT_BATCH((3 << 24) | (0xf0 << 16) | 64); + OUT_BATCH(0); + OUT_BATCH(1 << 16 | 1); + + /* + * IMPORTANT: We need to preuse the buffer in a + * different domain than what the pipe control write + * (and kernel wa) uses! + */ + OUT_RELOC(target_bo, + I915_GEM_DOMAIN_RENDER, I915_GEM_DOMAIN_RENDER, + 0); + OUT_BATCH(0xdeadbeef); + ADVANCE_BATCH(); + + intel_batchbuffer_flush(batch); + igt_assert(target_bo->offset != 0); + } else + igt_assert(target_bo->offset == 0); + /* gem_storedw_batches_loop.c is a bit overenthusiastic with * creating new batchbuffers - with buffer reuse disabled, the * support code will do that for us. */ @@ -118,66 +141,54 @@ store_pipe_control_loop(void) drm_intel_bo_map(target_bo, 1); buf = target_bo->virtual; - if (buf[0] != val) { - fprintf(stderr, - "value mismatch: cur 0x%08x, stored 0x%08x\n", - buf[0], val); - igt_fail(-1); - } - buf[0] = 0; /* let batch write it again */ - drm_intel_bo_unmap(target_bo); + igt_assert(buf[0] == val); + drm_intel_bo_unmap(target_bo); + /* Make doublesure that this buffer won't get reused. */ + drm_intel_bo_disable_reuse(target_bo); drm_intel_bo_unreference(target_bo); val++; } - - printf("completed %d writes successfully\n", i); } +int fd; + int main(int argc, char **argv) { - int fd; + igt_subtest_init(argc, argv); - if (argc != 1) { - fprintf(stderr, "usage: %s\n", argv[0]); - igt_fail(-1); - } + igt_fixture { + fd = drm_open_any(); + devid = intel_get_drm_devid(fd); - fd = drm_open_any(); - devid = intel_get_drm_devid(fd); + bufmgr = drm_intel_bufmgr_gem_init(fd, 4096); + igt_assert(bufmgr); - bufmgr = drm_intel_bufmgr_gem_init(fd, 4096); - if (!bufmgr) { - fprintf(stderr, "failed to init libdrm\n"); - igt_fail(-1); - } + igt_skip_on(IS_GEN2(devid) || IS_GEN3(devid)); + igt_skip_on(devid == PCI_CHIP_I965_G); /* has totally broken pipe control */ - if (IS_GEN2(devid) || IS_GEN3(devid)) { - fprintf(stderr, "no pipe_control on gen2/3\n"); - return 77; - } - if (devid == PCI_CHIP_I965_G) { - fprintf(stderr, "pipe_control totally broken on i965\n"); - return 77; - } - /* IMPORTANT: No call to - * drm_intel_bufmgr_gem_enable_reuse(bufmgr); - * here because we wan't to have fresh buffers (to trash the tlb) - * every time! */ - - batch = intel_batchbuffer_alloc(bufmgr, devid); - if (!batch) { - fprintf(stderr, "failed to create batch buffer\n"); - igt_fail(-1); + /* IMPORTANT: No call to + * drm_intel_bufmgr_gem_enable_reuse(bufmgr); + * here because we wan't to have fresh buffers (to trash the tlb) + * every time! */ + + batch = intel_batchbuffer_alloc(bufmgr, devid); + igt_assert(batch); } - store_pipe_control_loop(); + igt_subtest("fresh-buffer") + store_pipe_control_loop(false); - intel_batchbuffer_free(batch); - drm_intel_bufmgr_destroy(bufmgr); + igt_subtest("reused-buffer") + store_pipe_control_loop(true); - close(fd); + igt_fixture { + intel_batchbuffer_free(batch); + drm_intel_bufmgr_destroy(bufmgr); + + close(fd); + } - return 0; + igt_exit(); } |