Convert ShadowFunctionDeclaration to FunctionDeclarationJudgment, add FunctionNodeJudgment.

Change-Id: Ib1edf20c22b448314cc2b1028559d3466ecfe4f8
Reviewed-on: https://dart-review.googlesource.com/61916
Reviewed-by: Brian Wilkerson <brianwilkerson@google.com>
Reviewed-by: Paul Berry <paulberry@google.com>
Commit-Queue: Konstantin Shcheglov <scheglov@google.com>
diff --git a/pkg/front_end/lib/src/fasta/kernel/body_builder.dart b/pkg/front_end/lib/src/fasta/kernel/body_builder.dart
index 6810e39..da8635e 100644
--- a/pkg/front_end/lib/src/fasta/kernel/body_builder.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/body_builder.dart
@@ -3014,7 +3014,7 @@
       deprecated_addCompileTimeError(offsetForToken(name.token),
           "'${variable.name}' already declared in this scope.");
     }
-    push(new ShadowFunctionDeclaration(
+    push(new FunctionDeclarationJudgment(
         variable,
         // The function node is created later.
         null)
@@ -3079,7 +3079,7 @@
     if (!isFunctionExpression) {
       annotations = pop(); // Metadata.
     }
-    FunctionNode function = formals.addToFunction(new FunctionNode(body,
+    FunctionNode function = formals.addToFunction(new FunctionNodeJudgment(body,
         typeParameters: typeParameters,
         asyncMarker: asyncModifier,
         returnType: returnType)
@@ -3093,7 +3093,7 @@
           variable.addAnnotation(annotation);
         }
       }
-      ShadowFunctionDeclaration.setHasImplicitReturnType(
+      FunctionDeclarationJudgment.setHasImplicitReturnType(
           declaration, hasImplicitReturnType);
 
       variable.type = function.functionType;
@@ -3163,7 +3163,7 @@
     FormalParameters<Expression, Statement, Arguments> formals = pop();
     exitFunction();
     List<TypeParameter> typeParameters = typeVariableBuildersToKernel(pop());
-    FunctionNode function = formals.addToFunction(new FunctionNode(body,
+    FunctionNode function = formals.addToFunction(new FunctionNodeJudgment(body,
         typeParameters: typeParameters, asyncMarker: asyncModifier)
       ..fileOffset = beginToken.charOffset
       ..fileEndOffset = token.charOffset);
diff --git a/pkg/front_end/lib/src/fasta/kernel/kernel_ast_api.dart b/pkg/front_end/lib/src/fasta/kernel/kernel_ast_api.dart
index 437f507..669600c 100644
--- a/pkg/front_end/lib/src/fasta/kernel/kernel_ast_api.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/kernel_ast_api.dart
@@ -77,8 +77,9 @@
         ShadowFactoryConstructorInvocation,
         ShadowFieldInitializer,
         ForInJudgment,
-        ShadowFunctionDeclaration,
+        FunctionDeclarationJudgment,
         FunctionExpressionJudgment,
+        FunctionNodeJudgment,
         IfNullJudgment,
         IfJudgment,
         IllegalAssignmentJudgment,
diff --git a/pkg/front_end/lib/src/fasta/kernel/kernel_shadow_ast.dart b/pkg/front_end/lib/src/fasta/kernel/kernel_shadow_ast.dart
index 88a0d42..a274a42 100644
--- a/pkg/front_end/lib/src/fasta/kernel/kernel_shadow_ast.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/kernel_shadow_ast.dart
@@ -1280,38 +1280,66 @@
   }
 }
 
+/// Concrete shadow object representing a function expression in kernel form.
+class FunctionNodeJudgment extends FunctionNode {
+  FunctionNodeJudgment(Statement body,
+      {List<TypeParameter> typeParameters,
+      List<VariableDeclaration> positionalParameters,
+      List<VariableDeclaration> namedParameters,
+      int requiredParameterCount,
+      DartType returnType: const DynamicType(),
+      AsyncMarker asyncMarker: AsyncMarker.Sync,
+      AsyncMarker dartAsyncMarker})
+      : super(body,
+            typeParameters: typeParameters,
+            positionalParameters: positionalParameters,
+            namedParameters: namedParameters,
+            requiredParameterCount: requiredParameterCount,
+            returnType: returnType,
+            asyncMarker: asyncMarker,
+            dartAsyncMarker: dartAsyncMarker);
+
+  void infer<Expression, Statement, Initializer, Type>(
+      ShadowTypeInferrer inferrer,
+      Factory<Expression, Statement, Initializer, Type> factory,
+      bool hasImplicitReturnType,
+      int returnTypeInstrumentationOffset) {
+    DartType returnContext = hasImplicitReturnType
+        ? (inferrer.strongMode ? null : const DynamicType())
+        : returnType;
+    inferrer.inferLocalFunction(
+        factory, this, null, returnTypeInstrumentationOffset, returnContext);
+  }
+}
+
 /// Concrete shadow object representing a local function declaration in kernel
 /// form.
-class ShadowFunctionDeclaration extends FunctionDeclaration
+class FunctionDeclarationJudgment extends FunctionDeclaration
     implements StatementJudgment {
   bool _hasImplicitReturnType = false;
 
-  ShadowFunctionDeclaration(
+  FunctionDeclarationJudgment(
       VariableDeclarationJudgment variable, FunctionNode function)
       : super(variable, function);
 
   VariableDeclarationJudgment get variableJudgment => variable;
 
+  FunctionNodeJudgment get functionJudgment => function;
+
   @override
   void infer<Expression, Statement, Initializer, Type>(
       ShadowTypeInferrer inferrer,
       Factory<Expression, Statement, Initializer, Type> factory) {
     inferrer.inferMetadataKeepingHelper(factory, variable.annotations);
-    inferrer.inferLocalFunction(
-        factory,
-        function,
-        null,
-        fileOffset,
-        _hasImplicitReturnType
-            ? (inferrer.strongMode ? null : const DynamicType())
-            : function.returnType);
+    functionJudgment.infer(
+        inferrer, factory, _hasImplicitReturnType, fileOffset);
     var inferredType = variable.type = function.functionType;
     inferrer.listener.functionDeclaration(
         variableJudgment.createLemma(inferrer), inferredType);
   }
 
   static void setHasImplicitReturnType(
-      ShadowFunctionDeclaration declaration, bool hasImplicitReturnType) {
+      FunctionDeclarationJudgment declaration, bool hasImplicitReturnType) {
     declaration._hasImplicitReturnType = hasImplicitReturnType;
   }
 }