star-rhs-iter-rtrn-res-done-no-value.js (2861B)
1 // Copyright (C) 2016 the V8 project authors. All rights reserved. 2 // This code is governed by the BSD license found in the LICENSE file. 3 /*--- 4 esid: sec-generator-function-definitions-runtime-semantics-evaluation 5 es6id: 14.4.14 6 description: > 7 `value` property is not accessed when iteration is incomplete 8 info: | 9 YieldExpression : yield * AssignmentExpression 10 11 1. Let exprRef be the result of evaluating AssignmentExpression. 12 2. Let value be ? GetValue(exprRef). 13 3. Let iterator be ? GetIterator(value). 14 4. Let received be NormalCompletion(undefined). 15 5. Repeat 16 a. If received.[[Type]] is normal, then 17 [...] 18 b. Else if received.[[Type]] is throw, then 19 [...] 20 c. Else, 21 i. Assert: received.[[Type]] is return. 22 ii. Let return be ? GetMethod(iterator, "return"). 23 iii. If return is undefined, return Completion(received). 24 iv. Let innerReturnResult be ? Call(return, iterator, « 25 received.[[Value]] »). 26 v. If Type(innerReturnResult) is not Object, throw a TypeError 27 exception. 28 vi. Let done be ? IteratorComplete(innerReturnResult). 29 vii. If done is true, then 30 1. Let value be ? IteratorValue(innerReturnResult). 31 2. Return Completion{[[Type]]: return, [[Value]]: value, 32 [[Target]]: empty}. 33 viii. Let received be GeneratorYield(innerReturnResult). 34 35 7.4.3 IteratorComplete 36 37 1. Assert: Type(iterResult) is Object. 38 2. Return ToBoolean(? Get(iterResult, "done")). 39 features: [generators, Symbol.iterator] 40 ---*/ 41 42 var badIter = {}; 43 var callCount = 0; 44 var spyValue = Object.defineProperty({ done: false }, 'value', { 45 get: function() { 46 callCount += 1; 47 } 48 }); 49 badIter[Symbol.iterator] = function() { 50 return { 51 next: function() { 52 return { done: false }; 53 }, 54 return: function() { 55 return spyValue; 56 } 57 }; 58 }; 59 var normalCompletion = false; 60 var errorCompletion = false; 61 var delegationComplete = false; 62 function* g() { 63 try { 64 yield * badIter; 65 normalCompletion = true; 66 } catch (_) { 67 errorCompletion = true; 68 } finally { 69 delegationComplete = true; 70 } 71 } 72 var iter = g(); 73 74 iter.next(); 75 assert.sameValue(callCount, 0, 'access count (first iteration)'); 76 assert.sameValue( 77 delegationComplete, false, 'delegation ongoing (first iteration)' 78 ); 79 80 iter.return(); 81 assert.sameValue(callCount, 0, 'access count (second iteration)'); 82 assert.sameValue( 83 delegationComplete, false, 'delegation ongoing (second iteration)' 84 ); 85 86 spyValue.done = true; 87 iter.return(); 88 assert.sameValue(callCount, 1, 'access count (final iteration)'); 89 assert.sameValue(delegationComplete, true, 'delegation complete'); 90 assert.sameValue(normalCompletion, false, 'completion was abrupt'); 91 assert.sameValue(errorCompletion, false, 'completion was not of type "throw"'); 92 93 reportCompare(0, 0);