// Copyright 2016 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.


{ // yield in try-catch

  let g = function*() {
    try {yield 1} catch (error) {assertEquals("caught", error)}
  };

  assertThrowsEquals(() => g().throw("not caught"), "not caught");

  {
    let x = g();
    assertEquals({value: 1, done: false}, x.next());
    assertEquals({value: undefined, done: true}, x.throw("caught"));
  }

  {
    let x = g();
    assertEquals({value: 1, done: false}, x.next());
    assertEquals({value: undefined, done: true}, x.next());
    assertThrowsEquals(() => x.throw("not caught"), "not caught");
  }
}


{ // return that doesn't close
  let g = function*() { try {return 42} finally {yield 43} };

  {
    let x = g();
    assertEquals({value: 43, done: false}, x.next());
    assertEquals({value: 42, done: true}, x.next());
  }
}


{ // return that doesn't close
  let x;
  let g = function*() { try {return 42} finally {x.throw(666)} };

  {
    x = g();
    assertThrows(() => x.next(), TypeError);  // still executing
  }
}


{ // yield in try-finally, finally clause performs return

  let g = function*() { try {yield 42} finally {return 13} };

  { // "return" closes at suspendedStart
    let x = g();
    assertEquals({value: 666, done: true}, x.return(666));
    assertEquals({value: undefined, done: true}, x.next(42));
    assertThrowsEquals(() => x.throw(43), 43);
    assertEquals({value: 42, done: true}, x.return(42));
  }

  { // "throw" closes at suspendedStart
    let x = g();
    assertThrowsEquals(() => x.throw(666), 666);
    assertEquals({value: undefined, done: true}, x.next(42));
    assertEquals({value: 43, done: true}, x.return(43));
    assertThrowsEquals(() => x.throw(44), 44);
  }

  { // "next" closes at suspendedYield
    let x = g();
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 13, done: true}, x.next(666));
    assertEquals({value: undefined, done: true}, x.next(666));
    assertThrowsEquals(() => x.throw(666), 666);
  }

  { // "return" closes at suspendedYield
    let x = g();
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 13, done: true}, x.return(666));
    assertEquals({value: undefined, done: true}, x.next(666));
    assertEquals({value: 666, done: true}, x.return(666));
  }

  { // "throw" closes at suspendedYield
    let x = g();
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 13, done: true}, x.throw(666));
    assertThrowsEquals(() => x.throw(666), 666);
    assertEquals({value: undefined, done: true}, x.next(666));
  }
}


{ // yield in try-finally, finally clause doesn't perform return

  let g = function*() { try {yield 42} finally {13} };

  { // "return" closes at suspendedStart
    let x = g();
    assertEquals({value: 666, done: true}, x.return(666));
    assertEquals({value: undefined, done: true}, x.next(42));
    assertThrowsEquals(() => x.throw(43), 43);
    assertEquals({value: 42, done: true}, x.return(42));
  }

  { // "throw" closes at suspendedStart
    let x = g();
    assertThrowsEquals(() => x.throw(666), 666);
    assertEquals({value: undefined, done: true}, x.next(42));
    assertEquals({value: 43, done: true}, x.return(43));
    assertThrowsEquals(() => x.throw(44), 44);
  }

  { // "next" closes at suspendedYield
    let x = g();
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: undefined, done: true}, x.next(666));
    assertEquals({value: undefined, done: true}, x.next(666));
    assertThrowsEquals(() => x.throw(666), 666);
    assertEquals({value: 42, done: true}, x.return(42));
  }

  { // "return" closes at suspendedYield
    let x = g();
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 666, done: true}, x.return(666));
    assertEquals({value: undefined, done: true}, x.next(666));
    assertThrowsEquals(() => x.throw(44), 44);
    assertEquals({value: 42, done: true}, x.return(42));
  }

  { // "throw" closes at suspendedYield
    let x = g();
    assertEquals({value: 42, done: false}, x.next());
    assertThrowsEquals(() => x.throw(666), 666);
    assertEquals({value: undefined, done: true}, x.next(666));
    assertThrowsEquals(() => x.throw(666), 666);
    assertEquals({value: 42, done: true}, x.return(42));
  }
}


{ // yield in try-finally, finally clause yields and performs return

  let g = function*() { try {yield 42} finally {yield 43; return 13} };

  {
    let x = g();
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 43, done: false}, x.return(666));
    assertEquals({value: 13, done: true}, x.next());
    assertEquals({value: 666, done: true}, x.return(666));
  }

  {
    let x = g();
    assertEquals({value: 666, done: true}, x.return(666));
    assertEquals({value: undefined, done: true}, x.next());
    assertEquals({value: 666, done: true}, x.return(666));
  }
}


{ // yield in try-finally, finally clause yields and doesn't perform return

  let g = function*() { try {yield 42} finally {yield 43; 13} };

  {
    let x = g();
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 43, done: false}, x.return(666));
    assertEquals({value: 666, done: true}, x.next());
    assertEquals({value: 5, done: true}, x.return(5));
  }

  {
    let x = g();
    assertEquals({value: 666, done: true}, x.return(666));
    assertEquals({value: undefined, done: true}, x.next());
    assertEquals({value: 666, done: true}, x.return(666));
  }
}


{ // yield*, finally clause performs return

  let h = function*() { try {yield 42} finally {yield 43; return 13} };
  let g = function*() { yield 1; yield yield* h(); };

  {
    let x = g();
    assertEquals({value: 1, done: false}, x.next());
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 43, done: false}, x.next(666));
    assertEquals({value: 13, done: false}, x.next());
    assertEquals({value: undefined, done: true}, x.next());
  }

  {
    let x = g();
    assertEquals({value: 1, done: false}, x.next());
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 43, done: false}, x.return(666));
    assertEquals({value: 13, done: false}, x.next());
    assertEquals({value: undefined, done: true}, x.next());
  }

  {
    let x = g();
    assertEquals({value: 1, done: false}, x.next());
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 43, done: false}, x.throw(666));
    assertEquals({value: 13, done: false}, x.next());
    assertEquals({value: undefined, done: true}, x.next());
  }
}


{ // yield*, finally clause does not perform return

  let h = function*() { try {yield 42} finally {yield 43; 13} };
  let g = function*() { yield 1; yield yield* h(); };

  {
    let x = g();
    assertEquals({value: 1, done: false}, x.next());
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 43, done: false}, x.next(666));
    assertEquals({value: undefined, done: false}, x.next());
    assertEquals({value: undefined, done: true}, x.next());
  }

  {
    let x = g();
    assertEquals({value: 1, done: false}, x.next());
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 43, done: false}, x.return(666));
    assertEquals({value: undefined, done: false}, x.next());
    assertEquals({value: undefined, done: true}, x.next());
  }

  {
    let x = g();
    assertEquals({value: 1, done: false}, x.next());
    assertEquals({value: 42, done: false}, x.next());
    assertEquals({value: 43, done: false}, x.throw(666));
    assertThrowsEquals(() => x.next(), 666);
  }
}
