Commit f46f5762 authored by Kees Cook's avatar Kees Cook Committed by Shuah Khan

selftests/harness: Move test child waiting logic

In order to better handle timeout failures, rearrange the child waiting
logic into a separate function. This is mostly a copy/paste with an
indentation change. To handle pid tracking, a new field is added for
the child pid. Also move the alarm() pairing into the function.
Signed-off-by: default avatarKees Cook <keescook@chromium.org>
Signed-off-by: default avatarShuah Khan <skhan@linuxfoundation.org>
parent fb0bb395
...@@ -635,6 +635,7 @@ ...@@ -635,6 +635,7 @@
struct __test_metadata { struct __test_metadata {
const char *name; const char *name;
void (*fn)(struct __test_metadata *); void (*fn)(struct __test_metadata *);
pid_t pid; /* pid of test when being run */
int termsig; int termsig;
int passed; int passed;
int trigger; /* extra handler after the evaluation */ int trigger; /* extra handler after the evaluation */
...@@ -695,26 +696,14 @@ static inline int __bail(int for_realz, bool no_print, __u8 step) ...@@ -695,26 +696,14 @@ static inline int __bail(int for_realz, bool no_print, __u8 step)
return 0; return 0;
} }
void __run_test(struct __test_metadata *t) void __wait_for_test(struct __test_metadata *t)
{ {
pid_t child_pid;
int status; int status;
t->passed = 1;
t->trigger = 0;
printf("[ RUN ] %s\n", t->name);
alarm(t->timeout); alarm(t->timeout);
child_pid = fork(); waitpid(t->pid, &status, 0);
if (child_pid < 0) { alarm(0);
printf("ERROR SPAWNING TEST CHILD\n");
t->passed = 0;
} else if (child_pid == 0) {
t->fn(t);
/* return the step that failed or 0 */
_exit(t->passed ? 0 : t->step);
} else {
/* TODO(wad) add timeout support. */
waitpid(child_pid, &status, 0);
if (WIFEXITED(status)) { if (WIFEXITED(status)) {
t->passed = t->termsig == -1 ? !WEXITSTATUS(status) : 0; t->passed = t->termsig == -1 ? !WEXITSTATUS(status) : 0;
if (t->termsig != -1) { if (t->termsig != -1) {
...@@ -750,9 +739,25 @@ void __run_test(struct __test_metadata *t) ...@@ -750,9 +739,25 @@ void __run_test(struct __test_metadata *t)
t->name, t->name,
status); status);
} }
}
void __run_test(struct __test_metadata *t)
{
t->passed = 1;
t->trigger = 0;
printf("[ RUN ] %s\n", t->name);
t->pid = fork();
if (t->pid < 0) {
printf("ERROR SPAWNING TEST CHILD\n");
t->passed = 0;
} else if (t->pid == 0) {
t->fn(t);
/* return the step that failed or 0 */
_exit(t->passed ? 0 : t->step);
} else {
__wait_for_test(t);
} }
printf("[ %4s ] %s\n", (t->passed ? "OK" : "FAIL"), t->name); printf("[ %4s ] %s\n", (t->passed ? "OK" : "FAIL"), t->name);
alarm(0);
} }
static int test_harness_run(int __attribute__((unused)) argc, static int test_harness_run(int __attribute__((unused)) argc,
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment