Fix abstract unix socket test
There was a race between the subprocess listening on the socket and the test trying to connect. Also the Android bits of the test harness needed to be taught about the abstract_socket_test program, similar to how process_test is handled. TEST=Fixes tests Change-Id: I5e1c5d2e23e4bff2a01cd5c491a45e1c58d2578e Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/201861 Reviewed-by: Alexander Aprelev <aam@google.com> Commit-Queue: Zach Anderson <zra@google.com>
This commit is contained in:
committed by
commit-bot@chromium.org
parent
ab91ef643c
commit
8beec1d9cc
@@ -609,6 +609,7 @@ abstract class AdbCommand {
|
||||
class AdbPrecompilationCommand extends Command implements AdbCommand {
|
||||
final String buildPath; // Path to the output directory of the build.
|
||||
final String processTestFilename;
|
||||
final String abstractSocketTestFilename;
|
||||
final String precompiledTestDirectory;
|
||||
final List<String> arguments;
|
||||
final bool useElf;
|
||||
@@ -617,6 +618,7 @@ class AdbPrecompilationCommand extends Command implements AdbCommand {
|
||||
AdbPrecompilationCommand(
|
||||
this.buildPath,
|
||||
this.processTestFilename,
|
||||
this.abstractSocketTestFilename,
|
||||
this.precompiledTestDirectory,
|
||||
this.arguments,
|
||||
this.useElf,
|
||||
@@ -627,6 +629,7 @@ class AdbPrecompilationCommand extends Command implements AdbCommand {
|
||||
AdbPrecompilationCommand indexedCopy(int index) => AdbPrecompilationCommand(
|
||||
buildPath,
|
||||
processTestFilename,
|
||||
abstractSocketTestFilename,
|
||||
precompiledTestDirectory,
|
||||
arguments,
|
||||
useElf,
|
||||
@@ -662,17 +665,28 @@ class AdbPrecompilationCommand extends Command implements AdbCommand {
|
||||
class AdbDartkCommand extends Command implements AdbCommand {
|
||||
final String buildPath;
|
||||
final String processTestFilename;
|
||||
final String abstractSocketTestFilename;
|
||||
final String kernelFile;
|
||||
final List<String> arguments;
|
||||
final List<String> extraLibraries;
|
||||
|
||||
AdbDartkCommand(this.buildPath, this.processTestFilename, this.kernelFile,
|
||||
this.arguments, this.extraLibraries,
|
||||
AdbDartkCommand(
|
||||
this.buildPath,
|
||||
this.processTestFilename,
|
||||
this.abstractSocketTestFilename,
|
||||
this.kernelFile,
|
||||
this.arguments,
|
||||
this.extraLibraries,
|
||||
{int index = 0})
|
||||
: super._("adb_precompilation", index: index);
|
||||
|
||||
AdbDartkCommand indexedCopy(int index) => AdbDartkCommand(
|
||||
buildPath, processTestFilename, kernelFile, arguments, extraLibraries,
|
||||
buildPath,
|
||||
processTestFilename,
|
||||
abstractSocketTestFilename,
|
||||
kernelFile,
|
||||
arguments,
|
||||
extraLibraries,
|
||||
index: index);
|
||||
|
||||
_buildHashCode(HashCodeBuilder builder) {
|
||||
|
||||
@@ -639,6 +639,7 @@ class CommandExecutorImpl implements CommandExecutor {
|
||||
AdbDevice device, AdbPrecompilationCommand command, int timeout) async {
|
||||
var buildPath = command.buildPath;
|
||||
var processTest = command.processTestFilename;
|
||||
var abstractSocketTest = command.abstractSocketTestFilename;
|
||||
var testdir = command.precompiledTestDirectory;
|
||||
var arguments = command.arguments;
|
||||
var devicedir = DartPrecompiledAdbRuntimeConfiguration.deviceDir;
|
||||
@@ -662,10 +663,12 @@ class CommandExecutorImpl implements CommandExecutor {
|
||||
'$devicedir/dart_precompiled_runtime'));
|
||||
steps.add(
|
||||
() => device.pushCachedData(processTest, '$devicedir/process_test'));
|
||||
steps.add(() => device.pushCachedData(
|
||||
abstractSocketTest, '$devicedir/abstract_socket_test'));
|
||||
steps.add(() => device.runAdbShellCommand([
|
||||
'chmod',
|
||||
'777',
|
||||
'$devicedir/dart_precompiled_runtime $devicedir/process_test'
|
||||
'$devicedir/dart_precompiled_runtime $devicedir/process_test $devicedir/abstract_socket_test'
|
||||
]));
|
||||
|
||||
steps.addAll(_pushLibraries(command, device, devicedir, deviceTestDir));
|
||||
|
||||
@@ -125,6 +125,13 @@ abstract class RuntimeConfiguration {
|
||||
return processTestExecutable;
|
||||
}
|
||||
|
||||
String get abstractSocketTestBinaryFileName {
|
||||
var abstractSocketTestExecutable =
|
||||
'$buildDir/abstract_socket_test$executableExtension';
|
||||
TestUtils.ensureExists(abstractSocketTestExecutable, _configuration);
|
||||
return abstractSocketTestExecutable;
|
||||
}
|
||||
|
||||
String get d8FileName {
|
||||
var d8Dir = Repository.dir.append('third_party/d8');
|
||||
var d8Path =
|
||||
@@ -358,8 +365,10 @@ class DartkAdbRuntimeConfiguration extends DartVmRuntimeConfiguration {
|
||||
|
||||
var buildPath = buildDir;
|
||||
var processTest = processTestBinaryFileName;
|
||||
var abstractSocketTest = abstractSocketTestBinaryFileName;
|
||||
return [
|
||||
AdbDartkCommand(buildPath, processTest, script, arguments, extraLibs)
|
||||
AdbDartkCommand(buildPath, processTest, abstractSocketTest, script,
|
||||
arguments, extraLibs)
|
||||
];
|
||||
}
|
||||
}
|
||||
@@ -385,9 +394,10 @@ class DartPrecompiledAdbRuntimeConfiguration
|
||||
}
|
||||
|
||||
var processTest = processTestBinaryFileName;
|
||||
var abstractSocketTest = abstractSocketTestBinaryFileName;
|
||||
return [
|
||||
AdbPrecompilationCommand(
|
||||
buildDir, processTest, script, arguments, useElf, extraLibs)
|
||||
AdbPrecompilationCommand(buildDir, processTest, abstractSocketTest,
|
||||
script, arguments, useElf, extraLibs)
|
||||
];
|
||||
}
|
||||
}
|
||||
|
||||
@@ -175,7 +175,11 @@ Future testShortAbstractAddress() async {
|
||||
if (!Platform.isLinux && !Platform.isAndroid) {
|
||||
return;
|
||||
}
|
||||
var retries = 10;
|
||||
var retryDelay = const Duration(seconds: 1);
|
||||
Process? process;
|
||||
Future? stdoutFuture;
|
||||
Future? stderrFuture;
|
||||
try {
|
||||
var socketAddress = '@hidden';
|
||||
var abstractSocketServer = getAbstractSocketTestFileName();
|
||||
@@ -184,10 +188,36 @@ Future testShortAbstractAddress() async {
|
||||
if (!File(abstractSocketServer).existsSync()) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Start up a subprocess that listens on '@hidden'.
|
||||
process = await Process.start(abstractSocketServer, [socketAddress]);
|
||||
stdoutFuture = process.stdout
|
||||
.transform(const Utf8Decoder(allowMalformed: true))
|
||||
.listen(stdout.write)
|
||||
.asFuture(null);
|
||||
stderrFuture = process.stderr
|
||||
.transform(const Utf8Decoder(allowMalformed: true))
|
||||
.listen(stderr.write)
|
||||
.asFuture(null);
|
||||
var serverAddress =
|
||||
InternetAddress(socketAddress, type: InternetAddressType.unix);
|
||||
Socket client = await Socket.connect(serverAddress, 0);
|
||||
|
||||
// The subprocess may take some time to start, so retry setting up the
|
||||
// connection a few times.
|
||||
Socket? client;
|
||||
while (true) {
|
||||
try {
|
||||
client = await Socket.connect(serverAddress, 0);
|
||||
break;
|
||||
} catch (e, st) {
|
||||
if (retries <= 0) {
|
||||
rethrow;
|
||||
}
|
||||
retries--;
|
||||
}
|
||||
await Future.delayed(retryDelay);
|
||||
}
|
||||
|
||||
List<int> sendData = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
|
||||
List<int> data = [];
|
||||
var completer = Completer<void>();
|
||||
@@ -206,6 +236,9 @@ Future testShortAbstractAddress() async {
|
||||
Expect.fail('Failed with exception:\n$e\n$st');
|
||||
} finally {
|
||||
process?.kill(ProcessSignal.sigkill);
|
||||
await stdoutFuture;
|
||||
await stderrFuture;
|
||||
await process?.exitCode;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -5,8 +5,8 @@
|
||||
// @dart = 2.9
|
||||
|
||||
import 'dart:async';
|
||||
import 'dart:io';
|
||||
import 'dart:convert';
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:expect/expect.dart';
|
||||
|
||||
@@ -177,7 +177,11 @@ Future testShortAbstractAddress() async {
|
||||
if (!Platform.isLinux && !Platform.isAndroid) {
|
||||
return;
|
||||
}
|
||||
var retries = 10;
|
||||
var retryDelay = const Duration(seconds: 1);
|
||||
Process process;
|
||||
var stdoutFuture;
|
||||
var stderrFuture;
|
||||
try {
|
||||
var socketAddress = '@hidden';
|
||||
var abstractSocketServer = getAbstractSocketTestFileName();
|
||||
@@ -186,10 +190,36 @@ Future testShortAbstractAddress() async {
|
||||
if (!File(abstractSocketServer).existsSync()) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Start up a subprocess that listens on '@hidden'.
|
||||
process = await Process.start(abstractSocketServer, [socketAddress]);
|
||||
stdoutFuture = process.stdout
|
||||
.transform(const Utf8Decoder(allowMalformed: true))
|
||||
.listen(stdout.write)
|
||||
.asFuture(null);
|
||||
stderrFuture = process.stderr
|
||||
.transform(const Utf8Decoder(allowMalformed: true))
|
||||
.listen(stderr.write)
|
||||
.asFuture(null);
|
||||
var serverAddress =
|
||||
InternetAddress(socketAddress, type: InternetAddressType.unix);
|
||||
Socket client = await Socket.connect(serverAddress, 0);
|
||||
|
||||
// The subprocess may take some time to start, so retry setting up the
|
||||
// connection a few times.
|
||||
Socket client;
|
||||
while (true) {
|
||||
try {
|
||||
client = await Socket.connect(serverAddress, 0);
|
||||
break;
|
||||
} catch (e, st) {
|
||||
if (retries <= 0) {
|
||||
rethrow;
|
||||
}
|
||||
retries--;
|
||||
}
|
||||
await Future.delayed(retryDelay);
|
||||
}
|
||||
|
||||
List<int> sendData = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
|
||||
List<int> data = [];
|
||||
var completer = Completer<void>();
|
||||
@@ -208,6 +238,9 @@ Future testShortAbstractAddress() async {
|
||||
Expect.fail('Failed with exception:\n$e\n$st');
|
||||
} finally {
|
||||
process?.kill(ProcessSignal.sigkill);
|
||||
await stdoutFuture;
|
||||
await stderrFuture;
|
||||
await process?.exitCode;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user