]> granicus.if.org Git - php/commitdiff
Add special "all" conflict
authorNikita Popov <nikita.ppv@gmail.com>
Thu, 21 Feb 2019 08:35:30 +0000 (09:35 +0100)
committerNikita Popov <nikita.ppv@gmail.com>
Thu, 21 Feb 2019 10:04:43 +0000 (11:04 +0100)
If a test conflicts with "all", then no other tests may be run in
parallel. This is needed for windows_mb_path tests, which rely on
the console codepage, which is shared across all parallel workers.

Also add support for comments in the CONFLICTS section/file.

ext/standard/tests/file/windows_mb_path/CONFLICTS
run-tests.php

index 1d0dfe69bed77c2b87e61b652e5c7b4bd81a73e2..692a324587e10cb1fff9dc30b29498688165c0d2 100644 (file)
@@ -1 +1,3 @@
-windows_mb_path
+# These tests depend on the console codepage, which is shared across all parallel workers.
+# Force these tests to run sequentially to make sure the codepage isn't change by another process.
+all
index 037b5d9fce659c0d725a3d4eb21b2259e950e53a..9b6e85ab401bd6b2c540ebae8de7e72d3de63ea9 100755 (executable)
@@ -1356,10 +1356,11 @@ function run_all_tests_parallel($test_files, $env, $redir_tested) {
        // specified either in the --CONFLICTS-- section, or CONFLICTS file inside a directory.
        $dirConflictsWith = [];
        $fileConflictsWith = [];
-       foreach ($test_files as $file) {
+       $sequentialTests = [];
+       foreach ($test_files as $i => $file) {
                $contents = file_get_contents($file);
                if (preg_match('/^--CONFLICTS--(.+?)^--/ms', $contents, $matches)) {
-                       $conflicts = array_map('trim', explode("\n", trim($matches[1])));
+                       $conflicts = parse_conflicts($matches[1]);
                } else {
                        // Cache per-directory conflicts in a separate map, so we compute these only once.
                        $dir = dirname($file);
@@ -1367,13 +1368,20 @@ function run_all_tests_parallel($test_files, $env, $redir_tested) {
                                $dirConflicts = [];
                                if (file_exists($dir . '/CONFLICTS')) {
                                        $contents = file_get_contents($dir . '/CONFLICTS');
-                                       $dirConflicts = array_map('trim', explode("\n", trim($contents)));
+                                       $dirConflicts = parse_conflicts($contents);
                                }
                                $dirConflictsWith[$dir] = $dirConflicts;
                        }
                        $conflicts = $dirConflictsWith[$dir];
                }
 
+               // For tests conflicting with "all", no other tests may run in parallel. We'll run these
+               // tests separately at the end, when only one worker is left.
+               if (in_array('all', $conflicts, true)) {
+                       $sequentialTests[] = $file;
+                       unset($test_files[$i]);
+               }
+
                $fileConflictsWith[$file] = $conflicts;
        }
 
@@ -1480,7 +1488,7 @@ function run_all_tests_parallel($test_files, $env, $redir_tested) {
        $waitingTests = [];
 
 escape:
-       while ($test_files || $testsInProgress > 0) {
+       while ($test_files || $sequentialTests || $testsInProgress > 0) {
                $toRead = array_values($workerSocks);
                $toWrite = NULL;
                $toExcept = NULL;
@@ -1525,6 +1533,11 @@ escape:
                                                        }
                                                        // intentional fall-through
                                                case "ready":
+                                                       // Schedule sequential tests only once we are down to one worker.
+                                                       if (count($workerProcs) === 1 && $sequentialTests) {
+                                                               $test_files = array_merge($test_files, $sequentialTests);
+                                                               $sequentialTests = [];
+                                                       }
                                                        // Batch multiple tests to reduce communication overhead.
                                                        $files = [];
                                                        $batchSize = $shuffle ? 4 : 32;
@@ -3190,6 +3203,12 @@ function clear_show_test() {
        }
 }
 
+function parse_conflicts(string $text) : array {
+       // Strip comments
+       $text = preg_replace('/#.*/', '', $text);
+       return array_map('trim', explode("\n", trim($text)));
+}
+
 function show_result($result, $tested, $tested_file, $extra = '', $temp_filenames = null)
 {
        global $html_output, $html_file, $temp_target, $temp_urlbase, $line_length, $SHOW_ONLY_GROUPS;