1// Copyright 2014 the V8 project authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5// Flags: --allow-natives-syntax 6 7 8// Note in general that "arguments.foo" and "var o = arguments; o.foo" 9// are treated differently by full-codegen, and so both cases need to be 10// tested. 11 12function TestDirectArgumentsIteratorProperty() { 13 assertTrue(arguments.hasOwnProperty(Symbol.iterator)); 14 assertFalse(arguments.propertyIsEnumerable(Symbol.iterator)); 15 var descriptor = Object.getOwnPropertyDescriptor(arguments, Symbol.iterator); 16 assertTrue(descriptor.writable); 17 assertFalse(descriptor.enumerable); 18 assertTrue(descriptor.configurable); 19 assertEquals(descriptor.value, [][Symbol.iterator]); 20 assertEquals(arguments[Symbol.iterator], [][Symbol.iterator]); 21} 22TestDirectArgumentsIteratorProperty(); 23 24 25function TestIndirectArgumentsIteratorProperty() { 26 var o = arguments; 27 assertTrue(o.hasOwnProperty(Symbol.iterator)); 28 assertFalse(o.propertyIsEnumerable(Symbol.iterator)); 29 assertEquals(o[Symbol.iterator], [][Symbol.iterator]); 30} 31TestIndirectArgumentsIteratorProperty(); 32 33 34function assertIteratorResult(value, done, result) { 35 assertEquals({value: value, done: done}, result); 36} 37 38 39function TestDirectValues1(a, b, c) { 40 var iterator = arguments[Symbol.iterator](); 41 assertIteratorResult(a, false, iterator.next()); 42 assertIteratorResult(b, false, iterator.next()); 43 assertIteratorResult(c, false, iterator.next()); 44 assertIteratorResult(undefined, true, iterator.next()); 45} 46TestDirectValues1(1, 2, 3); 47 48 49function TestIndirectValues1(a, b, c) { 50 var args = arguments; 51 var iterator = args[Symbol.iterator](); 52 assertIteratorResult(a, false, iterator.next()); 53 assertIteratorResult(b, false, iterator.next()); 54 assertIteratorResult(c, false, iterator.next()); 55 assertIteratorResult(undefined, true, iterator.next()); 56} 57TestIndirectValues1(1, 2, 3); 58 59 60function TestDirectValues2(a, b, c) { 61 var iterator = arguments[Symbol.iterator](); 62 assertIteratorResult(a, false, iterator.next()); 63 assertIteratorResult(b, false, iterator.next()); 64 assertIteratorResult(c, false, iterator.next()); 65 assertIteratorResult(undefined, true, iterator.next()); 66 67 arguments[3] = 4; 68 arguments.length = 4; 69 assertIteratorResult(undefined, true, iterator.next()); 70} 71TestDirectValues2(1, 2, 3); 72 73 74function TestIndirectValues2(a, b, c) { 75 var args = arguments; 76 var iterator = args[Symbol.iterator](); 77 assertIteratorResult(a, false, iterator.next()); 78 assertIteratorResult(b, false, iterator.next()); 79 assertIteratorResult(c, false, iterator.next()); 80 assertIteratorResult(undefined, true, iterator.next()); 81 82 arguments[3] = 4; 83 arguments.length = 4; 84 assertIteratorResult(undefined, true, iterator.next()); 85} 86TestIndirectValues2(1, 2, 3); 87 88 89function TestDirectValues3(a, b, c) { 90 var iterator = arguments[Symbol.iterator](); 91 assertIteratorResult(a, false, iterator.next()); 92 assertIteratorResult(b, false, iterator.next()); 93 94 arguments.length = 2; 95 assertIteratorResult(undefined, true, iterator.next()); 96} 97TestDirectValues3(1, 2, 3); 98 99 100function TestIndirectValues3(a, b, c) { 101 var args = arguments; 102 var iterator = args[Symbol.iterator](); 103 assertIteratorResult(a, false, iterator.next()); 104 assertIteratorResult(b, false, iterator.next()); 105 106 arguments.length = 2; 107 assertIteratorResult(undefined, true, iterator.next()); 108} 109TestIndirectValues3(1, 2, 3); 110 111 112function TestDirectValues4(a, b, c) { 113 var iterator = arguments[Symbol.iterator](); 114 assertIteratorResult(a, false, iterator.next()); 115 assertIteratorResult(b, false, iterator.next()); 116 assertIteratorResult(c, false, iterator.next()); 117 118 arguments.length = 4; 119 assertIteratorResult(undefined, false, iterator.next()); 120 assertIteratorResult(undefined, true, iterator.next()); 121} 122TestDirectValues4(1, 2, 3); 123 124 125function TestIndirectValues4(a, b, c) { 126 var args = arguments; 127 var iterator = args[Symbol.iterator](); 128 assertIteratorResult(a, false, iterator.next()); 129 assertIteratorResult(b, false, iterator.next()); 130 assertIteratorResult(c, false, iterator.next()); 131 132 arguments.length = 4; 133 assertIteratorResult(undefined, false, iterator.next()); 134 assertIteratorResult(undefined, true, iterator.next()); 135} 136TestIndirectValues4(1, 2, 3); 137 138 139function TestForOf() { 140 var i = 0; 141 for (var value of arguments) { 142 assertEquals(arguments[i++], value); 143 } 144 145 assertEquals(arguments.length, i); 146} 147TestForOf(1, 2, 3, 4, 5); 148 149 150function TestAssignmentToIterator() { 151 var i = 0; 152 arguments[Symbol.iterator] = [].entries; 153 for (var entry of arguments) { 154 assertEquals([i, arguments[i]], entry); 155 i++; 156 } 157 158 assertEquals(arguments.length, i); 159} 160TestAssignmentToIterator(1, 2, 3, 4, 5); 161 162 163// Regression test for crbug.com/521484. 164function TestAssignmentToIterator2() { 165 var i = 0; 166 arguments.__defineGetter__('callee', function(){}); 167 arguments.__defineGetter__('length', function(){ return 1 }); 168 arguments[Symbol.iterator] = [].entries; 169 for (var entry of arguments) { 170 assertEquals([i, arguments[i]], entry); 171 i++; 172 } 173 174 assertEquals(arguments.length, i); 175} 176TestAssignmentToIterator2(1, 2, 3, 4, 5); 177 178function TestArgumentsMutation() { 179 var i = 0; 180 for (var x of arguments) { 181 assertEquals(arguments[i], x); 182 arguments[i+1] *= 2; 183 i++; 184 } 185 186 assertEquals(arguments.length, i); 187} 188TestArgumentsMutation(1, 2, 3, 4, 5); 189 190 191function TestSloppyArgumentsAliasing(a0, a1, a2, a3, a4) { 192 var i = 0; 193 for (var x of arguments) { 194 assertEquals(arguments[i], x); 195 a0 = a1; a1 = a2; a3 = a4; 196 i++; 197 } 198 199 assertEquals(arguments.length, i); 200} 201TestSloppyArgumentsAliasing(1, 2, 3, 4, 5); 202 203 204function TestStrictArgumentsAliasing(a0, a1, a2, a3, a4) { 205 "use strict"; 206 var i = 0; 207 for (var x of arguments) { 208 a0 = a1; a1 = a2; a3 = a4; 209 assertEquals(arguments[i], x); 210 i++; 211 } 212 213 assertEquals(arguments.length, i); 214} 215TestStrictArgumentsAliasing(1, 2, 3, 4, 5); 216 217 218function TestArgumentsAsProto() { 219 "use strict"; 220 221 var o = {__proto__:arguments}; 222 assertSame([][Symbol.iterator], o[Symbol.iterator]); 223 // Make o dict-mode. 224 %OptimizeObjectForAddingMultipleProperties(o, 0); 225 assertFalse(o.hasOwnProperty(Symbol.iterator)); 226 assertSame([][Symbol.iterator], o[Symbol.iterator]); 227 o[Symbol.iterator] = 10; 228 assertTrue(o.hasOwnProperty(Symbol.iterator)); 229 assertEquals(10, o[Symbol.iterator]); 230 assertSame([][Symbol.iterator], arguments[Symbol.iterator]); 231 232 // Frozen o. 233 o = Object.freeze({__proto__:arguments}); 234 assertSame([][Symbol.iterator], o[Symbol.iterator]); 235 assertFalse(o.hasOwnProperty(Symbol.iterator)); 236 assertSame([][Symbol.iterator], o[Symbol.iterator]); 237 assertThrows(function () { o[Symbol.iterator] = 10 }); 238 assertFalse(o.hasOwnProperty(Symbol.iterator)); 239 assertEquals([][Symbol.iterator], o[Symbol.iterator]); 240 assertSame([][Symbol.iterator], arguments[Symbol.iterator]); 241} 242TestArgumentsAsProto(); 243