// Copyright (c) 2011, 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.

// @dart = 2.9

import "package:expect/expect.dart";

// Tests function statements and expressions.

class Bug4089219 {
  int x;
  var f;

  Bug4089219(int i) : this.x = i {
    f = () => x;
  }
}

class Bug4342163 {
  final m;
  Bug4342163(int a) : this.m = (() => a) {}
}

class StaticFunctionDef {
  static const int one = 1;
  static var fn1;
  static var fn2;
  static var fn3;

  static init() {
    fn1 = () {
      return one;
    };
    fn2 = () {
      return (() {
        return one;
      })();
    };
    fn3 = () {
      final local = 1;
      return (() {
        return local;
      })();
    };
  }
}

class A {
  var ma;
  A(a) {
    ma = a;
  }
}

class B1 extends A {
  final mfn;
  B1(int a)
      : this.mfn = (() {
          return a;
        }),
        super(a);
}

class B2 extends A {
  final mfn;
  B2(int a)
      : this.mfn = (() {
          return a;
        }),
        super(2);
}

class B3 extends A {
  final mfn;
  B3(int a)
      : this.mfn = (() {
          return a;
        }),
        super(() {
          return a;
        });
}

typedef void Fisk();

class FunctionTest {
  FunctionTest() {}

  static void testMain() {
    var test = new FunctionTest();
    test.testForEach();
    test.testVarOrder1();
    test.testVarOrder2();
    test.testLexicalClosureRef1();
    test.testLexicalClosureRef2();
    test.testLexicalClosureRef3();
    test.testLexicalClosureRef4();
    test.testLexicalClosureRef5();
    test.testDefaultParametersOrder();
    test.testParametersOrder();
    test.testFunctionDefaults1();
    test.testFunctionDefaults2();
    test.testEscapingFunctions();
    test.testThisBinding();
    test.testFnBindingInStatics();
    test.testFnBindingInInitLists();
    test.testSubclassConstructorScopeAlias();
  }

  void testSubclassConstructorScopeAlias() {
    var b1 = new B1(10);
    Expect.equals(10, (b1.mfn)());
    Expect.equals(10, b1.ma);

    var b2 = new B2(11);
    Expect.equals(11, (b2.mfn)());
    Expect.equals(2, b2.ma);

    var b3 = new B3(12);
    Expect.equals(12, (b3.mfn)());
    Expect.equals(12, (b3.ma)());
  }

  void testFnBindingInInitLists() {
    Expect.equals(1, (new Bug4342163(1).m)());
  }

  void testFnBindingInStatics() {
    StaticFunctionDef.init();
    Expect.equals(1, ((StaticFunctionDef.fn1)()));
    Expect.equals(1, ((StaticFunctionDef.fn2)()));
    Expect.equals(1, ((StaticFunctionDef.fn3)()));
  }

  Fisk testReturnVoidFunction() {
    void f() {}
    Fisk x = f;
    return f;
  }

  void testVarOrder1() {
    var a = 0, b = a++, c = a++;

    Expect.equals(a, 2);
    Expect.equals(b, 0);
    Expect.equals(c, 1);
  }

  void testVarOrder2() {
    var a = 0;
    f() {
      return a++;
    }

    ;
    var b = f(), c = f();

    Expect.equals(a, 2);
    Expect.equals(b, 0);
    Expect.equals(c, 1);
  }

  void testLexicalClosureRef1() {
    var a = 1;
    var f, g;
    {
      var b = 2;
      f = () {
        return b - a;
      };
    }

    {
      var b = 3;
      g = () {
        return b - a;
      };
    }
    Expect.equals(1, f());
    Expect.equals(2, g());
  }

  void testLexicalClosureRef2() {
    var a = 1;
    var f, g;
    {
      var b = 2;
      f = () {
        return (() {
          return b - a;
        })();
      };
    }

    {
      var b = 3;
      g = () {
        return (() {
          return b - a;
        })();
      };
    }
    Expect.equals(1, f());
    Expect.equals(2, g());
  }

  void testLexicalClosureRef3() {
    var a = [];
    for (int i = 0; i < 10; i++) {
      var x = i;
      a.add(() {
        return x;
      });
    }

    var sum = 0;
    for (int i = 0; i < a.length; i++) {
      sum += (a[i])();
    }

    Expect.equals(45, sum);
  }

  void testLexicalClosureRef5() {
    {
      var a;
      Expect.equals(null, a);
      a = 1;
      Expect.equals(1, a);
    }

    {
      var a;
      Expect.equals(null, a);
      a = 1;
      Expect.equals(1, a);
    }
  }

  // Make sure labels are preserved, and a second 'i' does influence the first.
  void testLexicalClosureRef4() {
    var a = [];
    x:
    for (int i = 0; i < 10; i++) {
      a.add(() {
        return i;
      });
      continue x;
    }

    var sum = 0;
    for (int i = 0; i < a.length; i++) {
      sum += (a[i])();
    }

    Expect.equals(45, sum);
  }

  int tempField;

  void testForEach() {
    List<int> vals = [1, 2, 3];
    int total = 0;
    vals.forEach((int v) {
      total += v;
    });
    Expect.equals(6, total);
  }

  void testDefaultParametersOrder() {
    f([a = 1, b = 3]) {
      return a - b;
    }

    Expect.equals(-2, f());
  }

  void testParametersOrder() {
    f(a, b) {
      return a - b;
    }

    Expect.equals(-2, f(1, 3));
  }

  void testFunctionDefaults1() {
    // TODO(jimhug): This return null shouldn't be necessary.
    f() {
      return null;
    }

    ;
    (([a = 10]) {
      Expect.equals(10, a);
    })();
    ((a, [b = 10]) {
      Expect.equals(10, b);
    })(1);
    (([a = 10]) {
      Expect.equals(null, a);
    })(f());
    // FAILS: (([a = 10]) { Expect.equals(null ,a); })( f() );
  }

  void testFunctionDefaults2() {
    Expect.equals(10, helperFunctionDefaults2());
    Expect.equals(1, helperFunctionDefaults2(1));
  }

  num helperFunctionDefaults2([a = 10]) {
    return (() {
      return a;
    })();
  }

  void testEscapingFunctions() {
    f() {
      return 42;
    }

    ;
    (() {
      Expect.equals(42, f());
    })();
    var o = new Bug4089219(42);
    Expect.equals(42, (o.f)());
  }

  void testThisBinding() {
    Expect.equals(this, () {
      return this;
    }());
  }
}

typedef void Foo<A, B>(A a, B b);

class Bar<A, B> {
  Foo<A, B> field;
  Bar(A a, B b) : this.field = ((A a1, B b2) {}) {
    field(a, b);
  }
}

typedef UntypedFunction(arg);
typedef UntypedFunction2(arg);

class UseFunctionTypes {
  void test() {
    Function f = null;
    UntypedFunction uf = null;
    UntypedFunction2 uf2 = null;
    Foo foo = null;
    Foo<int, String> fooIntString = null;
    Foo<Object, Object> fooObjectObject = null;

    f = uf;
    f = uf2;
    f = foo;
    f = fooIntString;

    uf = f;
    uf2 = f;
    foo = f;
    fooIntString = f;

    fooIntString = foo;

    foo = fooObjectObject;
    fooObjectObject = foo;

    uf = uf2;
    uf2 = uf;
  }
}

main() {
  FunctionTest.testMain();
}
