Message ID | 1444896344-34927-1-git-send-email-derek.j.morton@intel.com (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
On 15 October 2015 at 09:05, Derek Morton <derek.j.morton@intel.com> wrote: > This test is based on gem_exec_nop but submits nop batch buffers concurrently > from different threads to check for ring hangs and other issues during > concurrent submissions. Is there any reason not to include this as extra subtests in gem_exec_nop so that related tests are grouped together? > > Signed-off-by: Derek Morton <derek.j.morton@intel.com> > --- > tests/.gitignore | 1 + > tests/Makefile.sources | 1 + > tests/gem_exec_nop_concurrent.c | 172 ++++++++++++++++++++++++++++++++++++++++ > 3 files changed, 174 insertions(+) > create mode 100644 tests/gem_exec_nop_concurrent.c > > diff --git a/tests/.gitignore b/tests/.gitignore > index dc8bb53..0ad36f3 100644 > --- a/tests/.gitignore > +++ b/tests/.gitignore > @@ -46,6 +46,7 @@ gem_exec_blt > gem_exec_faulting_reloc > gem_exec_lut_handle > gem_exec_nop > +gem_exec_nop_concurrent > gem_exec_params > gem_exec_parse > gem_fd_exhaustion > diff --git a/tests/Makefile.sources b/tests/Makefile.sources > index 2e2e088..aece831 100644 > --- a/tests/Makefile.sources > +++ b/tests/Makefile.sources > @@ -27,6 +27,7 @@ TESTS_progs_M = \ > gem_exec_bad_domains \ > gem_exec_faulting_reloc \ > gem_exec_nop \ > + gem_exec_nop_concurrent \ > gem_exec_params \ > gem_exec_parse \ > gem_fenced_exec_thrash \ > diff --git a/tests/gem_exec_nop_concurrent.c b/tests/gem_exec_nop_concurrent.c > new file mode 100644 > index 0000000..578f651 > --- /dev/null > +++ b/tests/gem_exec_nop_concurrent.c > @@ -0,0 +1,172 @@ > +/* > + * Copyright © 2015 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: > + * Derek Morton <derek.j.morton@intel.com> > + * > + * This test is based on gem_exec_nop but submits nop batch buffers concurrently > + * from different threads to check for ring hangs and other issues during > + * concurrent submissions. > + * > + */ > + > +#include "igt.h" > +#include <unistd.h> > +#include <stdlib.h> > +#include <stdint.h> > +#include <stdio.h> > +#include <string.h> > +#include <fcntl.h> > +#include <inttypes.h> > +#include <errno.h> > +#include <sys/stat.h> > +#include <sys/ioctl.h> > +#include <sys/time.h> > +#include <time.h> > +#include "drm.h" > + > +#define LOCAL_I915_EXEC_NO_RELOC (1<<11) > +#define LOCAL_I915_EXEC_HANDLE_LUT (1<<12) > + > +#define LOCAL_I915_EXEC_VEBOX (4<<0) > + > +IGT_TEST_DESCRIPTION( > + "This Test will submit nop batch buffers concurrently to the same ring " > + "and different rings in an attempt to trigger ring hangs."); > + > +const uint32_t batch[2] = {MI_BATCH_BUFFER_END}; > + > +struct ring > +{ > + unsigned ring_id; > + const char *ring_name; > + bool direction; > +}; > + > +static void loop(int fd, uint32_t handle, int child_nbr, struct ring* ring, bool up) > +{ > + struct drm_i915_gem_execbuffer2 execbuf; > + struct drm_i915_gem_exec_object2 gem_exec[1]; > + int count; > + int max_count = SLOW_QUICK(15, 4); > + > + gem_require_ring(fd, ring->ring_id); > + > + memset(&gem_exec, 0, sizeof(gem_exec)); > + gem_exec[0].handle = handle; > + > + memset(&execbuf, 0, sizeof(execbuf)); > + execbuf.buffers_ptr = (uintptr_t)gem_exec; > + execbuf.buffer_count = 1; > + execbuf.flags = ring->ring_id; > + execbuf.flags |= LOCAL_I915_EXEC_HANDLE_LUT; > + execbuf.flags |= LOCAL_I915_EXEC_NO_RELOC; > + if (drmIoctl(fd, DRM_IOCTL_I915_GEM_EXECBUFFER2, &execbuf)) { > + execbuf.flags = ring->ring_id; > + do_ioctl(fd, DRM_IOCTL_I915_GEM_EXECBUFFER2, &execbuf); > + } > + gem_sync(fd, handle); > + > + for (count = 0; count <= max_count; count++) { > + const int reps = 7; > + int n, nbr_loops; > + > + if (up) > + nbr_loops = 1 << count; > + else > + nbr_loops = 1 << (max_count - count); > + > + igt_info("Thread %d: starting submitting batches of %d batch buffers (ring=%s)\n", > + child_nbr, nbr_loops, ring->ring_name); > + fflush(stdout); > + > + for (n = 0; n < reps; n++) { > + int loops = nbr_loops; > + > + while (loops--) > + do_ioctl(fd, DRM_IOCTL_I915_GEM_EXECBUFFER2, &execbuf); > + gem_sync(fd, handle); > + } > + > + igt_info("Thread %d: finished submitting batches of %d batch buffers (ring=%s)\n", > + child_nbr, nbr_loops, ring->ring_name); > + fflush(stdout); > + } > +} > + > +static void run_forked(struct ring rings[]) > +{ > + int nbr_rings = 0; > + while (rings[nbr_rings].ring_name != NULL) > + nbr_rings++; > + > + igt_fork(child, nbr_rings) { > + int fd; > + uint32_t handle; > + > + fd = drm_open_driver(DRIVER_INTEL); > + > + handle = gem_create(fd, 4096); > + gem_write(fd, handle, 0, batch, sizeof(batch)); > + > + igt_info("Starting thread %d on ring %s\n", child, rings[child].ring_name); > + fflush(stdout); > + loop(fd, handle, child, &rings[child], rings[child].direction); > + > + gem_close(fd, handle); > + > + close(fd); > + } > + igt_waitchildren(); > +} > + > +igt_main > +{ > + struct ring all_rings[] = { > + {I915_EXEC_RENDER, "render", 1}, > + {I915_EXEC_BSD, "bsd", 1}, > + {I915_EXEC_BLT, "blt", 1}, > + {LOCAL_I915_EXEC_VEBOX, "vebox", 1}, > + { 0, NULL, 0 }, > + }, > + rings[] = { > + { 0, NULL, 1 }, > + { 0, NULL, 0 }, > + { 0, NULL, 0 }, > + }, *t1, *t2; > + > + for (t1 = all_rings; t1->ring_name; t1++) { > + rings[0].ring_id = t1->ring_id; > + rings[0].ring_name = t1->ring_name; > + > + for (t2 = all_rings; t2->ring_name; t2++) { > + rings[1].ring_id = t2->ring_id; > + rings[1].ring_name = t2->ring_name; > + > + igt_subtest_f("%s-%s",t1->ring_name, t2->ring_name) > + run_forked(rings); > + } > + } > + igt_subtest("all-rings") > + run_forked(all_rings); > + > +} > -- > 1.9.1 > > _______________________________________________ > Intel-gfx mailing list > Intel-gfx@lists.freedesktop.org > http://lists.freedesktop.org/mailman/listinfo/intel-gfx
On Fri, Oct 16, 2015 at 02:00:42PM +0100, Thomas Wood wrote: > On 15 October 2015 at 09:05, Derek Morton <derek.j.morton@intel.com> wrote: > > This test is based on gem_exec_nop but submits nop batch buffers concurrently > > from different threads to check for ring hangs and other issues during > > concurrent submissions. > > Is there any reason not to include this as extra subtests in > gem_exec_nop so that related tests are grouped together? It's a better fit for ringfill. It already does concurrent clients to the same ring in order to catch exactly the same bugs as described here, so extending it to fill all rings concurrently should be easy. -Chris
> >On Fri, Oct 16, 2015 at 02:00:42PM +0100, Thomas Wood wrote: >> On 15 October 2015 at 09:05, Derek Morton <derek.j.morton@intel.com> wrote: >> > This test is based on gem_exec_nop but submits nop batch buffers >> > concurrently from different threads to check for ring hangs and >> > other issues during concurrent submissions. >> >> Is there any reason not to include this as extra subtests in >> gem_exec_nop so that related tests are grouped together? > gem_exec_nop takes 25 minutes to run on android (with the speed improvement patch I submitted yesterday) gem_exec_nop_concurrent takes a similar time. I would strongly resist combining the two into a test that takes nearly an hour for us to run. >It's a better fit for ringfill. It already does concurrent clients to the same ring in order to catch exactly the same bugs as described here, so extending it to fill all rings concurrently should be easy. I will take a look at gem_ringfill //Derek >-Chris > >-- >Chris Wilson, Intel Open Source Technology Centre >
diff --git a/tests/.gitignore b/tests/.gitignore index dc8bb53..0ad36f3 100644 --- a/tests/.gitignore +++ b/tests/.gitignore @@ -46,6 +46,7 @@ gem_exec_blt gem_exec_faulting_reloc gem_exec_lut_handle gem_exec_nop +gem_exec_nop_concurrent gem_exec_params gem_exec_parse gem_fd_exhaustion diff --git a/tests/Makefile.sources b/tests/Makefile.sources index 2e2e088..aece831 100644 --- a/tests/Makefile.sources +++ b/tests/Makefile.sources @@ -27,6 +27,7 @@ TESTS_progs_M = \ gem_exec_bad_domains \ gem_exec_faulting_reloc \ gem_exec_nop \ + gem_exec_nop_concurrent \ gem_exec_params \ gem_exec_parse \ gem_fenced_exec_thrash \ diff --git a/tests/gem_exec_nop_concurrent.c b/tests/gem_exec_nop_concurrent.c new file mode 100644 index 0000000..578f651 --- /dev/null +++ b/tests/gem_exec_nop_concurrent.c @@ -0,0 +1,172 @@ +/* + * Copyright © 2015 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: + * Derek Morton <derek.j.morton@intel.com> + * + * This test is based on gem_exec_nop but submits nop batch buffers concurrently + * from different threads to check for ring hangs and other issues during + * concurrent submissions. + * + */ + +#include "igt.h" +#include <unistd.h> +#include <stdlib.h> +#include <stdint.h> +#include <stdio.h> +#include <string.h> +#include <fcntl.h> +#include <inttypes.h> +#include <errno.h> +#include <sys/stat.h> +#include <sys/ioctl.h> +#include <sys/time.h> +#include <time.h> +#include "drm.h" + +#define LOCAL_I915_EXEC_NO_RELOC (1<<11) +#define LOCAL_I915_EXEC_HANDLE_LUT (1<<12) + +#define LOCAL_I915_EXEC_VEBOX (4<<0) + +IGT_TEST_DESCRIPTION( + "This Test will submit nop batch buffers concurrently to the same ring " + "and different rings in an attempt to trigger ring hangs."); + +const uint32_t batch[2] = {MI_BATCH_BUFFER_END}; + +struct ring +{ + unsigned ring_id; + const char *ring_name; + bool direction; +}; + +static void loop(int fd, uint32_t handle, int child_nbr, struct ring* ring, bool up) +{ + struct drm_i915_gem_execbuffer2 execbuf; + struct drm_i915_gem_exec_object2 gem_exec[1]; + int count; + int max_count = SLOW_QUICK(15, 4); + + gem_require_ring(fd, ring->ring_id); + + memset(&gem_exec, 0, sizeof(gem_exec)); + gem_exec[0].handle = handle; + + memset(&execbuf, 0, sizeof(execbuf)); + execbuf.buffers_ptr = (uintptr_t)gem_exec; + execbuf.buffer_count = 1; + execbuf.flags = ring->ring_id; + execbuf.flags |= LOCAL_I915_EXEC_HANDLE_LUT; + execbuf.flags |= LOCAL_I915_EXEC_NO_RELOC; + if (drmIoctl(fd, DRM_IOCTL_I915_GEM_EXECBUFFER2, &execbuf)) { + execbuf.flags = ring->ring_id; + do_ioctl(fd, DRM_IOCTL_I915_GEM_EXECBUFFER2, &execbuf); + } + gem_sync(fd, handle); + + for (count = 0; count <= max_count; count++) { + const int reps = 7; + int n, nbr_loops; + + if (up) + nbr_loops = 1 << count; + else + nbr_loops = 1 << (max_count - count); + + igt_info("Thread %d: starting submitting batches of %d batch buffers (ring=%s)\n", + child_nbr, nbr_loops, ring->ring_name); + fflush(stdout); + + for (n = 0; n < reps; n++) { + int loops = nbr_loops; + + while (loops--) + do_ioctl(fd, DRM_IOCTL_I915_GEM_EXECBUFFER2, &execbuf); + gem_sync(fd, handle); + } + + igt_info("Thread %d: finished submitting batches of %d batch buffers (ring=%s)\n", + child_nbr, nbr_loops, ring->ring_name); + fflush(stdout); + } +} + +static void run_forked(struct ring rings[]) +{ + int nbr_rings = 0; + while (rings[nbr_rings].ring_name != NULL) + nbr_rings++; + + igt_fork(child, nbr_rings) { + int fd; + uint32_t handle; + + fd = drm_open_driver(DRIVER_INTEL); + + handle = gem_create(fd, 4096); + gem_write(fd, handle, 0, batch, sizeof(batch)); + + igt_info("Starting thread %d on ring %s\n", child, rings[child].ring_name); + fflush(stdout); + loop(fd, handle, child, &rings[child], rings[child].direction); + + gem_close(fd, handle); + + close(fd); + } + igt_waitchildren(); +} + +igt_main +{ + struct ring all_rings[] = { + {I915_EXEC_RENDER, "render", 1}, + {I915_EXEC_BSD, "bsd", 1}, + {I915_EXEC_BLT, "blt", 1}, + {LOCAL_I915_EXEC_VEBOX, "vebox", 1}, + { 0, NULL, 0 }, + }, + rings[] = { + { 0, NULL, 1 }, + { 0, NULL, 0 }, + { 0, NULL, 0 }, + }, *t1, *t2; + + for (t1 = all_rings; t1->ring_name; t1++) { + rings[0].ring_id = t1->ring_id; + rings[0].ring_name = t1->ring_name; + + for (t2 = all_rings; t2->ring_name; t2++) { + rings[1].ring_id = t2->ring_id; + rings[1].ring_name = t2->ring_name; + + igt_subtest_f("%s-%s",t1->ring_name, t2->ring_name) + run_forked(rings); + } + } + igt_subtest("all-rings") + run_forked(all_rings); + +}
This test is based on gem_exec_nop but submits nop batch buffers concurrently from different threads to check for ring hangs and other issues during concurrent submissions. Signed-off-by: Derek Morton <derek.j.morton@intel.com> --- tests/.gitignore | 1 + tests/Makefile.sources | 1 + tests/gem_exec_nop_concurrent.c | 172 ++++++++++++++++++++++++++++++++++++++++ 3 files changed, 174 insertions(+) create mode 100644 tests/gem_exec_nop_concurrent.c