[dartdev] Factor out cross compilation tests into a separate test file.
Since current cross compilation tests are flaky due to being dependent on the uploaded artifacts, separate them out into a separate file that can be approved without hiding other failures in the compile test suite until they can be more properly fixed. Do some cleanup and refactoring to abstract out the common parts of the cross compilation failure tests as well. TEST=pkg/dartdev Issue: https://github.com/dart-lang/sdk/issues/61181 Change-Id: I1bee602f6d19ebd175bd27f6aded7a1909d1944f Cq-Include-Trybots: luci.dart.try:pkg-linux-release-arm64-try,pkg-linux-release-try,pkg-mac-release-arm64-try,pkg-mac-release-try,pkg-win-release-arm64-try,pkg-win-release-try,dart-sdk-linux-riscv64-try,dart-sdk-linux-arm64-try,dart-sdk-linux-try,dart-sdk-mac-try,dart-sdk-win-arm64-try,dart-sdk-win-try,dart-sdk-mac-arm64-try Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/442060 Reviewed-by: Alexander Markov <alexmarkov@google.com> Commit-Queue: Tess Strickland <sstrickl@google.com>
This commit is contained in:
committed by
Commit Queue
parent
8acd5894e0
commit
7da04d0144
@@ -26,6 +26,7 @@ import '../vm_interop_handler.dart';
|
||||
|
||||
const int genericErrorExitCode = 255;
|
||||
const int compileErrorExitCode = 254;
|
||||
const int crossCompileErrorExitCode = 128;
|
||||
|
||||
class Option {
|
||||
final String flag;
|
||||
@@ -597,7 +598,7 @@ Remove debugging information from the output and save it separately to the speci
|
||||
stderr.writeln('Unsupported target platform $target.');
|
||||
stderr.writeln('Supported target platforms: '
|
||||
'${supportedTargetPlatforms.join(', ')}');
|
||||
return 128;
|
||||
return crossCompileErrorExitCode;
|
||||
}
|
||||
|
||||
var cacheDir = getDartStorageDirectory();
|
||||
|
||||
@@ -8,14 +8,14 @@ import 'dart:math';
|
||||
import 'package:code_assets/code_assets.dart';
|
||||
import 'package:dart2native/dart2native_macho.dart' show pipeStream;
|
||||
import 'package:dart2native/macho.dart';
|
||||
import 'package:dartdev/src/commands/compile.dart'
|
||||
show compileErrorExitCode, genericErrorExitCode;
|
||||
import 'package:hooks_runner/hooks_runner.dart';
|
||||
import 'package:path/path.dart' as path;
|
||||
import 'package:test/test.dart';
|
||||
|
||||
import '../utils.dart';
|
||||
|
||||
const int compileErrorExitCode = 254;
|
||||
|
||||
void main() {
|
||||
ensureRunFromSdkBinDart();
|
||||
|
||||
@@ -27,21 +27,13 @@ const String soundNullSafetyWarning =
|
||||
"Warning: Option '--sound-null-safety' is deprecated.";
|
||||
|
||||
const String failedAssertionError = 'Failed assertion: line';
|
||||
String usingTargetOSMessageForPlatform(String targetOS) =>
|
||||
String usingTargetOSMessage(OS targetOS) =>
|
||||
'Specializing Platform getters for target OS $targetOS.';
|
||||
final String usingTargetOSMessage =
|
||||
usingTargetOSMessageForPlatform(Platform.operatingSystem);
|
||||
String unsupportedTargetError(Target target) =>
|
||||
'Unsupported target platform $target';
|
||||
final String targetingHostOSMessage = usingTargetOSMessage(Target.current.os);
|
||||
|
||||
void defineCompileTests() {
|
||||
final host = Target.current;
|
||||
// AOT compilation is not available on IA32.
|
||||
final bool isRunningOnIA32 = host.architecture == Architecture.ia32;
|
||||
// Cross compilation is not available on 32-bit architectures.
|
||||
final bool isRunningOn32Bit = isRunningOnIA32 ||
|
||||
host.architecture == Architecture.arm ||
|
||||
host.architecture == Architecture.riscv32;
|
||||
final bool isRunningOnIA32 = Target.current.architecture == Architecture.ia32;
|
||||
|
||||
if (Platform.isMacOS) {
|
||||
test('Compile exe for MacOS signing', () async {
|
||||
@@ -266,7 +258,7 @@ void defineCompileTests() {
|
||||
'-v',
|
||||
inFile,
|
||||
]);
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stderr, isNot(contains(soundNullSafetyMessage)));
|
||||
expect(result.exitCode, 0);
|
||||
final file = File(outFile);
|
||||
@@ -294,7 +286,7 @@ void defineCompileTests() {
|
||||
);
|
||||
|
||||
// Executables should be (host) OS-specific by default.
|
||||
expect(result.stdout, contains(usingTargetOSMessage));
|
||||
expect(result.stdout, contains(targetingHostOSMessage));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
expect(File(outFile).existsSync(), true,
|
||||
@@ -365,7 +357,7 @@ void defineCompileTests() {
|
||||
],
|
||||
);
|
||||
|
||||
expect(result.stdout, contains(usingTargetOSMessage));
|
||||
expect(result.stdout, contains(targetingHostOSMessage));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
expect(File(outFile).existsSync(), true,
|
||||
@@ -418,95 +410,6 @@ void defineCompileTests() {
|
||||
expect(result.exitCode, 0);
|
||||
}, skip: isRunningOnIA32);
|
||||
|
||||
Future<void> basicCrossCompileTest(Target target) async {
|
||||
final p = project(
|
||||
mainSrc: 'void main() {print(const String.fromEnvironment("cross"));}');
|
||||
final inFile = path.canonicalize(path.join(p.dirPath, p.relativeFilePath));
|
||||
final outFile = path.canonicalize(path.join(p.dirPath, 'myexe'));
|
||||
final result = await p.run(
|
||||
[
|
||||
'compile',
|
||||
'exe',
|
||||
'-v',
|
||||
'--target-os',
|
||||
target.os.name,
|
||||
'--target-arch',
|
||||
target.architecture.name,
|
||||
'-o',
|
||||
outFile,
|
||||
inFile,
|
||||
],
|
||||
);
|
||||
|
||||
if (result.exitCode != 0) {
|
||||
print('Subcommand terminated with exit code ${result.exitCode}.');
|
||||
if (result.stdout.isNotEmpty) {
|
||||
print('Subcommand stdout:');
|
||||
print(result.stdout);
|
||||
}
|
||||
if (result.stderr.isNotEmpty) {
|
||||
print('Subcommand stderr:');
|
||||
print(result.stderr);
|
||||
}
|
||||
}
|
||||
|
||||
expect(result.stdout,
|
||||
contains(usingTargetOSMessageForPlatform(target.os.name)));
|
||||
expect(result.stderr, isNot(contains(unsupportedTargetError(target))));
|
||||
expect(result.exitCode, 0);
|
||||
}
|
||||
|
||||
final crossCompileOSes = [
|
||||
OS.linux,
|
||||
];
|
||||
|
||||
final crossCompileArchitectures = [
|
||||
Architecture.arm,
|
||||
Architecture.arm64,
|
||||
Architecture.riscv64,
|
||||
Architecture.x64,
|
||||
];
|
||||
|
||||
for (final os in crossCompileOSes) {
|
||||
for (final arch in crossCompileArchitectures) {
|
||||
if (os == host.os && arch == host.architecture) continue;
|
||||
final target = Target.fromArchitectureAndOS(arch, os);
|
||||
test('Compile executable can cross compile to $os $arch',
|
||||
() async => basicCrossCompileTest(target),
|
||||
skip: isRunningOn32Bit);
|
||||
}
|
||||
}
|
||||
|
||||
test('Compile executable cannot compile cross-OS', () async {
|
||||
final p = project(
|
||||
mainSrc: 'void main() {print(const String.fromEnvironment("cross"));}');
|
||||
final inFile = path.canonicalize(path.join(p.dirPath, p.relativeFilePath));
|
||||
final outFile = path.canonicalize(path.join(p.dirPath, 'myexe'));
|
||||
// Make sure targetOS is always unsupported (not Linux and not matches host
|
||||
// OS) to trigger an error.
|
||||
final targetOS = Platform.isWindows ? OS.macOS : OS.windows;
|
||||
final targetArch = Architecture.arm64;
|
||||
final target = Target.fromArchitectureAndOS(targetArch, targetOS);
|
||||
final result = await p.run(
|
||||
[
|
||||
'compile',
|
||||
'exe',
|
||||
'-v',
|
||||
'--target-os',
|
||||
targetOS.name,
|
||||
'--target-arch',
|
||||
targetArch.name,
|
||||
'-o',
|
||||
outFile,
|
||||
inFile,
|
||||
],
|
||||
);
|
||||
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stderr, contains(unsupportedTargetError(target)));
|
||||
expect(result.exitCode, 128);
|
||||
}, skip: isRunningOnIA32);
|
||||
|
||||
test('Compile and run aot snapshot', () async {
|
||||
final p = project(mainSrc: 'void main() { print("I love AOT"); }');
|
||||
final inFile = path.canonicalize(path.join(p.dirPath, p.relativeFilePath));
|
||||
@@ -524,7 +427,7 @@ void defineCompileTests() {
|
||||
);
|
||||
|
||||
// AOT snapshots should be OS-specific by default.
|
||||
expect(result.stdout, contains(usingTargetOSMessage));
|
||||
expect(result.stdout, contains(targetingHostOSMessage));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
expect(File(outFile).existsSync(), true,
|
||||
@@ -541,73 +444,6 @@ void defineCompileTests() {
|
||||
expect(result.exitCode, 0);
|
||||
}, skip: isRunningOnIA32);
|
||||
|
||||
test('Compile aot snapshot can compile to host platform', () async {
|
||||
final targetOS = Platform.operatingSystem;
|
||||
final p = project(mainSrc: 'void main() { print("I love $targetOS"); }');
|
||||
final inFile = path.canonicalize(path.join(p.dirPath, p.relativeFilePath));
|
||||
final outFile = path.canonicalize(path.join(p.dirPath, 'main.aot'));
|
||||
|
||||
var result = await p.run(
|
||||
[
|
||||
'compile',
|
||||
'aot-snapshot',
|
||||
'-v',
|
||||
'--target-os',
|
||||
targetOS,
|
||||
'-o',
|
||||
'main.aot',
|
||||
inFile,
|
||||
],
|
||||
);
|
||||
|
||||
expect(result.stdout, contains(usingTargetOSMessageForPlatform(targetOS)));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
expect(File(outFile).existsSync(), true,
|
||||
reason: 'File not found: $outFile');
|
||||
|
||||
final Directory binDir = File(Platform.resolvedExecutable).parent;
|
||||
result = Process.runSync(
|
||||
path.join(binDir.path, 'dartaotruntime'),
|
||||
[outFile],
|
||||
);
|
||||
|
||||
expect(result.stdout, contains('I love $targetOS'));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
}, skip: isRunningOnIA32);
|
||||
|
||||
test('Compile aot snapshot cannot compile cross platform', () async {
|
||||
// Make sure targetOS is always unsupported (not Linux and not matches host
|
||||
// OS) to trigger an error.
|
||||
final targetOS = Platform.isWindows ? OS.macOS : OS.windows;
|
||||
final targetArch = Architecture.arm64;
|
||||
final target = Target.fromArchitectureAndOS(targetArch, targetOS);
|
||||
final p = project(mainSrc: 'void main() { print("I love $targetOS"); }');
|
||||
final inFile = path.canonicalize(path.join(p.dirPath, p.relativeFilePath));
|
||||
|
||||
var result = await p.run(
|
||||
[
|
||||
'compile',
|
||||
'aot-snapshot',
|
||||
'-v',
|
||||
'--target-os',
|
||||
targetOS.name,
|
||||
'--target-arch',
|
||||
targetArch.name,
|
||||
'-o',
|
||||
'main.aot',
|
||||
inFile,
|
||||
],
|
||||
);
|
||||
|
||||
expect(result.stdout,
|
||||
isNot(contains(usingTargetOSMessageForPlatform(targetOS.name))));
|
||||
expect(result.stderr, contains(unsupportedTargetError(target)));
|
||||
|
||||
expect(result.exitCode, isNot(0));
|
||||
}, skip: isRunningOnIA32);
|
||||
|
||||
test('Compile and run kernel snapshot', () async {
|
||||
final p = project(mainSrc: 'void main() { print("I love kernel"); }');
|
||||
final outFile = path.join(p.dirPath, 'main.dill');
|
||||
@@ -623,7 +459,7 @@ void defineCompileTests() {
|
||||
);
|
||||
expect(File(outFile).existsSync(), true,
|
||||
reason: 'File not found: $outFile');
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stderr, isNot(contains(soundNullSafetyMessage)));
|
||||
expect(result.exitCode, 0);
|
||||
|
||||
@@ -653,7 +489,7 @@ void defineCompileTests() {
|
||||
'-v',
|
||||
inFile,
|
||||
]);
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
final file = File(outFile);
|
||||
@@ -683,7 +519,7 @@ void defineCompileTests() {
|
||||
outFile,
|
||||
inFile,
|
||||
]);
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
final file = File(outFile);
|
||||
@@ -853,7 +689,7 @@ void main() {
|
||||
);
|
||||
|
||||
// Only printed when -v/--verbose is used, not --verbosity.
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stdout, isNot(contains(soundNullSafetyMessage)));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
@@ -883,7 +719,7 @@ void main() {
|
||||
);
|
||||
|
||||
// Only printed when -v/--verbose is used, not --verbosity.
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stdout, isNot(contains(soundNullSafetyMessage)));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
@@ -910,7 +746,7 @@ void main() {
|
||||
);
|
||||
|
||||
// Only printed when -v/--verbose is used, not --verbosity.
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stdout, isNot(contains(soundNullSafetyMessage)));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
@@ -977,7 +813,7 @@ void main() {}
|
||||
|
||||
expect(result.stderr,
|
||||
contains('Error: The output file "foo" does not end with ".wasm"'));
|
||||
expect(result.exitCode, 255);
|
||||
expect(result.exitCode, genericErrorExitCode);
|
||||
}, skip: isRunningOnIA32);
|
||||
|
||||
test('Compile wasm with error', () async {
|
||||
@@ -1166,7 +1002,7 @@ void main() {
|
||||
);
|
||||
|
||||
// Only printed when -v/--verbose is used, not --verbosity.
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stdout, isNot(contains(soundNullSafetyMessage)));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
@@ -1196,7 +1032,7 @@ void main() {
|
||||
);
|
||||
|
||||
// Only printed when -v/--verbose is used, not --verbosity.
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stdout, isNot(contains(soundNullSafetyMessage)));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
@@ -1223,7 +1059,7 @@ void main() {
|
||||
);
|
||||
|
||||
// Only printed when -v/--verbose is used, not --verbosity.
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stdout, isNot(contains(soundNullSafetyMessage)));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
@@ -1299,7 +1135,7 @@ void main() {}
|
||||
(dynamic o) => '$o'.contains('Unable to open file'),
|
||||
),
|
||||
);
|
||||
expect(result.exitCode, 255);
|
||||
expect(result.exitCode, genericErrorExitCode);
|
||||
});
|
||||
|
||||
test('Compile kernel with invalid trailing argument', () async {
|
||||
@@ -1347,7 +1183,7 @@ void main() {}
|
||||
],
|
||||
);
|
||||
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stderr, isNot(contains(soundNullSafetyMessage)));
|
||||
expect(result.exitCode, 0);
|
||||
expect(File(outFile).existsSync(), true,
|
||||
@@ -1567,10 +1403,10 @@ void main() {
|
||||
);
|
||||
|
||||
// Only printed when -v/--verbose is used, not --verbosity.
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage)));
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stdout, isNot(contains(soundNullSafetyMessage)));
|
||||
expect(result.stderr, contains(failedAssertionError));
|
||||
expect(result.exitCode, 255);
|
||||
expect(result.exitCode, genericErrorExitCode);
|
||||
|
||||
result = await p.run(
|
||||
['--enable-asserts', outFile],
|
||||
|
||||
@@ -0,0 +1,144 @@
|
||||
// Copyright (c) 2025, the Dart project authors. Please see the AUTHORS file
|
||||
// for details. All rights reserved. Use of this source code is governed by a
|
||||
// BSD-style license that can be found in the LICENSE file.
|
||||
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:code_assets/code_assets.dart';
|
||||
import 'package:dartdev/src/commands/compile.dart'
|
||||
show CompileNativeCommand, crossCompileErrorExitCode;
|
||||
import 'package:hooks_runner/hooks_runner.dart';
|
||||
import 'package:path/path.dart' as path;
|
||||
import 'package:test/test.dart';
|
||||
|
||||
import '../utils.dart';
|
||||
import 'compile_test.dart' show targetingHostOSMessage, usingTargetOSMessage;
|
||||
|
||||
void main() {
|
||||
ensureRunFromSdkBinDart();
|
||||
|
||||
// Cross compilation is not available on 32-bit architectures.
|
||||
final hostArch = Target.current.architecture;
|
||||
final bool isRunningOn32Bit = hostArch == Architecture.ia32 ||
|
||||
hostArch == Architecture.arm ||
|
||||
hostArch == Architecture.riscv32;
|
||||
|
||||
group('cross compile -', defineCrossCompileTests,
|
||||
timeout: longTimeout, skip: isRunningOn32Bit);
|
||||
}
|
||||
|
||||
String unsupportedTargetMessage(Target target) =>
|
||||
'Unsupported target platform $target';
|
||||
typedef TestFunction = Future<void> Function();
|
||||
|
||||
void defineCrossCompileTests() {
|
||||
final subcommands = [
|
||||
CompileNativeCommand.aotSnapshotCmdName,
|
||||
CompileNativeCommand.exeCmdName,
|
||||
];
|
||||
final crossCompileTargets = CompileNativeCommand.supportedTargetPlatforms;
|
||||
String mainMessage(Target target) => 'I love ${target.os}';
|
||||
|
||||
Future<(ProcessResult, String)> crossCompile(
|
||||
String subcommand, Target target) async {
|
||||
final p =
|
||||
project(mainSrc: 'void main() {print("${mainMessage(target)}");}');
|
||||
final inFile = path.canonicalize(path.join(p.dirPath, p.relativeFilePath));
|
||||
final filename = subcommand == CompileNativeCommand.exeCmdName
|
||||
? 'myexe'
|
||||
: subcommand == CompileNativeCommand.aotSnapshotCmdName
|
||||
? 'out.so'
|
||||
: throw ArgumentError(
|
||||
'Unexpected subcommand $subcommand', 'subcommand');
|
||||
final outFile = path.canonicalize(path.join(p.dirPath, filename));
|
||||
final result = await p.run(
|
||||
[
|
||||
'compile',
|
||||
subcommand,
|
||||
'-v',
|
||||
'--target-os',
|
||||
target.os.name,
|
||||
'--target-arch',
|
||||
target.architecture.name,
|
||||
'-o',
|
||||
outFile,
|
||||
inFile,
|
||||
],
|
||||
);
|
||||
|
||||
print('Subcommand terminated with exit code ${result.exitCode}.');
|
||||
if (result.stdout.isNotEmpty) {
|
||||
print('Subcommand stdout:');
|
||||
print(result.stdout);
|
||||
}
|
||||
if (result.stderr.isNotEmpty) {
|
||||
print('Subcommand stderr:');
|
||||
print(result.stderr);
|
||||
}
|
||||
|
||||
return (result, outFile);
|
||||
}
|
||||
|
||||
TestFunction crossCompileTest(String subcommand, Target target) => () async {
|
||||
expect(subcommand, isIn(subcommands));
|
||||
expect(target, isIn(crossCompileTargets));
|
||||
var (result, outFile) = await crossCompile(subcommand, target);
|
||||
|
||||
expect(result.stdout, contains(usingTargetOSMessage(target.os)));
|
||||
expect(
|
||||
result.stderr, isNot(contains(unsupportedTargetMessage(target))));
|
||||
expect(result.exitCode, 0);
|
||||
expect(File(outFile).existsSync(), true,
|
||||
reason: 'File not found: $outFile');
|
||||
|
||||
if (target != Target.current) return;
|
||||
|
||||
if (subcommand == CompileNativeCommand.exeCmdName) {
|
||||
result = Process.runSync(outFile, const []);
|
||||
} else {
|
||||
expect(subcommand, CompileNativeCommand.aotSnapshotCmdName);
|
||||
final Directory binDir = File(Platform.resolvedExecutable).parent;
|
||||
result = Process.runSync(
|
||||
path.join(binDir.path, 'dartaotruntime'),
|
||||
[outFile],
|
||||
);
|
||||
}
|
||||
|
||||
expect(result.stdout, contains(mainMessage(target)));
|
||||
expect(result.stderr, isEmpty);
|
||||
expect(result.exitCode, 0);
|
||||
};
|
||||
|
||||
TestFunction crossCompileFailureTest(String subcommand, Target target) =>
|
||||
() async {
|
||||
expect(subcommand, isIn(subcommands));
|
||||
expect(target, isNot(Target.current));
|
||||
expect(target, isNot(isIn(crossCompileTargets)));
|
||||
final (result, outFile) = await crossCompile(subcommand, target);
|
||||
|
||||
expect(result.stdout, isNot(contains(targetingHostOSMessage)));
|
||||
expect(result.stdout, isNot(contains(usingTargetOSMessage(target.os))));
|
||||
expect(result.stderr, contains(unsupportedTargetMessage(target)));
|
||||
expect(result.exitCode, crossCompileErrorExitCode);
|
||||
expect(File(outFile).existsSync(), false,
|
||||
reason: 'File created despite failure: $outFile');
|
||||
};
|
||||
|
||||
for (final subcommand in subcommands) {
|
||||
for (final target in crossCompileTargets) {
|
||||
test('Compile $subcommand can cross compile to $target',
|
||||
crossCompileTest(subcommand, target));
|
||||
}
|
||||
var targetOS = Platform.isWindows ? OS.macOS : OS.windows;
|
||||
var targetArch = Architecture.arm64;
|
||||
var target = Target.fromArchitectureAndOS(targetArch, targetOS);
|
||||
test('Compile $subcommand fails on invalid target OS',
|
||||
crossCompileFailureTest(subcommand, target));
|
||||
|
||||
targetOS = OS.linux;
|
||||
targetArch = Architecture.riscv32;
|
||||
target = Target.fromArchitectureAndOS(targetArch, targetOS);
|
||||
test('Compile $subcommand fails on invalid target architecture',
|
||||
crossCompileFailureTest(subcommand, target));
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user