Build elements for constructor initializers.

R=brianwilkerson@google.com

Change-Id: Ic41e6ec93571f0407184f8b8e8271517e1e1ec59
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/101000
Reviewed-by: Brian Wilkerson <brianwilkerson@google.com>
Commit-Queue: Konstantin Shcheglov <scheglov@google.com>
diff --git a/pkg/analyzer/lib/src/summary2/declaration_splicer.dart b/pkg/analyzer/lib/src/summary2/declaration_splicer.dart
index 468fb19..7120538 100644
--- a/pkg/analyzer/lib/src/summary2/declaration_splicer.dart
+++ b/pkg/analyzer/lib/src/summary2/declaration_splicer.dart
@@ -28,10 +28,15 @@
   }
 
   FunctionBody _body(FunctionBody full) {
+    _buildLocalElements(full);
+    return full;
+  }
+
+  void _buildLocalElements(AstNode node) {
     var holder = ElementHolder();
 
     var elementBuilder = LocalElementBuilder(holder, null);
-    full.accept(elementBuilder);
+    node.accept(elementBuilder);
 
     var element = _walker.element;
     if (element is ExecutableElementImpl) {
@@ -39,8 +44,6 @@
       element.encloseElements(holder.labels);
       element.encloseElements(holder.localVariables);
     }
-
-    return full;
   }
 
   void _classDeclaration(ClassDeclaration full, ClassDeclaration partial) {
@@ -74,16 +77,23 @@
     _match(partial.name, element);
     (partial as ConstructorDeclarationImpl).declaredElement = element;
     _walk(_ElementWalker.forExecutable(element), () {
-      _node(full.parameters, partial.parameters);
-      // TODO(scheglov) Not very nice.
-      if (full.initializers.isNotEmpty && partial.initializers.isEmpty) {
-        partial.initializers.addAll(full.initializers);
-      }
+      _formalParameterList(full.parameters, partial.parameters);
+      _constructorInitializers(full.initializers, partial.initializers);
       partial.body = _body(full.body);
     });
     _metadata(partial.metadata, element);
   }
 
+  void _constructorInitializers(
+    List<ConstructorInitializer> full,
+    List<ConstructorInitializer> partial,
+  ) {
+    if (full.isNotEmpty && partial.isEmpty) {
+      partial.addAll(full);
+    }
+    partial.forEach(_buildLocalElements);
+  }
+
   void _declarations(CompilationUnit full, CompilationUnit partial) {
     _walk(_ElementWalker.forCompilationUnit(_unitElement), () {
       var fullList = full.declarations;
diff --git a/pkg/analyzer/test/src/dart/resolution/constructor_test.dart b/pkg/analyzer/test/src/dart/resolution/constructor_test.dart
new file mode 100644
index 0000000..b91fbda
--- /dev/null
+++ b/pkg/analyzer/test/src/dart/resolution/constructor_test.dart
@@ -0,0 +1,38 @@
+// Copyright (c) 2019, 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 'package:test_reflective_loader/test_reflective_loader.dart';
+
+import 'driver_resolution.dart';
+
+main() {
+  defineReflectiveSuite(() {
+    defineReflectiveTests(ConstructorResolutionTest);
+  });
+}
+
+@reflectiveTest
+class ConstructorResolutionTest extends DriverResolutionTest {
+  test_initializer_field_functionExpression_expressionBody() async {
+    addTestFile(r'''
+class C {
+  final int x;
+  C(int a) : x = (() => a + 1)();
+}
+''');
+    await resolveTestFile();
+    assertElement(findNode.simple('a + 1'), findElement.parameter('a'));
+  }
+
+  test_initializer_field_functionExpression_blockBody() async {
+    addTestFile(r'''
+class C {
+  var x;
+  C(int a) : x = (() {return a + 1;})();
+}
+''');
+    await resolveTestFile();
+    assertElement(findNode.simple('a + 1'), findElement.parameter('a'));
+  }
+}
diff --git a/pkg/analyzer/test/src/dart/resolution/test_all.dart b/pkg/analyzer/test/src/dart/resolution/test_all.dart
index ccbc919..8c03439 100644
--- a/pkg/analyzer/test/src/dart/resolution/test_all.dart
+++ b/pkg/analyzer/test/src/dart/resolution/test_all.dart
@@ -9,6 +9,7 @@
 import 'class_test.dart' as class_resolution;
 import 'comment_test.dart' as comment;
 import 'constant_test.dart' as constant;
+import 'constructor_test.dart' as constructor;
 import 'definite_assignment_test.dart' as definite_assignment;
 import 'enum_test.dart' as enum_resolution;
 import 'flow_analysis_test.dart' as flow_analysis;
@@ -36,6 +37,7 @@
     class_resolution.main();
     comment.main();
     constant.main();
+    constructor.main();
     definite_assignment.main();
     enum_resolution.main();
     flow_analysis.main();