Skip to content

Commit

Permalink
Merge pull request #14 from clue-labs/race
Browse files Browse the repository at this point in the history
Avoid race condition for forked process in test suite
  • Loading branch information
clue authored May 15, 2019
2 parents d87d8e4 + f44922d commit dcaddcc
Show file tree
Hide file tree
Showing 2 changed files with 33 additions and 2 deletions.
15 changes: 14 additions & 1 deletion tests/FunctionalSshProcessConnectorTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,20 @@ public function testConnectPendingWillNotInheritActiveFileDescriptors()
// close server and ensure we can start a new server on the previous address
// the pending SSH connection process should not inherit the existing server socket
fclose($server);
$server = stream_socket_server('tcp://' . $address);

$server = @stream_socket_server('tcp://' . $address);
if ($server === false) {
// There's a very short race condition where the forked php process
// first has to `dup()` the file descriptor specs before invoking
// `exec()` to switch to the actual `ssh` child process. We don't
// need to wait for the child process to be ready, but only for the
// forked process to close the file descriptors. This happens ~80%
// of times on single core machines and almost never on multi core
// systems, so simply wait 5ms (plenty of time!) and retry again.
usleep(5000);
$server = stream_socket_server('tcp://' . $address);
}

$this->assertTrue(is_resource($server));
fclose($server);

Expand Down
20 changes: 19 additions & 1 deletion tests/FunctionalSshSocksConnectorTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,25 @@ public function testConnectPendingWillNotInheritActiveFileDescriptors()
// close server and ensure we can start a new server on the previous address
// the pending SSH connection process should not inherit the existing server socket
fclose($server);
$server = stream_socket_server('tcp://' . $address);

$server = @stream_socket_server('tcp://' . $address);
if ($server === false) {
// There's a very short race condition where the forked php process
// first has to `dup()` the file descriptor specs before invoking
// `exec()` to switch to the actual `ssh` child process. We don't
// need to wait for the child process to be ready, but only for the
// forked process to close the file descriptors. This happens ~80%
// of times on single core machines and almost never on multi core
// systems, so simply wait 5ms (plenty of time!) and retry again twice.
usleep(5000);
$server = @stream_socket_server('tcp://' . $address);

if ($server === false) {
usleep(5000);
$server = stream_socket_server('tcp://' . $address);
}
}

$this->assertTrue(is_resource($server));
fclose($server);

Expand Down

0 comments on commit dcaddcc

Please sign in to comment.