summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/igt_aux.h2
-rw-r--r--lib/intel_os.c53
-rw-r--r--tests/gem_concurrent_all.c68
3 files changed, 85 insertions, 38 deletions
diff --git a/lib/igt_aux.h b/lib/igt_aux.h
index 95028665..82bd5962 100644
--- a/lib/igt_aux.h
+++ b/lib/igt_aux.h
@@ -86,6 +86,8 @@ uint64_t intel_get_avail_ram_mb(void);
uint64_t intel_get_total_ram_mb(void);
uint64_t intel_get_total_swap_mb(void);
+int __intel_check_memory(uint32_t count, uint64_t size, unsigned mode,
+ uint64_t *out_required, uint64_t *out_total);
void intel_require_memory(uint32_t count, uint64_t size, unsigned mode);
#define CHECK_RAM 0x1
#define CHECK_SWAP 0x2
diff --git a/lib/intel_os.c b/lib/intel_os.c
index 06361f4c..64e37222 100644
--- a/lib/intel_os.c
+++ b/lib/intel_os.c
@@ -192,6 +192,38 @@ intel_get_total_swap_mb(void)
return retval / (1024*1024);
}
+int __intel_check_memory(uint32_t count, uint64_t size, unsigned mode,
+ uint64_t *out_required, uint64_t *out_total)
+{
+/* rough estimate of how many bytes the kernel requires to track each object */
+#define KERNEL_BO_OVERHEAD 512
+ uint64_t required, total;
+
+ required = count;
+ required *= size + KERNEL_BO_OVERHEAD;
+ required = ALIGN(required, 4096);
+
+ igt_debug("Checking %'u surfaces of size %'llu bytes (total %'llu) against %s%s\n",
+ count, (long long)size, (long long)required,
+ mode & (CHECK_RAM | CHECK_SWAP) ? "RAM" : "",
+ mode & CHECK_SWAP ? " + swap": "");
+
+ total = 0;
+ if (mode & (CHECK_RAM | CHECK_SWAP))
+ total += intel_get_avail_ram_mb();
+ if (mode & CHECK_SWAP)
+ total += intel_get_total_swap_mb();
+ total *= 1024 * 1024;
+
+ if (out_required)
+ *out_required = required;
+
+ if (out_total)
+ *out_total = total;
+
+ return required < total;
+}
+
/**
* intel_require_memory:
* @count: number of surfaces that will be created
@@ -217,27 +249,10 @@ intel_get_total_swap_mb(void)
*/
void intel_require_memory(uint32_t count, uint64_t size, unsigned mode)
{
-/* rough estimate of how many bytes the kernel requires to track each object */
-#define KERNEL_BO_OVERHEAD 512
uint64_t required, total;
- required = count;
- required *= size + KERNEL_BO_OVERHEAD;
- required = ALIGN(required, 4096);
-
- igt_debug("Checking %'u surfaces of size %'llu bytes (total %'llu) against %s%s\n",
- count, (long long)size, (long long)required,
- mode & (CHECK_RAM | CHECK_SWAP) ? "RAM" : "",
- mode & CHECK_SWAP ? " + swap": "");
-
- total = 0;
- if (mode & (CHECK_RAM | CHECK_SWAP))
- total += intel_get_avail_ram_mb();
- if (mode & CHECK_SWAP)
- total += intel_get_total_swap_mb();
- total *= 1024 * 1024;
-
- igt_skip_on_f(total <= required,
+ igt_skip_on_f(!__intel_check_memory(count, size, mode,
+ &required, &total),
"Estimated that we need %'llu bytes for the test, but only have %'llu bytes available (%s%s)\n",
(long long)required, (long long)total,
mode & (CHECK_RAM | CHECK_SWAP) ? "RAM" : "",
diff --git a/tests/gem_concurrent_all.c b/tests/gem_concurrent_all.c
index 558b9c13..a7db23cb 100644
--- a/tests/gem_concurrent_all.c
+++ b/tests/gem_concurrent_all.c
@@ -155,9 +155,9 @@ static bool can_create_stolen(void)
static drm_intel_bo *
(*create_func)(drm_intel_bufmgr *bufmgr, uint64_t size);
-static void create_cpu_require(void)
+static bool create_cpu_require(void)
{
- igt_require(create_func != create_stolen_bo);
+ return create_func != create_stolen_bo;
}
static drm_intel_bo *
@@ -375,7 +375,7 @@ gpu_cmp_bo(drm_intel_bo *bo, uint32_t val, int width, int height, drm_intel_bo *
const struct access_mode {
const char *name;
- void (*require)(void);
+ bool (*require)(void);
void (*set_bo)(drm_intel_bo *bo, uint32_t val, int w, int h);
void (*cmp_bo)(drm_intel_bo *bo, uint32_t val, int w, int h, drm_intel_bo *tmp);
drm_intel_bo *(*create_bo)(drm_intel_bufmgr *bufmgr, int width, int height);
@@ -1321,24 +1321,22 @@ run_basic_modes(const char *prefix,
}
static void
-run_modes(const char *style, const struct access_mode *mode)
+run_modes(const char *style, const struct access_mode *mode, unsigned allow_mem)
{
- if (mode->require)
- mode->require();
-
- igt_debug("%s: using 2x%d buffers, each 1MiB\n", style, num_buffers);
- intel_require_memory(2*num_buffers, 1024*1024, CHECK_RAM);
+ if (mode->require && !mode->require())
+ return;
- if (all) {
- run_basic_modes(style, mode, "", run_single);
+ igt_debug("%s: using 2x%d buffers, each 1MiB\n",
+ style, num_buffers);
+ if (!__intel_check_memory(2*num_buffers, 1024*1024, allow_mem,
+ NULL, NULL))
+ return;
- igt_fork_signal_helper();
- run_basic_modes(style, mode, "-interruptible", run_interruptible);
- igt_stop_signal_helper();
- }
+ run_basic_modes(style, mode, "", run_single);
+ run_basic_modes(style, mode, "-forked", run_forked);
igt_fork_signal_helper();
- run_basic_modes(style, mode, "-forked", run_forked);
+ run_basic_modes(style, mode, "-interruptible", run_interruptible);
run_basic_modes(style, mode, "-bomb", run_bomb);
igt_stop_signal_helper();
}
@@ -1355,6 +1353,8 @@ igt_main
{ "stolen-", create_stolen_bo, can_create_stolen },
{ NULL, NULL }
}, *c;
+ uint64_t pin_sz = 0;
+ void *pinned = NULL;
int i;
igt_skip_on_simulation();
@@ -1381,7 +1381,7 @@ igt_main
if (c->require()) {
snprintf(name, sizeof(name), "%s%s", c->name, "small");
for (i = 0; i < ARRAY_SIZE(access_modes); i++)
- run_modes(name, &access_modes[i]);
+ run_modes(name, &access_modes[i], CHECK_RAM);
}
igt_fixture {
@@ -1391,7 +1391,7 @@ igt_main
if (c->require()) {
snprintf(name, sizeof(name), "%s%s", c->name, "thrash");
for (i = 0; i < ARRAY_SIZE(access_modes); i++)
- run_modes(name, &access_modes[i]);
+ run_modes(name, &access_modes[i], CHECK_RAM);
}
igt_fixture {
@@ -1401,7 +1401,37 @@ igt_main
if (c->require()) {
snprintf(name, sizeof(name), "%s%s", c->name, "full");
for (i = 0; i < ARRAY_SIZE(access_modes); i++)
- run_modes(name, &access_modes[i]);
+ run_modes(name, &access_modes[i], CHECK_RAM);
+ }
+
+ igt_fixture {
+ num_buffers = gem_mappable_aperture_size() / (1024 * 1024);
+ pin_sz = intel_get_avail_ram_mb() - num_buffers;
+
+ igt_debug("Pinning %ld MiB\n", pin_sz);
+ pin_sz *= 1024 * 1024;
+
+ if (posix_memalign(&pinned, 4096, pin_sz) ||
+ mlock(pinned, pin_sz) ||
+ madvise(pinned, pin_sz, MADV_DONTFORK)) {
+ free(pinned);
+ pinned = NULL;
+ }
+ igt_require(pinned);
+ }
+
+ if (c->require()) {
+ snprintf(name, sizeof(name), "%s%s", c->name, "swap");
+ for (i = 0; i < ARRAY_SIZE(access_modes); i++)
+ run_modes(name, &access_modes[i], CHECK_RAM | CHECK_SWAP);
+ }
+
+ igt_fixture {
+ if (pinned) {
+ munlock(pinned, pin_sz);
+ free(pinned);
+ pinned = NULL;
+ }
}
}
}