Unverified Commit e8b98f96 authored by Ben Konyi's avatar Ben Konyi Committed by GitHub

Manual engine roll for 2019-03-19 (#29627)

* Manual engine roll for 2019-03-19
* Applying patch for Dart SDK changes (see PR #29004)
parent edd4c620
571964e1d7b49e5424c800b461006207d670736f
96ad0c8926b0493d4276a39ee9bc6de6fa97bece
......@@ -57,12 +57,15 @@ class TargetModel {
}
class CompilerOutput {
const CompilerOutput(this.outputFilename, this.errorCount);
const CompilerOutput(this.outputFilename, this.errorCount, this.sources);
final String outputFilename;
final int errorCount;
final List<Uri> sources;
}
enum StdoutState { CollectDiagnostic, CollectDependencies }
/// Handles stdin/stdout communication with the frontend server.
class StdoutHandler {
StdoutHandler({this.consumer = printError}) {
......@@ -72,40 +75,71 @@ class StdoutHandler {
bool compilerMessageReceived = false;
final CompilerMessageConsumer consumer;
String boundaryKey;
StdoutState state = StdoutState.CollectDiagnostic;
Completer<CompilerOutput> compilerOutput;
final List<Uri> sources = <Uri>[];
bool _suppressCompilerMessages;
bool _expectSources;
void handler(String message) {
printTrace('-> $message');
const String kResultPrefix = 'result ';
if (boundaryKey == null && message.startsWith(kResultPrefix)) {
boundaryKey = message.substring(kResultPrefix.length);
} else if (message.startsWith(boundaryKey)) {
return;
}
if (message.startsWith(boundaryKey)) {
if (_expectSources) {
if (state == StdoutState.CollectDiagnostic) {
state = StdoutState.CollectDependencies;
return;
}
}
if (message.length <= boundaryKey.length) {
compilerOutput.complete(null);
return;
}
final int spaceDelimiter = message.lastIndexOf(' ');
compilerOutput.complete(
CompilerOutput(
message.substring(boundaryKey.length + 1, spaceDelimiter),
int.parse(message.substring(spaceDelimiter + 1).trim())));
} else if (!_suppressCompilerMessages) {
if (compilerMessageReceived == false) {
consumer('\nCompiler message:');
compilerMessageReceived = true;
CompilerOutput(
message.substring(boundaryKey.length + 1, spaceDelimiter),
int.parse(message.substring(spaceDelimiter + 1).trim()),
sources));
return;
}
if (state == StdoutState.CollectDiagnostic) {
if (!_suppressCompilerMessages) {
if (compilerMessageReceived == false) {
consumer('\nCompiler message:');
compilerMessageReceived = true;
}
consumer(message);
}
} else {
assert(state == StdoutState.CollectDependencies);
switch (message[0]) {
case '+':
sources.add(Uri.parse(message.substring(1)));
break;
case '-':
sources.remove(Uri.parse(message.substring(1)));
break;
default:
printTrace('Unexpected prefix for $message uri - ignoring');
}
consumer(message);
}
}
// This is needed to get ready to process next compilation result output,
// with its own boundary key and new completer.
void reset({ bool suppressCompilerMessages = false }) {
void reset({ bool suppressCompilerMessages = false, bool expectSources = true }) {
boundaryKey = null;
compilerMessageReceived = false;
compilerOutput = Completer<CompilerOutput>();
_suppressCompilerMessages = suppressCompilerMessages;
_expectSources = expectSources;
state = StdoutState.CollectDiagnostic;
}
}
......@@ -200,7 +234,7 @@ class KernelCompiler {
if (await fingerprinter.doesFingerprintMatch()) {
printTrace('Skipping kernel compilation. Fingerprint match.');
return CompilerOutput(outputFilePath, 0);
return CompilerOutput(outputFilePath, 0, /* sources */ null);
}
}
......@@ -453,10 +487,13 @@ class ResidentCompiler {
? _mapFilename(request.mainPath, packageUriMapper) + ' '
: '';
_server.stdin.writeln('recompile $mainUri$inputKey');
printTrace('<- recompile $mainUri$inputKey');
for (String fileUri in request.invalidatedFiles) {
_server.stdin.writeln(_mapFileUri(fileUri, packageUriMapper));
printTrace('<- ${_mapFileUri(fileUri, packageUriMapper)}');
}
_server.stdin.writeln(inputKey);
printTrace('<- $inputKey');
return _stdoutHandler.compilerOutput.future;
}
......@@ -545,6 +582,7 @@ class ResidentCompiler {
.listen((String message) { printError(message); });
_server.stdin.writeln('compile $scriptUri');
printTrace('<- compile $scriptUri');
return _stdoutHandler.compilerOutput.future;
}
......@@ -570,7 +608,7 @@ class ResidentCompiler {
}
Future<CompilerOutput> _compileExpression(_CompileExpressionRequest request) async {
_stdoutHandler.reset(suppressCompilerMessages: true);
_stdoutHandler.reset(suppressCompilerMessages: true, expectSources: false);
// 'compile-expression' should be invoked after compiler has been started,
// program was compiled.
......@@ -597,6 +635,7 @@ class ResidentCompiler {
void accept() {
if (_compileRequestNeedsConfirmation) {
_server.stdin.writeln('accept');
printTrace('<- accept');
}
_compileRequestNeedsConfirmation = false;
}
......@@ -620,6 +659,7 @@ class ResidentCompiler {
}
_stdoutHandler.reset();
_server.stdin.writeln('reject');
printTrace('<- reject');
_compileRequestNeedsConfirmation = false;
return _stdoutHandler.compilerOutput.future;
}
......@@ -629,6 +669,7 @@ class ResidentCompiler {
/// kernel file.
void reset() {
_server?.stdin?.writeln('reset');
printTrace('<- reset');
}
String _mapFilename(String filename, PackageUriMapper packageUriMapper) {
......
......@@ -484,6 +484,8 @@ class DevFS {
outputPath: dillOutputPath ?? getDefaultApplicationKernelPath(trackWidgetCreation: trackWidgetCreation),
packagesFilePath : _packagesFilePath,
);
// list of sources that needs to be monitored are in [compilerOutput.sources]
//
// Don't send full kernel file that would overwrite what VM already
// started loading from.
if (!bundleFirstUpload) {
......
......@@ -78,14 +78,17 @@ example:org-dartlang-app:/
});
});
test(StdoutHandler, () async {
testUsingContext('StdOutHandler test', () async {
final StdoutHandler stdoutHandler = StdoutHandler();
stdoutHandler.handler('result 12345');
expect(stdoutHandler.boundaryKey, '12345');
stdoutHandler.handler('12345');
stdoutHandler.handler('12345 message 0');
final CompilerOutput output = await stdoutHandler.compilerOutput.future;
expect(output.errorCount, 0);
expect(output.outputFilename, 'message');
}, overrides: <Type, Generator>{
Logger: () => BufferLogger(),
});
group('batch compile', () {
......@@ -115,7 +118,7 @@ example:org-dartlang-app:/
when(mockFrontendServer.stdout)
.thenAnswer((Invocation invocation) => Stream<List<int>>.fromFuture(
Future<List<int>>.value(utf8.encode(
'result abc\nline1\nline2\nabc /path/to/main.dart.dill 0'
'result abc\nline1\nline2\nabc\nabc /path/to/main.dart.dill 0'
))
));
final CompilerOutput output = await kernelCompiler.compile(sdkRoot: '/path/to/sdkroot',
......@@ -138,7 +141,7 @@ example:org-dartlang-app:/
when(mockFrontendServer.stdout)
.thenAnswer((Invocation invocation) => Stream<List<int>>.fromFuture(
Future<List<int>>.value(utf8.encode(
'result abc\nline1\nline2\nabc'
'result abc\nline1\nline2\nabc\nabc'
))
));
final CompilerOutput output = await kernelCompiler.compile(sdkRoot: '/path/to/sdkroot',
......@@ -163,7 +166,7 @@ example:org-dartlang-app:/
when(mockFrontendServer.stdout)
.thenAnswer((Invocation invocation) => Stream<List<int>>.fromFuture(
Future<List<int>>.value(utf8.encode(
'result abc\nline1\nline2\nabc'
'result abc\nline1\nline2\nabc\nabc'
))
));
final CompilerOutput output = await kernelCompiler.compile(
......@@ -220,7 +223,7 @@ example:org-dartlang-app:/
when(mockFrontendServer.stdout)
.thenAnswer((Invocation invocation) => Stream<List<int>>.fromFuture(
Future<List<int>>.value(utf8.encode(
'result abc\nline1\nline2\nabc /path/to/main.dart.dill 0'
'result abc\nline1\nline2\nabc\nabc /path/to/main.dart.dill 0'
))
));
......@@ -264,7 +267,7 @@ example:org-dartlang-app:/
final StreamController<List<int>> streamController = StreamController<List<int>>();
when(mockFrontendServer.stdout)
.thenAnswer((Invocation invocation) => streamController.stream);
streamController.add(utf8.encode('result abc\nline0\nline1\nabc /path/to/main.dart.dill 0\n'));
streamController.add(utf8.encode('result abc\nline0\nline1\nabc\nabc /path/to/main.dart.dill 0\n'));
await generator.recompile(
'/path/to/main.dart',
null, /* invalidatedFiles */
......@@ -278,14 +281,14 @@ example:org-dartlang-app:/
await _reject(streamController, generator, mockFrontendServerStdIn, '', '');
await _recompile(streamController, generator, mockFrontendServerStdIn,
'result abc\nline1\nline2\nabc /path/to/main.dart.dill 0\n');
'result abc\nline1\nline2\nabc\nabc /path/to/main.dart.dill 0\n');
await _accept(streamController, generator, mockFrontendServerStdIn, '^accept\\n\$');
await _recompile(streamController, generator, mockFrontendServerStdIn,
'result abc\nline1\nline2\nabc /path/to/main.dart.dill 0\n');
'result abc\nline1\nline2\nabc\nabc /path/to/main.dart.dill 0\n');
await _reject(streamController, generator, mockFrontendServerStdIn, 'result abc\nabc\n',
await _reject(streamController, generator, mockFrontendServerStdIn, 'result abc\nabc\nabc\nabc',
'^reject\\n\$');
verifyNoMoreInteractions(mockFrontendServerStdIn);
......@@ -309,15 +312,15 @@ example:org-dartlang-app:/
when(mockFrontendServer.stdout)
.thenAnswer((Invocation invocation) => streamController.stream);
streamController.add(utf8.encode(
'result abc\nline0\nline1\nabc /path/to/main.dart.dill 0\n'
'result abc\nline0\nline1\nabc\nabc /path/to/main.dart.dill 0\n'
));
await generator.recompile('/path/to/main.dart', null /* invalidatedFiles */, outputPath: '/build/');
expect(mockFrontendServerStdIn.getAndClear(), 'compile /path/to/main.dart\n');
await _recompile(streamController, generator, mockFrontendServerStdIn,
'result abc\nline1\nline2\nabc /path/to/main.dart.dill 0\n');
'result abc\nline1\nline2\nabc\nabc /path/to/main.dart.dill 0\n');
await _recompile(streamController, generator, mockFrontendServerStdIn,
'result abc\nline2\nline3\nabc /path/to/main.dart.dill 0\n');
'result abc\nline2\nline3\nabc\nabc /path/to/main.dart.dill 0\n');
verifyNoMoreInteractions(mockFrontendServerStdIn);
expect(mockFrontendServerStdIn.getAndClear(), isEmpty);
......@@ -389,7 +392,7 @@ example:org-dartlang-app:/
compileExpressionResponseCompleter.future]));
compileResponseCompleter.complete(Future<List<int>>.value(utf8.encode(
'result abc\nline1\nline2\nabc /path/to/main.dart.dill 0\n'
'result abc\nline1\nline2\nabc\nabc /path/to/main.dart.dill 0\n'
)));
await generator.recompile(
......@@ -406,7 +409,7 @@ example:org-dartlang-app:/
compileExpressionResponseCompleter.complete(
Future<List<int>>.value(utf8.encode(
'result def\nline1\nline2\ndef /path/to/main.dart.dill.incremental 0\n'
'result def\nline1\nline2\ndef\ndef /path/to/main.dart.dill.incremental 0\n'
)));
generator.compileExpression(
'2+2', null, null, null, null, false).then(
......@@ -488,7 +491,7 @@ example:org-dartlang-app:/
);
compileResponseCompleter.complete(Future<List<int>>.value(utf8.encode(
'result abc\nline1\nline2\nabc /path/to/main.dart.dill 0\n'
'result abc\nline1\nline2\nabc\nabc /path/to/main.dart.dill 0\n'
)));
expect(await lastExpressionCompleted.future, isTrue);
......
......@@ -490,6 +490,6 @@ class MockResidentCompiler extends BasicMock implements ResidentCompiler {
Future<CompilerOutput> recompile(String mainPath, List<String> invalidatedFiles, { String outputPath, String packagesFilePath }) async {
fs.file(outputPath).createSync(recursive: true);
fs.file(outputPath).writeAsStringSync('compiled_kernel_output');
return CompilerOutput(outputPath, 0);
return CompilerOutput(outputPath, 0, <Uri>[]);
}
}
......@@ -177,7 +177,7 @@ Hello!
packagesPath: anyNamed('packagesPath'),
)).thenAnswer((_) async {
fs.file('$mainPath.dill').createSync(recursive: true);
return CompilerOutput('$mainPath.dill', 0);
return CompilerOutput('$mainPath.dill', 0, <Uri>[]);
});
final LaunchResult result = await device.startApp(null,
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment