Mesa (master): aco/tests: Fix deadlock for too large test lists
GitLab Mirror
gitlab-mirror at kemper.freedesktop.org
Tue Dec 29 19:05:36 UTC 2020
Module: Mesa
Branch: master
Commit: 6a246f5c6d51db1a91f4419871051f81d4b552d9
URL: http://cgit.freedesktop.org/mesa/mesa/commit/?id=6a246f5c6d51db1a91f4419871051f81d4b552d9
Author: Tony Wasserka <tony.wasserka at gmx.de>
Date: Thu Nov 5 16:21:49 2020 +0100
aco/tests: Fix deadlock for too large test lists
The write() to the communication pipe shared with check_output.py would block
for large test output streams since the pipe's consumer wouldn't be launched
until the write already completed.
Reviewed-by: Daniel Schürmann <daniel at schuermann.dev>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/7461>
---
src/amd/compiler/tests/main.cpp | 30 ++++++++++++++++++++++--------
1 file changed, 22 insertions(+), 8 deletions(-)
diff --git a/src/amd/compiler/tests/main.cpp b/src/amd/compiler/tests/main.cpp
index cb646e2dd30..b1980217ff2 100644
--- a/src/amd/compiler/tests/main.cpp
+++ b/src/amd/compiler/tests/main.cpp
@@ -173,14 +173,28 @@ int check_output(char **argv)
int stdin_pipe[2];
pipe(stdin_pipe);
- write(stdin_pipe[1], checker_stdin_data, checker_stdin_size);
- close(stdin_pipe[1]);
- dup2(stdin_pipe[0], STDIN_FILENO);
-
- execlp(ACO_TEST_PYTHON_BIN, ACO_TEST_PYTHON_BIN, ACO_TEST_SOURCE_DIR "/check_output.py", NULL);
-
- fprintf(stderr, "%s: execl() failed: %s\n", argv[0], strerror(errno));
- return 99;
+ pid_t child_pid = fork();
+ if (child_pid == -1) {
+ fprintf(stderr, "%s: fork() failed: %s\n", argv[0], strerror(errno));
+ return 99;
+ } else if (child_pid != 0) {
+ /* Evaluate test output externally using Python */
+ dup2(stdin_pipe[0], STDIN_FILENO);
+ close(stdin_pipe[0]);
+ close(stdin_pipe[1]);
+
+ execlp(ACO_TEST_PYTHON_BIN, ACO_TEST_PYTHON_BIN, ACO_TEST_SOURCE_DIR "/check_output.py", NULL);
+ fprintf(stderr, "%s: execlp() failed: %s\n", argv[0], strerror(errno));
+ return 99;
+ } else {
+ /* Feed input data to the Python process. Writing large streams to
+ * stdin will block eventually, so this is done in a forked process
+ * to let the test checker process chunks of data as they arrive */
+ write(stdin_pipe[1], checker_stdin_data, checker_stdin_size);
+ close(stdin_pipe[0]);
+ close(stdin_pipe[1]);
+ exit(0);
+ }
}
bool match_test(std::string name, std::string pattern)
More information about the mesa-commit
mailing list