| Index: pkg/kernel/lib/transformations/closure/info.dart | 
| diff --git a/pkg/kernel/lib/transformations/closure/info.dart b/pkg/kernel/lib/transformations/closure/info.dart | 
| index 2d9c2ca3c90f6f38ea3b78201741b63a3eaa7c94..b47da636cc3c54acac95d7a22522dd7726b69b29 100644 | 
| --- a/pkg/kernel/lib/transformations/closure/info.dart | 
| +++ b/pkg/kernel/lib/transformations/closure/info.dart | 
| @@ -9,13 +9,17 @@ import '../../ast.dart' | 
| Class, | 
| Constructor, | 
| Field, | 
| +        FieldInitializer, | 
| FunctionDeclaration, | 
| FunctionNode, | 
| +        LocalInitializer, | 
| Member, | 
| Name, | 
| Procedure, | 
| ProcedureKind, | 
| PropertyGet, | 
| +        RedirectingInitializer, | 
| +        SuperInitializer, | 
| ThisExpression, | 
| TypeParameter, | 
| TypeParameterType, | 
| @@ -100,8 +104,30 @@ class ClosureInfo extends RecursiveVisitor { | 
| } | 
|  | 
| visitConstructor(Constructor node) { | 
| +    /// [currentFunction] should be set to [currentMemberFunction] before | 
| +    /// visiting the [FunctionNode] of the constructor, because initializers may | 
| +    /// use constructor parameters and it shouldn't be treated as capturing | 
| +    /// them.  Consider the following code: | 
| +    /// | 
| +    ///     class A { | 
| +    ///       int x; | 
| +    ///       A(int x)  /* [x] is visible in initializers and body. */ | 
| +    ///         : this.x = x {  /* Initializer. */ | 
| +    ///         /* Constructor body. */ | 
| +    ///       } | 
| +    ///     } | 
| +    /// | 
| +    /// Here the parameter shouldn't be captured into a context in the | 
| +    /// initializer.  However, [currentFunction] is `null` if not set, and | 
| +    /// `function[node.variable]` in this case points to the [FunctionNode] of | 
| +    /// the constructor (which is not `null`).  It leads to `x` being treated as | 
| +    /// captured, because it's seen as used outside of the function where it is | 
| +    /// declared.  In turn, it leads to unnecessary context creation and usage. | 
| beginMember(node, node.function); | 
| -    super.visitConstructor(node); | 
| +    saveCurrentFunction(() { | 
| +      currentFunction = currentMemberFunction; | 
| +      super.visitConstructor(node); | 
| +    }); | 
| endMember(); | 
| } | 
|  | 
| @@ -158,10 +184,12 @@ class ClosureInfo extends RecursiveVisitor { | 
|  | 
| visitFunctionNode(FunctionNode node) { | 
| localNames.putIfAbsent(node, computeUniqueLocalName); | 
| -    var saved = currentFunction; | 
| -    currentFunction = node; | 
| -    node.visitChildren(this); | 
| -    currentFunction = saved; | 
| + | 
| +    saveCurrentFunction(() { | 
| +      currentFunction = node; | 
| +      node.visitChildren(this); | 
| +    }); | 
| + | 
| Set<TypeParameter> capturedTypeVariables = typeVariables[node]; | 
| if (capturedTypeVariables != null && !isOuterMostContext) { | 
| // Propagate captured type variables to enclosing function. | 
| @@ -209,4 +237,13 @@ class ClosureInfo extends RecursiveVisitor { | 
| invokedGetters.add(node.name); | 
| super.visitPropertyGet(node); | 
| } | 
| + | 
| +  saveCurrentFunction(void f()) { | 
| +    var saved = currentFunction; | 
| +    try { | 
| +      f(); | 
| +    } finally { | 
| +      currentFunction = saved; | 
| +    } | 
| +  } | 
| } | 
|  |