[Intel-gfx] [PATCH 2/2] lib/igt_core.c: disable lowmemorykiller during tests

tim.gore at intel.com tim.gore at intel.com
Fri Sep 26 11:27:24 CEST 2014


From: Tim Gore <tim.gore at intel.com>

Several IGT tests put a lot of pressure on memory and
when running these tests on Android they tend to get
killed by the lowmemorykiller. The lowmemorykiller really
is not usefull in this context and is just preventing the
test from doing its job. So this commit disables the
lowmemorykiller by writing "9999" to its oom adj parameter
which means it will never "select" any process to kill.
The normal linux oom killer is still there to protect
the kernel.
NOTE: if a test is not well behaved, it could exit
without re-enabling the lowmemorykiller. This should
be mostly benign, especially since running these tests
requires the Android system to be stopped, and restarting
the Android system automatically re-enstates the default
lowmemorykiller oom adj parameters.

Signed-off-by: Tim Gore <tim.gore at intel.com>
---
 lib/igt_core.c | 68 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 68 insertions(+)

diff --git a/lib/igt_core.c b/lib/igt_core.c
index 9344815..9ef39ab 100644
--- a/lib/igt_core.c
+++ b/lib/igt_core.c
@@ -326,6 +326,67 @@ static void print_usage(const char *help_str, bool output_on_stderr)
 		fprintf(f, "%s\n", help_str);
 }
 
+
+/* Some of the IGT tests put quite a lot of pressure on memory and when
+ * running on Android they are sometimes killed by the Android low memory killer.
+ * The low memory killer really isn't usefull in this context and has no
+ * interaction with the gpu driver that we are testing, so the following
+ * function is used to disable it by modifying one of its module parameters.
+ * We still have the normal linux oom killer to protect the kernel.
+ * Apparently it is also possible for the lowmemorykiller to get included
+ * in some linux distributions; so rather than check for Android we directly
+ * check for the existence of the module parameter we want to adjust.
+ */
+void low_mem_killer_disable(bool disable)
+{
+	static const char* adj_fname="/sys/module/lowmemorykiller/parameters/adj";
+	static const char no_lowmem_killer[] = "9999";
+	int fd;
+	struct stat buf;
+	/* The following must persist across invocations */
+	static char prev_adj_scores[256];
+	static int adj_scores_len = 0;
+	static bool is_disabled = false;
+
+	/* capture the permissions bits for the lowmemkiller adj pseudo-file.
+	   Bail out if the stat fails; it probably means that there is no
+	   lowmemorykiller, but in any case we're doomed. */
+	if (stat (adj_fname, &buf))
+	{
+		igt_assert(errno == ENOENT);
+		return;
+	}
+	/* make sure the file can be read/written - by default it is write-only */
+	chmod (adj_fname, S_IRUSR | S_IWUSR);
+
+	if (disable && (!is_disabled))
+	{
+		/* read the current oom adj parameters for lowmemorykiller */
+		fd = open(adj_fname, O_RDWR);
+		igt_assert(fd != -1);
+		adj_scores_len = read(fd, (void*)prev_adj_scores, 255);
+
+		/* writing 9999 to this module parameter effectively diables the
+		 * low memory killer. This is not a real file, so we dont need to
+		 * seek to the start or truncate it */
+		write(fd, no_lowmem_killer, sizeof(no_lowmem_killer));
+		close(fd);
+		is_disabled = true;
+	}
+	else if ((!disable) && is_disabled)
+	{
+		/* just re-enstate the original settings */
+		fd = open(adj_fname, O_WRONLY);
+		igt_assert(fd != -1);
+		write(fd, prev_adj_scores, adj_scores_len);
+		close(fd);
+		is_disabled = false;
+	}
+
+	/* re-enstate the file permissions */
+	chmod (adj_fname, buf.st_mode);
+}
+
 static void oom_adjust_for_doom(void)
 {
 	int fd;
@@ -334,6 +395,10 @@ static void oom_adjust_for_doom(void)
 	fd = open("/proc/self/oom_score_adj", O_WRONLY);
 	igt_assert(fd != -1);
 	igt_assert(write(fd, always_kill, sizeof(always_kill)) == sizeof(always_kill));
+	close(fd);
+
+	/* disable the low memory killer (not oom) if present. */
+	low_mem_killer_disable(true);
 }
 
 static int common_init(int argc, char **argv,
@@ -848,6 +913,9 @@ void igt_exit(void)
 {
 	igt_exit_called = true;
 
+	/* re-enstate the low mem killer if it exists */
+	low_mem_killer_disable(false);
+
 	if (run_single_subtest && !run_single_subtest_found) {
 		igt_warn("Unknown subtest: %s\n", run_single_subtest);
 		exit(IGT_EXIT_INVALID);
-- 
2.0.3




More information about the Intel-gfx mailing list