Roll engine to 4c79e423dc6f89f98d8ceb263a5ca78e2f2da996 (#23384)

Also includes
  * Updates to affected tests
  * Change flutter_tools to pass package URIs to the Dart front end
    instead of filesystem paths
diff --git a/bin/internal/engine.version b/bin/internal/engine.version
index 9face4a..6c3c7fa 100644
--- a/bin/internal/engine.version
+++ b/bin/internal/engine.version
@@ -1 +1 @@
-58cdd53f9083412fa7da893f53c1ca1c93500532
+4c79e423dc6f89f98d8ceb263a5ca78e2f2da996
diff --git a/packages/flutter_tools/lib/src/base/build.dart b/packages/flutter_tools/lib/src/base/build.dart
index 4ee873f..0999f01 100644
--- a/packages/flutter_tools/lib/src/base/build.dart
+++ b/packages/flutter_tools/lib/src/base/build.dart
@@ -291,6 +291,7 @@
     @required TargetPlatform platform,
     @required BuildMode buildMode,
     @required String mainPath,
+    @required String packagesPath,
     @required String outputPath,
     List<String> extraFrontEndOptions = const <String>[],
   }) async {
@@ -306,6 +307,7 @@
     final CompilerOutput compilerOutput = await kernelCompiler.compile(
       sdkRoot: artifacts.getArtifactPath(Artifact.flutterPatchedSdkPath),
       mainPath: mainPath,
+      packagesPath: packagesPath,
       outputFilePath: fs.path.join(outputPath, 'app.dill'),
       depFilePath: depfilePath,
       extraFrontEndOptions: extraFrontEndOptions,
diff --git a/packages/flutter_tools/lib/src/commands/build_aot.dart b/packages/flutter_tools/lib/src/commands/build_aot.dart
index fadfa6d..5989b9a 100644
--- a/packages/flutter_tools/lib/src/commands/build_aot.dart
+++ b/packages/flutter_tools/lib/src/commands/build_aot.dart
@@ -84,6 +84,7 @@
         platform: platform,
         buildMode: buildMode,
         mainPath: mainPath,
+        packagesPath: PackageMap.globalPackagesPath,
         outputPath: outputPath,
         extraFrontEndOptions: argResults[FlutterOptions.kExtraFrontEndOptions],
       );
diff --git a/packages/flutter_tools/lib/src/compile.dart b/packages/flutter_tools/lib/src/compile.dart
index 9ae0778..761de49 100644
--- a/packages/flutter_tools/lib/src/compile.dart
+++ b/packages/flutter_tools/lib/src/compile.dart
@@ -10,10 +10,13 @@
 import 'artifacts.dart';
 import 'base/common.dart';
 import 'base/context.dart';
+import 'base/file_system.dart';
 import 'base/fingerprint.dart';
 import 'base/io.dart';
+import 'base/platform.dart';
 import 'base/process_manager.dart';
 import 'base/terminal.dart';
+import 'dart/package_map.dart';
 import 'globals.dart';
 
 KernelCompiler get kernelCompiler => context[KernelCompiler];
@@ -74,6 +77,42 @@
   }
 }
 
+// Converts filesystem paths to package URIs.
+class _PackageUriMapper {
+  _PackageUriMapper(String scriptPath, String packagesPath) {
+    final Map<String, Uri> packageMap = PackageMap(fs.path.absolute(packagesPath)).map;
+    final String scriptUri = Uri.file(scriptPath, windows: platform.isWindows).toString();
+
+    for (String packageName in packageMap.keys) {
+      final String prefix = packageMap[packageName].toString();
+      if (scriptUri.startsWith(prefix)) {
+        _packageName = packageName;
+        _uriPrefix = prefix;
+        return;
+      }
+    }
+  }
+
+  String _packageName;
+  String _uriPrefix;
+
+  Uri map(String scriptPath) {
+    if (_packageName == null)
+      return null;
+
+    final String scriptUri = Uri.file(scriptPath, windows: platform.isWindows).toString();
+    if (scriptUri.startsWith(_uriPrefix)) {
+      return Uri.parse('package:$_packageName/${scriptUri.substring(_uriPrefix.length)}');
+    }
+
+    return null;
+  }
+
+  static Uri findUri(String scriptPath, String packagesPath) {
+    return _PackageUriMapper(scriptPath, packagesPath).map(scriptPath);
+  }
+}
+
 class KernelCompiler {
   const KernelCompiler();
 
@@ -168,7 +207,14 @@
 
     if (extraFrontEndOptions != null)
       command.addAll(extraFrontEndOptions);
-    command.add(mainPath);
+
+    Uri mainUri;
+    if (packagesPath != null) {
+      command.addAll(<String>['--packages', packagesPath]);
+      mainUri = _PackageUriMapper.findUri(mainPath, packagesPath);
+    }
+    command.add(mainUri?.toString() ?? mainPath);
+
     printTrace(command.join(' '));
     final Process server = await processManager
         .start(command)
@@ -302,15 +348,26 @@
 
     // First time recompile is called we actually have to compile the app from
     // scratch ignoring list of invalidated files.
+    _PackageUriMapper packageUriMapper;
+    if (request.packagesFilePath != null) {
+      packageUriMapper = _PackageUriMapper(request.mainPath, request.packagesFilePath);
+    }
+
     if (_server == null) {
-      return _compile(_mapFilename(request.mainPath),
-          request.outputPath, _mapFilename(request.packagesFilePath));
+      return _compile(
+          _mapFilename(request.mainPath, packageUriMapper),
+          request.outputPath,
+          _mapFilename(request.packagesFilePath, /* packageUriMapper= */ null)
+      );
     }
 
     final String inputKey = Uuid().generateV4();
-    _server.stdin.writeln('recompile ${request.mainPath != null ? _mapFilename(request.mainPath) + " ": ""}$inputKey');
+    final String mainUri = request.mainPath != null
+        ? _mapFilename(request.mainPath, packageUriMapper) + ' '
+        : '';
+    _server.stdin.writeln('recompile $mainUri$inputKey');
     for (String fileUri in request.invalidatedFiles) {
-      _server.stdin.writeln(_mapFileUri(fileUri));
+      _server.stdin.writeln(_mapFileUri(fileUri, packageUriMapper));
     }
     _server.stdin.writeln(inputKey);
 
@@ -334,7 +391,7 @@
     }
   }
 
-  Future<CompilerOutput> _compile(String scriptFilename, String outputPath,
+  Future<CompilerOutput> _compile(String scriptUri, String outputPath,
       String packagesFilePath) async {
     final String frontendServer = artifacts.getArtifactPath(
       Artifact.frontendServerSnapshotForEngineDartSdk
@@ -394,7 +451,7 @@
       .transform<String>(const LineSplitter())
       .listen((String message) { printError(message); });
 
-    _server.stdin.writeln('compile $scriptFilename');
+    _server.stdin.writeln('compile $scriptUri');
 
     return _stdoutHandler.compilerOutput.future;
   }
@@ -457,22 +514,28 @@
     _server?.stdin?.writeln('reset');
   }
 
-  String _mapFilename(String filename) {
-    if (_fileSystemRoots != null) {
-      for (String root in _fileSystemRoots) {
-        if (filename.startsWith(root)) {
-          return Uri(
-              scheme: _fileSystemScheme, path: filename.substring(root.length))
-              .toString();
-        }
-      }
-    }
-    return filename;
+  String _mapFilename(String filename, _PackageUriMapper packageUriMapper) {
+    return _doMapFilename(filename, packageUriMapper) ?? filename;
   }
 
-  String _mapFileUri(String fileUri) {
+  String _mapFileUri(String fileUri, _PackageUriMapper packageUriMapper) {
+    String filename;
+    try {
+      filename = Uri.parse(fileUri).toFilePath();
+    } on UnsupportedError catch (_) {
+      return fileUri;
+    }
+    return _doMapFilename(filename, packageUriMapper) ?? fileUri;
+  }
+
+  String _doMapFilename(String filename, _PackageUriMapper packageUriMapper) {
+    if (packageUriMapper != null) {
+      final Uri packageUri = packageUriMapper.map(filename);
+      if (packageUri != null)
+        return packageUri.toString();
+    }
+
     if (_fileSystemRoots != null) {
-      final String filename = Uri.parse(fileUri).toFilePath();
       for (String root in _fileSystemRoots) {
         if (filename.startsWith(root)) {
           return Uri(
@@ -481,7 +544,7 @@
         }
       }
     }
-    return fileUri;
+    return null;
   }
 
   Future<dynamic> shutdown() {
diff --git a/packages/flutter_tools/test/integration/expression_evaluation_test.dart b/packages/flutter_tools/test/integration/expression_evaluation_test.dart
index e594f2a..2ecddfc 100644
--- a/packages/flutter_tools/test/integration/expression_evaluation_test.dart
+++ b/packages/flutter_tools/test/integration/expression_evaluation_test.dart
@@ -33,13 +33,13 @@
 
     Future<VMIsolate> breakInBuildMethod(FlutterTestDriver flutter) async {
       return _flutter.breakAt(
-          Uri.file(_project.buildMethodBreakpointFile),
+          Uri.parse('package:test/main.dart'),
           _project.buildMethodBreakpointLine);
     }
 
     Future<VMIsolate> breakInTopLevelFunction(FlutterTestDriver flutter) async {
       return _flutter.breakAt(
-          Uri.file(_project.topLevelFunctionBreakpointFile),
+          Uri.parse('package:test/main.dart'),
           _project.topLevelFunctionBreakpointLine);
     }
 
diff --git a/packages/flutter_tools/test/integration/hot_reload_test.dart b/packages/flutter_tools/test/integration/hot_reload_test.dart
index 3abe5c3..86c0125 100644
--- a/packages/flutter_tools/test/integration/hot_reload_test.dart
+++ b/packages/flutter_tools/test/integration/hot_reload_test.dart
@@ -41,7 +41,7 @@
     test('reload hits breakpoints after reload', () async {
       await _flutter.run(withDebugger: true);
       final VMIsolate isolate = await _flutter.breakAt(
-          Uri.file(_project.breakpointFile),
+          Uri.parse('package:test/main.dart'),
           _project.breakpointLine);
       expect(isolate.pauseEvent, isInstanceOf<VMPauseBreakpointEvent>());
     });