From patchwork Thu Jun 28 21:35:32 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Chris Wilson X-Patchwork-Id: 10495275 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id C7FA3602B3 for ; Thu, 28 Jun 2018 21:35:46 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id B6E422A808 for ; Thu, 28 Jun 2018 21:35:46 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id AB3F62A848; Thu, 28 Jun 2018 21:35:46 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-5.2 required=2.0 tests=BAYES_00, MAILING_LIST_MULTI, RCVD_IN_DNSWL_MED autolearn=ham version=3.3.1 Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher DHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id C765D2A808 for ; Thu, 28 Jun 2018 21:35:45 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id C16386EECD; Thu, 28 Jun 2018 21:35:44 +0000 (UTC) X-Original-To: intel-gfx@lists.freedesktop.org Delivered-To: intel-gfx@lists.freedesktop.org Received: from fireflyinternet.com (mail.fireflyinternet.com [109.228.58.192]) by gabe.freedesktop.org (Postfix) with ESMTPS id CC9686EEBA; Thu, 28 Jun 2018 21:35:42 +0000 (UTC) X-Default-Received-SPF: pass (skip=forwardok (res=PASS)) x-ip-name=78.156.65.138; Received: from haswell.alporthouse.com (unverified [78.156.65.138]) by fireflyinternet.com (Firefly Internet (M1)) with ESMTP id 12192918-1500050 for multiple; Thu, 28 Jun 2018 22:35:35 +0100 Received: by haswell.alporthouse.com (sSMTP sendmail emulation); Thu, 28 Jun 2018 22:35:34 +0100 From: Chris Wilson To: intel-gfx@lists.freedesktop.org Date: Thu, 28 Jun 2018 22:35:32 +0100 Message-Id: <20180628213532.22008-1-chris@chris-wilson.co.uk> X-Mailer: git-send-email 2.18.0 X-Originating-IP: 78.156.65.138 X-Country: code=GB country="United Kingdom" ip=78.156.65.138 Subject: [Intel-gfx] [PATCH i-g-t] igt/gem_exec_gttfill: Avoid pwrite into busy handle X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: igt-dev@lists.freedesktop.org MIME-Version: 1.0 Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" X-Virus-Scanned: ClamAV using ClamSMTP The goal of gem_exec_gttfill is to exercise execbuf under heavy GTT pressure (by trying to execute more objects than may fit into the GTT). We spread the same set of handles across different processes, with the result that each would occasionally stall waiting for execution of an unrelated batch, limiting the pressure we were applying. If we using a steaming write via a WC pointer, we can avoid the serialisation penalty and so submit faster. Signed-off-by: Chris Wilson Reviewed-by: Tvrtko Ursulin --- tests/gem_exec_gttfill.c | 66 +++++++++++++++++++++++++--------------- 1 file changed, 42 insertions(+), 24 deletions(-) diff --git a/tests/gem_exec_gttfill.c b/tests/gem_exec_gttfill.c index 4097e4077..efd612bb6 100644 --- a/tests/gem_exec_gttfill.c +++ b/tests/gem_exec_gttfill.c @@ -28,18 +28,25 @@ IGT_TEST_DESCRIPTION("Fill the GTT with batches."); #define BATCH_SIZE (4096<<10) -static void xchg_u32(void *array, unsigned i, unsigned j) +struct batch { + uint32_t handle; + void *ptr; +}; + +static void xchg_batch(void *array, unsigned int i, unsigned int j) { - uint32_t *u32 = array; - uint32_t tmp = u32[i]; - u32[i] = u32[j]; - u32[j] = tmp; + struct batch *batches = array; + struct batch tmp; + + tmp = batches[i]; + batches[i] = batches[j]; + batches[j] = tmp; } static void submit(int fd, int gen, struct drm_i915_gem_execbuffer2 *eb, struct drm_i915_gem_relocation_entry *reloc, - uint32_t *handles, unsigned count) + struct batch *batches, unsigned int count) { struct drm_i915_gem_exec_object2 obj; uint32_t batch[16]; @@ -80,7 +87,7 @@ static void submit(int fd, int gen, eb->buffers_ptr = to_user_pointer(&obj); for (unsigned i = 0; i < count; i++) { - obj.handle = handles[i]; + obj.handle = batches[i].handle; reloc[0].target_handle = obj.handle; reloc[1].target_handle = obj.handle; @@ -88,8 +95,8 @@ static void submit(int fd, int gen, reloc[0].presumed_offset = obj.offset; reloc[1].presumed_offset = obj.offset; - gem_write(fd, obj.handle, eb->batch_start_offset, - batch, sizeof(batch)); + memcpy(batches[i].ptr + eb->batch_start_offset, + batch, sizeof(batch)); gem_execbuf(fd, eb); } @@ -103,7 +110,7 @@ static void fillgtt(int fd, unsigned ring, int timeout) struct drm_i915_gem_execbuffer2 execbuf; struct drm_i915_gem_relocation_entry reloc[2]; volatile uint64_t *shared; - unsigned *handles; + struct batch *batches; unsigned engines[16]; unsigned nengine; unsigned engine; @@ -145,29 +152,38 @@ static void fillgtt(int fd, unsigned ring, int timeout) if (gen < 6) execbuf.flags |= I915_EXEC_SECURE; - handles = calloc(count, sizeof(handles)); - igt_assert(handles); - for (unsigned i = 0; i < count; i++) - handles[i] = gem_create(fd, BATCH_SIZE); + batches = calloc(count, sizeof(*batches)); + igt_assert(batches); + for (unsigned i = 0; i < count; i++) { + batches[i].handle = gem_create(fd, BATCH_SIZE); + batches[i].ptr = + __gem_mmap__wc(fd, batches[i].handle, + 0, BATCH_SIZE, PROT_WRITE); + if (!batches[i].ptr) { + batches[i].ptr = + __gem_mmap__gtt(fd, batches[i].handle, + BATCH_SIZE, PROT_WRITE); + } + igt_require(batches[i].ptr); + } /* Flush all memory before we start the timer */ - submit(fd, gen, &execbuf, reloc, handles, count); + submit(fd, gen, &execbuf, reloc, batches, count); igt_fork(child, nengine) { uint64_t cycles = 0; hars_petruska_f54_1_random_perturb(child); - igt_permute_array(handles, count, xchg_u32); + igt_permute_array(batches, count, xchg_batch); execbuf.batch_start_offset = child*64; execbuf.flags |= engines[child]; igt_until_timeout(timeout) { - submit(fd, gen, &execbuf, reloc, handles, count); + submit(fd, gen, &execbuf, reloc, batches, count); for (unsigned i = 0; i < count; i++) { - uint32_t handle = handles[i]; - uint64_t buf[2]; + uint64_t offset, delta; - gem_read(fd, handle, reloc[1].offset, &buf[0], sizeof(buf[0])); - gem_read(fd, handle, reloc[0].delta, &buf[1], sizeof(buf[1])); - igt_assert_eq_u64(buf[0], buf[1]); + offset = *(uint64_t *)(batches[i].ptr + reloc[1].offset); + delta = *(uint64_t *)(batches[i].ptr + reloc[0].delta); + igt_assert_eq_u64(offset, delta); } cycles++; } @@ -176,8 +192,10 @@ static void fillgtt(int fd, unsigned ring, int timeout) } igt_waitchildren(); - for (unsigned i = 0; i < count; i++) - gem_close(fd, handles[i]); + for (unsigned i = 0; i < count; i++) { + munmap(batches[i].ptr, BATCH_SIZE); + gem_close(fd, batches[i].handle); + } shared[nengine] = 0; for (unsigned i = 0; i < nengine; i++)