OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "src/v8.h" | 5 #include "src/v8.h" |
6 | 6 |
7 #include "src/arguments.h" | 7 #include "src/arguments.h" |
8 #include "src/conversions.h" | 8 #include "src/conversions.h" |
9 #include "src/elements.h" | 9 #include "src/elements.h" |
10 #include "src/objects.h" | 10 #include "src/objects.h" |
(...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
140 | 140 |
141 | 141 |
142 MUST_USE_RESULT | 142 MUST_USE_RESULT |
143 static MaybeHandle<Object> ThrowArrayLengthRangeError(Isolate* isolate) { | 143 static MaybeHandle<Object> ThrowArrayLengthRangeError(Isolate* isolate) { |
144 return isolate->Throw<Object>( | 144 return isolate->Throw<Object>( |
145 isolate->factory()->NewRangeError("invalid_array_length", | 145 isolate->factory()->NewRangeError("invalid_array_length", |
146 HandleVector<Object>(NULL, 0))); | 146 HandleVector<Object>(NULL, 0))); |
147 } | 147 } |
148 | 148 |
149 | 149 |
150 static void CopyObjectToObjectElements(Handle<FixedArrayBase> from_base, | 150 static void CopyObjectToObjectElements(FixedArrayBase* from_base, |
151 ElementsKind from_kind, | 151 ElementsKind from_kind, |
152 uint32_t from_start, | 152 uint32_t from_start, |
153 Handle<FixedArrayBase> to_base, | 153 FixedArrayBase* to_base, |
154 ElementsKind to_kind, | 154 ElementsKind to_kind, uint32_t to_start, |
155 uint32_t to_start, | |
156 int raw_copy_size) { | 155 int raw_copy_size) { |
157 ASSERT(to_base->map() != | 156 ASSERT(to_base->map() != |
158 from_base->GetIsolate()->heap()->fixed_cow_array_map()); | 157 from_base->GetIsolate()->heap()->fixed_cow_array_map()); |
159 DisallowHeapAllocation no_allocation; | 158 DisallowHeapAllocation no_allocation; |
160 int copy_size = raw_copy_size; | 159 int copy_size = raw_copy_size; |
161 if (raw_copy_size < 0) { | 160 if (raw_copy_size < 0) { |
162 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || | 161 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || |
163 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); | 162 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); |
164 copy_size = Min(from_base->length() - from_start, | 163 copy_size = Min(from_base->length() - from_start, |
165 to_base->length() - to_start); | 164 to_base->length() - to_start); |
166 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { | 165 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { |
167 int start = to_start + copy_size; | 166 int start = to_start + copy_size; |
168 int length = to_base->length() - start; | 167 int length = to_base->length() - start; |
169 if (length > 0) { | 168 if (length > 0) { |
170 Heap* heap = from_base->GetHeap(); | 169 Heap* heap = from_base->GetHeap(); |
171 MemsetPointer(Handle<FixedArray>::cast(to_base)->data_start() + start, | 170 MemsetPointer(FixedArray::cast(to_base)->data_start() + start, |
172 heap->the_hole_value(), length); | 171 heap->the_hole_value(), length); |
173 } | 172 } |
174 } | 173 } |
175 } | 174 } |
176 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && | 175 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && |
177 (copy_size + static_cast<int>(from_start)) <= from_base->length()); | 176 (copy_size + static_cast<int>(from_start)) <= from_base->length()); |
178 if (copy_size == 0) return; | 177 if (copy_size == 0) return; |
179 Handle<FixedArray> from = Handle<FixedArray>::cast(from_base); | 178 FixedArray* from = FixedArray::cast(from_base); |
180 Handle<FixedArray> to = Handle<FixedArray>::cast(to_base); | 179 FixedArray* to = FixedArray::cast(to_base); |
181 ASSERT(IsFastSmiOrObjectElementsKind(from_kind)); | 180 ASSERT(IsFastSmiOrObjectElementsKind(from_kind)); |
182 ASSERT(IsFastSmiOrObjectElementsKind(to_kind)); | 181 ASSERT(IsFastSmiOrObjectElementsKind(to_kind)); |
183 Address to_address = to->address() + FixedArray::kHeaderSize; | 182 Address to_address = to->address() + FixedArray::kHeaderSize; |
184 Address from_address = from->address() + FixedArray::kHeaderSize; | 183 Address from_address = from->address() + FixedArray::kHeaderSize; |
185 CopyWords(reinterpret_cast<Object**>(to_address) + to_start, | 184 CopyWords(reinterpret_cast<Object**>(to_address) + to_start, |
186 reinterpret_cast<Object**>(from_address) + from_start, | 185 reinterpret_cast<Object**>(from_address) + from_start, |
187 static_cast<size_t>(copy_size)); | 186 static_cast<size_t>(copy_size)); |
188 if (IsFastObjectElementsKind(from_kind) && | 187 if (IsFastObjectElementsKind(from_kind) && |
189 IsFastObjectElementsKind(to_kind)) { | 188 IsFastObjectElementsKind(to_kind)) { |
190 Heap* heap = from->GetHeap(); | 189 Heap* heap = from->GetHeap(); |
191 if (!heap->InNewSpace(*to)) { | 190 if (!heap->InNewSpace(to)) { |
192 heap->RecordWrites(to->address(), | 191 heap->RecordWrites(to->address(), |
193 to->OffsetOfElementAt(to_start), | 192 to->OffsetOfElementAt(to_start), |
194 copy_size); | 193 copy_size); |
195 } | 194 } |
196 heap->incremental_marking()->RecordWrites(*to); | 195 heap->incremental_marking()->RecordWrites(to); |
197 } | 196 } |
198 } | 197 } |
199 | 198 |
200 | 199 |
201 static void CopyDictionaryToObjectElements(Handle<FixedArrayBase> from_base, | 200 static void CopyDictionaryToObjectElements( |
202 uint32_t from_start, | 201 FixedArrayBase* from_base, uint32_t from_start, FixedArrayBase* to_base, |
203 Handle<FixedArrayBase> to_base, | 202 ElementsKind to_kind, uint32_t to_start, int raw_copy_size) { |
204 ElementsKind to_kind, | |
205 uint32_t to_start, | |
206 int raw_copy_size) { | |
207 Handle<SeededNumberDictionary> from = | |
208 Handle<SeededNumberDictionary>::cast(from_base); | |
209 DisallowHeapAllocation no_allocation; | 203 DisallowHeapAllocation no_allocation; |
| 204 SeededNumberDictionary* from = SeededNumberDictionary::cast(from_base); |
210 int copy_size = raw_copy_size; | 205 int copy_size = raw_copy_size; |
211 Heap* heap = from->GetHeap(); | 206 Heap* heap = from->GetHeap(); |
212 if (raw_copy_size < 0) { | 207 if (raw_copy_size < 0) { |
213 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || | 208 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || |
214 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); | 209 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); |
215 copy_size = from->max_number_key() + 1 - from_start; | 210 copy_size = from->max_number_key() + 1 - from_start; |
216 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { | 211 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { |
217 int start = to_start + copy_size; | 212 int start = to_start + copy_size; |
218 int length = to_base->length() - start; | 213 int length = to_base->length() - start; |
219 if (length > 0) { | 214 if (length > 0) { |
220 Heap* heap = from->GetHeap(); | 215 Heap* heap = from->GetHeap(); |
221 MemsetPointer(Handle<FixedArray>::cast(to_base)->data_start() + start, | 216 MemsetPointer(FixedArray::cast(to_base)->data_start() + start, |
222 heap->the_hole_value(), length); | 217 heap->the_hole_value(), length); |
223 } | 218 } |
224 } | 219 } |
225 } | 220 } |
226 ASSERT(*to_base != *from_base); | 221 ASSERT(to_base != from_base); |
227 ASSERT(IsFastSmiOrObjectElementsKind(to_kind)); | 222 ASSERT(IsFastSmiOrObjectElementsKind(to_kind)); |
228 if (copy_size == 0) return; | 223 if (copy_size == 0) return; |
229 Handle<FixedArray> to = Handle<FixedArray>::cast(to_base); | 224 FixedArray* to = FixedArray::cast(to_base); |
230 uint32_t to_length = to->length(); | 225 uint32_t to_length = to->length(); |
231 if (to_start + copy_size > to_length) { | 226 if (to_start + copy_size > to_length) { |
232 copy_size = to_length - to_start; | 227 copy_size = to_length - to_start; |
233 } | 228 } |
234 for (int i = 0; i < copy_size; i++) { | 229 for (int i = 0; i < copy_size; i++) { |
235 int entry = from->FindEntry(i + from_start); | 230 int entry = from->FindEntry(i + from_start); |
236 if (entry != SeededNumberDictionary::kNotFound) { | 231 if (entry != SeededNumberDictionary::kNotFound) { |
237 Object* value = from->ValueAt(entry); | 232 Object* value = from->ValueAt(entry); |
238 ASSERT(!value->IsTheHole()); | 233 ASSERT(!value->IsTheHole()); |
239 to->set(i + to_start, value, SKIP_WRITE_BARRIER); | 234 to->set(i + to_start, value, SKIP_WRITE_BARRIER); |
240 } else { | 235 } else { |
241 to->set_the_hole(i + to_start); | 236 to->set_the_hole(i + to_start); |
242 } | 237 } |
243 } | 238 } |
244 if (IsFastObjectElementsKind(to_kind)) { | 239 if (IsFastObjectElementsKind(to_kind)) { |
245 if (!heap->InNewSpace(*to)) { | 240 if (!heap->InNewSpace(to)) { |
246 heap->RecordWrites(to->address(), | 241 heap->RecordWrites(to->address(), |
247 to->OffsetOfElementAt(to_start), | 242 to->OffsetOfElementAt(to_start), |
248 copy_size); | 243 copy_size); |
249 } | 244 } |
250 heap->incremental_marking()->RecordWrites(*to); | 245 heap->incremental_marking()->RecordWrites(to); |
251 } | 246 } |
252 } | 247 } |
253 | 248 |
254 | 249 |
255 static void CopyDoubleToObjectElements(Handle<FixedArrayBase> from_base, | 250 static void CopyDoubleToObjectElements(Handle<FixedArrayBase> from_base, |
256 uint32_t from_start, | 251 uint32_t from_start, |
257 Handle<FixedArrayBase> to_base, | 252 Handle<FixedArrayBase> to_base, |
258 ElementsKind to_kind, | 253 ElementsKind to_kind, |
259 uint32_t to_start, | 254 uint32_t to_start, |
260 int raw_copy_size) { | 255 int raw_copy_size) { |
261 ASSERT(IsFastSmiOrObjectElementsKind(to_kind)); | 256 ASSERT(IsFastSmiOrObjectElementsKind(to_kind)); |
262 int copy_size = raw_copy_size; | 257 int copy_size = raw_copy_size; |
263 if (raw_copy_size < 0) { | 258 if (raw_copy_size < 0) { |
264 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || | 259 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || |
265 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); | 260 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); |
266 copy_size = Min(from_base->length() - from_start, | 261 copy_size = Min(from_base->length() - from_start, |
267 to_base->length() - to_start); | 262 to_base->length() - to_start); |
268 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { | 263 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { |
269 // Also initialize the area that will be copied over since HeapNumber | 264 // Also initialize the area that will be copied over since HeapNumber |
270 // allocation below can cause an incremental marking step, requiring all | 265 // allocation below can cause an incremental marking step, requiring all |
271 // existing heap objects to be propertly initialized. | 266 // existing heap objects to be propertly initialized. |
272 int start = to_start; | 267 int start = to_start; |
273 int length = to_base->length() - start; | 268 int length = to_base->length() - start; |
274 if (length > 0) { | 269 if (length > 0) { |
275 Heap* heap = from_base->GetHeap(); | 270 Heap* heap = from_base->GetHeap(); |
276 MemsetPointer(Handle<FixedArray>::cast(to_base)->data_start() + start, | 271 MemsetPointer(FixedArray::cast(*to_base)->data_start() + start, |
277 heap->the_hole_value(), length); | 272 heap->the_hole_value(), length); |
278 } | 273 } |
279 } | 274 } |
280 } | 275 } |
281 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && | 276 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && |
282 (copy_size + static_cast<int>(from_start)) <= from_base->length()); | 277 (copy_size + static_cast<int>(from_start)) <= from_base->length()); |
283 if (copy_size == 0) return; | 278 if (copy_size == 0) return; |
284 Isolate* isolate = from_base->GetIsolate(); | 279 Isolate* isolate = from_base->GetIsolate(); |
285 Handle<FixedDoubleArray> from = Handle<FixedDoubleArray>::cast(from_base); | 280 Handle<FixedDoubleArray> from = Handle<FixedDoubleArray>::cast(from_base); |
286 Handle<FixedArray> to = Handle<FixedArray>::cast(to_base); | 281 Handle<FixedArray> to = Handle<FixedArray>::cast(to_base); |
287 for (int i = 0; i < copy_size; ++i) { | 282 for (int i = 0; i < copy_size; ++i) { |
288 HandleScope scope(isolate); | 283 HandleScope scope(isolate); |
289 if (IsFastSmiElementsKind(to_kind)) { | 284 if (IsFastSmiElementsKind(to_kind)) { |
290 UNIMPLEMENTED(); | 285 UNIMPLEMENTED(); |
291 } else { | 286 } else { |
292 ASSERT(IsFastObjectElementsKind(to_kind)); | 287 ASSERT(IsFastObjectElementsKind(to_kind)); |
293 Handle<Object> value = FixedDoubleArray::get(from, i + from_start); | 288 Handle<Object> value = FixedDoubleArray::get(from, i + from_start); |
294 to->set(i + to_start, *value, UPDATE_WRITE_BARRIER); | 289 to->set(i + to_start, *value, UPDATE_WRITE_BARRIER); |
295 } | 290 } |
296 } | 291 } |
297 } | 292 } |
298 | 293 |
299 | 294 |
300 static void CopyDoubleToDoubleElements(Handle<FixedArrayBase> from_base, | 295 static void CopyDoubleToDoubleElements(FixedArrayBase* from_base, |
301 uint32_t from_start, | 296 uint32_t from_start, |
302 Handle<FixedArrayBase> to_base, | 297 FixedArrayBase* to_base, |
303 uint32_t to_start, | 298 uint32_t to_start, int raw_copy_size) { |
304 int raw_copy_size) { | |
305 DisallowHeapAllocation no_allocation; | 299 DisallowHeapAllocation no_allocation; |
306 int copy_size = raw_copy_size; | 300 int copy_size = raw_copy_size; |
307 if (raw_copy_size < 0) { | 301 if (raw_copy_size < 0) { |
308 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || | 302 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || |
309 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); | 303 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); |
310 copy_size = Min(from_base->length() - from_start, | 304 copy_size = Min(from_base->length() - from_start, |
311 to_base->length() - to_start); | 305 to_base->length() - to_start); |
312 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { | 306 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { |
313 for (int i = to_start + copy_size; i < to_base->length(); ++i) { | 307 for (int i = to_start + copy_size; i < to_base->length(); ++i) { |
314 Handle<FixedDoubleArray>::cast(to_base)->set_the_hole(i); | 308 FixedDoubleArray::cast(to_base)->set_the_hole(i); |
315 } | 309 } |
316 } | 310 } |
317 } | 311 } |
318 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && | 312 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && |
319 (copy_size + static_cast<int>(from_start)) <= from_base->length()); | 313 (copy_size + static_cast<int>(from_start)) <= from_base->length()); |
320 if (copy_size == 0) return; | 314 if (copy_size == 0) return; |
321 Handle<FixedDoubleArray> from = Handle<FixedDoubleArray>::cast(from_base); | 315 FixedDoubleArray* from = FixedDoubleArray::cast(from_base); |
322 Handle<FixedDoubleArray> to = Handle<FixedDoubleArray>::cast(to_base); | 316 FixedDoubleArray* to = FixedDoubleArray::cast(to_base); |
323 Address to_address = to->address() + FixedDoubleArray::kHeaderSize; | 317 Address to_address = to->address() + FixedDoubleArray::kHeaderSize; |
324 Address from_address = from->address() + FixedDoubleArray::kHeaderSize; | 318 Address from_address = from->address() + FixedDoubleArray::kHeaderSize; |
325 to_address += kDoubleSize * to_start; | 319 to_address += kDoubleSize * to_start; |
326 from_address += kDoubleSize * from_start; | 320 from_address += kDoubleSize * from_start; |
327 int words_per_double = (kDoubleSize / kPointerSize); | 321 int words_per_double = (kDoubleSize / kPointerSize); |
328 CopyWords(reinterpret_cast<Object**>(to_address), | 322 CopyWords(reinterpret_cast<Object**>(to_address), |
329 reinterpret_cast<Object**>(from_address), | 323 reinterpret_cast<Object**>(from_address), |
330 static_cast<size_t>(words_per_double * copy_size)); | 324 static_cast<size_t>(words_per_double * copy_size)); |
331 } | 325 } |
332 | 326 |
333 | 327 |
334 static void CopySmiToDoubleElements(Handle<FixedArrayBase> from_base, | 328 static void CopySmiToDoubleElements(FixedArrayBase* from_base, |
335 uint32_t from_start, | 329 uint32_t from_start, |
336 Handle<FixedArrayBase> to_base, | 330 FixedArrayBase* to_base, uint32_t to_start, |
337 uint32_t to_start, | |
338 int raw_copy_size) { | 331 int raw_copy_size) { |
339 DisallowHeapAllocation no_allocation; | 332 DisallowHeapAllocation no_allocation; |
340 int copy_size = raw_copy_size; | 333 int copy_size = raw_copy_size; |
341 if (raw_copy_size < 0) { | 334 if (raw_copy_size < 0) { |
342 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || | 335 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || |
343 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); | 336 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); |
344 copy_size = from_base->length() - from_start; | 337 copy_size = from_base->length() - from_start; |
345 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { | 338 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { |
346 for (int i = to_start + copy_size; i < to_base->length(); ++i) { | 339 for (int i = to_start + copy_size; i < to_base->length(); ++i) { |
347 Handle<FixedDoubleArray>::cast(to_base)->set_the_hole(i); | 340 FixedDoubleArray::cast(to_base)->set_the_hole(i); |
348 } | 341 } |
349 } | 342 } |
350 } | 343 } |
351 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && | 344 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && |
352 (copy_size + static_cast<int>(from_start)) <= from_base->length()); | 345 (copy_size + static_cast<int>(from_start)) <= from_base->length()); |
353 if (copy_size == 0) return; | 346 if (copy_size == 0) return; |
354 Handle<FixedArray> from = Handle<FixedArray>::cast(from_base); | 347 FixedArray* from = FixedArray::cast(from_base); |
355 Handle<FixedDoubleArray> to = Handle<FixedDoubleArray>::cast(to_base); | 348 FixedDoubleArray* to = FixedDoubleArray::cast(to_base); |
356 Handle<Object> the_hole = from->GetIsolate()->factory()->the_hole_value(); | 349 Object* the_hole = from->GetHeap()->the_hole_value(); |
357 for (uint32_t from_end = from_start + static_cast<uint32_t>(copy_size); | 350 for (uint32_t from_end = from_start + static_cast<uint32_t>(copy_size); |
358 from_start < from_end; from_start++, to_start++) { | 351 from_start < from_end; from_start++, to_start++) { |
359 Object* hole_or_smi = from->get(from_start); | 352 Object* hole_or_smi = from->get(from_start); |
360 if (hole_or_smi == *the_hole) { | 353 if (hole_or_smi == the_hole) { |
361 to->set_the_hole(to_start); | 354 to->set_the_hole(to_start); |
362 } else { | 355 } else { |
363 to->set(to_start, Smi::cast(hole_or_smi)->value()); | 356 to->set(to_start, Smi::cast(hole_or_smi)->value()); |
364 } | 357 } |
365 } | 358 } |
366 } | 359 } |
367 | 360 |
368 | 361 |
369 static void CopyPackedSmiToDoubleElements(Handle<FixedArrayBase> from_base, | 362 static void CopyPackedSmiToDoubleElements(FixedArrayBase* from_base, |
370 uint32_t from_start, | 363 uint32_t from_start, |
371 Handle<FixedArrayBase> to_base, | 364 FixedArrayBase* to_base, |
372 uint32_t to_start, | 365 uint32_t to_start, int packed_size, |
373 int packed_size, | |
374 int raw_copy_size) { | 366 int raw_copy_size) { |
375 DisallowHeapAllocation no_allocation; | 367 DisallowHeapAllocation no_allocation; |
376 int copy_size = raw_copy_size; | 368 int copy_size = raw_copy_size; |
377 uint32_t to_end; | 369 uint32_t to_end; |
378 if (raw_copy_size < 0) { | 370 if (raw_copy_size < 0) { |
379 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || | 371 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || |
380 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); | 372 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); |
381 copy_size = packed_size - from_start; | 373 copy_size = packed_size - from_start; |
382 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { | 374 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { |
383 to_end = to_base->length(); | 375 to_end = to_base->length(); |
384 for (uint32_t i = to_start + copy_size; i < to_end; ++i) { | 376 for (uint32_t i = to_start + copy_size; i < to_end; ++i) { |
385 Handle<FixedDoubleArray>::cast(to_base)->set_the_hole(i); | 377 FixedDoubleArray::cast(to_base)->set_the_hole(i); |
386 } | 378 } |
387 } else { | 379 } else { |
388 to_end = to_start + static_cast<uint32_t>(copy_size); | 380 to_end = to_start + static_cast<uint32_t>(copy_size); |
389 } | 381 } |
390 } else { | 382 } else { |
391 to_end = to_start + static_cast<uint32_t>(copy_size); | 383 to_end = to_start + static_cast<uint32_t>(copy_size); |
392 } | 384 } |
393 ASSERT(static_cast<int>(to_end) <= to_base->length()); | 385 ASSERT(static_cast<int>(to_end) <= to_base->length()); |
394 ASSERT(packed_size >= 0 && packed_size <= copy_size); | 386 ASSERT(packed_size >= 0 && packed_size <= copy_size); |
395 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && | 387 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && |
396 (copy_size + static_cast<int>(from_start)) <= from_base->length()); | 388 (copy_size + static_cast<int>(from_start)) <= from_base->length()); |
397 if (copy_size == 0) return; | 389 if (copy_size == 0) return; |
398 Handle<FixedArray> from = Handle<FixedArray>::cast(from_base); | 390 FixedArray* from = FixedArray::cast(from_base); |
399 Handle<FixedDoubleArray> to = Handle<FixedDoubleArray>::cast(to_base); | 391 FixedDoubleArray* to = FixedDoubleArray::cast(to_base); |
400 for (uint32_t from_end = from_start + static_cast<uint32_t>(packed_size); | 392 for (uint32_t from_end = from_start + static_cast<uint32_t>(packed_size); |
401 from_start < from_end; from_start++, to_start++) { | 393 from_start < from_end; from_start++, to_start++) { |
402 Object* smi = from->get(from_start); | 394 Object* smi = from->get(from_start); |
403 ASSERT(!smi->IsTheHole()); | 395 ASSERT(!smi->IsTheHole()); |
404 to->set(to_start, Smi::cast(smi)->value()); | 396 to->set(to_start, Smi::cast(smi)->value()); |
405 } | 397 } |
406 } | 398 } |
407 | 399 |
408 | 400 |
409 static void CopyObjectToDoubleElements(Handle<FixedArrayBase> from_base, | 401 static void CopyObjectToDoubleElements(FixedArrayBase* from_base, |
410 uint32_t from_start, | 402 uint32_t from_start, |
411 Handle<FixedArrayBase> to_base, | 403 FixedArrayBase* to_base, |
412 uint32_t to_start, | 404 uint32_t to_start, int raw_copy_size) { |
413 int raw_copy_size) { | |
414 DisallowHeapAllocation no_allocation; | 405 DisallowHeapAllocation no_allocation; |
415 int copy_size = raw_copy_size; | 406 int copy_size = raw_copy_size; |
416 if (raw_copy_size < 0) { | 407 if (raw_copy_size < 0) { |
417 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || | 408 ASSERT(raw_copy_size == ElementsAccessor::kCopyToEnd || |
418 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); | 409 raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); |
419 copy_size = from_base->length() - from_start; | 410 copy_size = from_base->length() - from_start; |
420 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { | 411 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { |
421 for (int i = to_start + copy_size; i < to_base->length(); ++i) { | 412 for (int i = to_start + copy_size; i < to_base->length(); ++i) { |
422 Handle<FixedDoubleArray>::cast(to_base)->set_the_hole(i); | 413 FixedDoubleArray::cast(to_base)->set_the_hole(i); |
423 } | 414 } |
424 } | 415 } |
425 } | 416 } |
426 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && | 417 ASSERT((copy_size + static_cast<int>(to_start)) <= to_base->length() && |
427 (copy_size + static_cast<int>(from_start)) <= from_base->length()); | 418 (copy_size + static_cast<int>(from_start)) <= from_base->length()); |
428 if (copy_size == 0) return; | 419 if (copy_size == 0) return; |
429 Handle<FixedArray> from = Handle<FixedArray>::cast(from_base); | 420 FixedArray* from = FixedArray::cast(from_base); |
430 Handle<FixedDoubleArray> to = Handle<FixedDoubleArray>::cast(to_base); | 421 FixedDoubleArray* to = FixedDoubleArray::cast(to_base); |
431 Handle<Object> the_hole = from->GetIsolate()->factory()->the_hole_value(); | 422 Object* the_hole = from->GetHeap()->the_hole_value(); |
432 for (uint32_t from_end = from_start + copy_size; | 423 for (uint32_t from_end = from_start + copy_size; |
433 from_start < from_end; from_start++, to_start++) { | 424 from_start < from_end; from_start++, to_start++) { |
434 Object* hole_or_object = from->get(from_start); | 425 Object* hole_or_object = from->get(from_start); |
435 if (hole_or_object == *the_hole) { | 426 if (hole_or_object == the_hole) { |
436 to->set_the_hole(to_start); | 427 to->set_the_hole(to_start); |
437 } else { | 428 } else { |
438 to->set(to_start, hole_or_object->Number()); | 429 to->set(to_start, hole_or_object->Number()); |
439 } | 430 } |
440 } | 431 } |
441 } | 432 } |
442 | 433 |
443 | 434 |
444 static void CopyDictionaryToDoubleElements(Handle<FixedArrayBase> from_base, | 435 static void CopyDictionaryToDoubleElements(FixedArrayBase* from_base, |
445 uint32_t from_start, | 436 uint32_t from_start, |
446 Handle<FixedArrayBase> to_base, | 437 FixedArrayBase* to_base, |
447 uint32_t to_start, | 438 uint32_t to_start, |
448 int raw_copy_size) { | 439 int raw_copy_size) { |
449 Handle<SeededNumberDictionary> from = | |
450 Handle<SeededNumberDictionary>::cast(from_base); | |
451 DisallowHeapAllocation no_allocation; | 440 DisallowHeapAllocation no_allocation; |
| 441 SeededNumberDictionary* from = SeededNumberDictionary::cast(from_base); |
452 int copy_size = raw_copy_size; | 442 int copy_size = raw_copy_size; |
453 if (copy_size < 0) { | 443 if (copy_size < 0) { |
454 ASSERT(copy_size == ElementsAccessor::kCopyToEnd || | 444 ASSERT(copy_size == ElementsAccessor::kCopyToEnd || |
455 copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); | 445 copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole); |
456 copy_size = from->max_number_key() + 1 - from_start; | 446 copy_size = from->max_number_key() + 1 - from_start; |
457 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { | 447 if (raw_copy_size == ElementsAccessor::kCopyToEndAndInitializeToHole) { |
458 for (int i = to_start + copy_size; i < to_base->length(); ++i) { | 448 for (int i = to_start + copy_size; i < to_base->length(); ++i) { |
459 Handle<FixedDoubleArray>::cast(to_base)->set_the_hole(i); | 449 FixedDoubleArray::cast(to_base)->set_the_hole(i); |
460 } | 450 } |
461 } | 451 } |
462 } | 452 } |
463 if (copy_size == 0) return; | 453 if (copy_size == 0) return; |
464 Handle<FixedDoubleArray> to = Handle<FixedDoubleArray>::cast(to_base); | 454 FixedDoubleArray* to = FixedDoubleArray::cast(to_base); |
465 uint32_t to_length = to->length(); | 455 uint32_t to_length = to->length(); |
466 if (to_start + copy_size > to_length) { | 456 if (to_start + copy_size > to_length) { |
467 copy_size = to_length - to_start; | 457 copy_size = to_length - to_start; |
468 } | 458 } |
469 for (int i = 0; i < copy_size; i++) { | 459 for (int i = 0; i < copy_size; i++) { |
470 int entry = from->FindEntry(i + from_start); | 460 int entry = from->FindEntry(i + from_start); |
471 if (entry != SeededNumberDictionary::kNotFound) { | 461 if (entry != SeededNumberDictionary::kNotFound) { |
472 to->set(i + to_start, from->ValueAt(entry)->Number()); | 462 to->set(i + to_start, from->ValueAt(entry)->Number()); |
473 } else { | 463 } else { |
474 to->set_the_hole(i + to_start); | 464 to->set_the_hole(i + to_start); |
(...skipping 634 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1109 ElementsKind from_kind, | 1099 ElementsKind from_kind, |
1110 uint32_t to_start, | 1100 uint32_t to_start, |
1111 int packed_size, | 1101 int packed_size, |
1112 int copy_size) { | 1102 int copy_size) { |
1113 ElementsKind to_kind = KindTraits::Kind; | 1103 ElementsKind to_kind = KindTraits::Kind; |
1114 switch (from_kind) { | 1104 switch (from_kind) { |
1115 case FAST_SMI_ELEMENTS: | 1105 case FAST_SMI_ELEMENTS: |
1116 case FAST_HOLEY_SMI_ELEMENTS: | 1106 case FAST_HOLEY_SMI_ELEMENTS: |
1117 case FAST_ELEMENTS: | 1107 case FAST_ELEMENTS: |
1118 case FAST_HOLEY_ELEMENTS: | 1108 case FAST_HOLEY_ELEMENTS: |
1119 CopyObjectToObjectElements( | 1109 CopyObjectToObjectElements(*from, from_kind, from_start, *to, to_kind, |
1120 from, from_kind, from_start, to, to_kind, to_start, copy_size); | 1110 to_start, copy_size); |
1121 break; | 1111 break; |
1122 case FAST_DOUBLE_ELEMENTS: | 1112 case FAST_DOUBLE_ELEMENTS: |
1123 case FAST_HOLEY_DOUBLE_ELEMENTS: | 1113 case FAST_HOLEY_DOUBLE_ELEMENTS: |
1124 CopyDoubleToObjectElements( | 1114 CopyDoubleToObjectElements( |
1125 from, from_start, to, to_kind, to_start, copy_size); | 1115 from, from_start, to, to_kind, to_start, copy_size); |
1126 break; | 1116 break; |
1127 case DICTIONARY_ELEMENTS: | 1117 case DICTIONARY_ELEMENTS: |
1128 CopyDictionaryToObjectElements( | 1118 CopyDictionaryToObjectElements(*from, from_start, *to, to_kind, |
1129 from, from_start, to, to_kind, to_start, copy_size); | 1119 to_start, copy_size); |
1130 break; | 1120 break; |
1131 case SLOPPY_ARGUMENTS_ELEMENTS: { | 1121 case SLOPPY_ARGUMENTS_ELEMENTS: { |
1132 // TODO(verwaest): This is a temporary hack to support extending | 1122 // TODO(verwaest): This is a temporary hack to support extending |
1133 // SLOPPY_ARGUMENTS_ELEMENTS in SetFastElementsCapacityAndLength. | 1123 // SLOPPY_ARGUMENTS_ELEMENTS in SetFastElementsCapacityAndLength. |
1134 // This case should be UNREACHABLE(). | 1124 // This case should be UNREACHABLE(). |
1135 Handle<FixedArray> parameter_map = Handle<FixedArray>::cast(from); | 1125 Handle<FixedArray> parameter_map = Handle<FixedArray>::cast(from); |
1136 Handle<FixedArrayBase> arguments( | 1126 Handle<FixedArrayBase> arguments( |
1137 FixedArrayBase::cast(parameter_map->get(1))); | 1127 FixedArrayBase::cast(parameter_map->get(1))); |
1138 ElementsKind from_kind = ElementsKindForArray(arguments); | 1128 ElementsKind from_kind = ElementsKindForArray(arguments); |
1139 CopyElementsImpl(arguments, from_start, to, from_kind, | 1129 CopyElementsImpl(arguments, from_start, to, from_kind, |
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1233 protected: | 1223 protected: |
1234 static void CopyElementsImpl(Handle<FixedArrayBase> from, | 1224 static void CopyElementsImpl(Handle<FixedArrayBase> from, |
1235 uint32_t from_start, | 1225 uint32_t from_start, |
1236 Handle<FixedArrayBase> to, | 1226 Handle<FixedArrayBase> to, |
1237 ElementsKind from_kind, | 1227 ElementsKind from_kind, |
1238 uint32_t to_start, | 1228 uint32_t to_start, |
1239 int packed_size, | 1229 int packed_size, |
1240 int copy_size) { | 1230 int copy_size) { |
1241 switch (from_kind) { | 1231 switch (from_kind) { |
1242 case FAST_SMI_ELEMENTS: | 1232 case FAST_SMI_ELEMENTS: |
1243 CopyPackedSmiToDoubleElements( | 1233 CopyPackedSmiToDoubleElements(*from, from_start, *to, to_start, |
1244 from, from_start, to, to_start, packed_size, copy_size); | 1234 packed_size, copy_size); |
1245 break; | 1235 break; |
1246 case FAST_HOLEY_SMI_ELEMENTS: | 1236 case FAST_HOLEY_SMI_ELEMENTS: |
1247 CopySmiToDoubleElements(from, from_start, to, to_start, copy_size); | 1237 CopySmiToDoubleElements(*from, from_start, *to, to_start, copy_size); |
1248 break; | 1238 break; |
1249 case FAST_DOUBLE_ELEMENTS: | 1239 case FAST_DOUBLE_ELEMENTS: |
1250 case FAST_HOLEY_DOUBLE_ELEMENTS: | 1240 case FAST_HOLEY_DOUBLE_ELEMENTS: |
1251 CopyDoubleToDoubleElements(from, from_start, to, to_start, copy_size); | 1241 CopyDoubleToDoubleElements(*from, from_start, *to, to_start, copy_size); |
1252 break; | 1242 break; |
1253 case FAST_ELEMENTS: | 1243 case FAST_ELEMENTS: |
1254 case FAST_HOLEY_ELEMENTS: | 1244 case FAST_HOLEY_ELEMENTS: |
1255 CopyObjectToDoubleElements(from, from_start, to, to_start, copy_size); | 1245 CopyObjectToDoubleElements(*from, from_start, *to, to_start, copy_size); |
1256 break; | 1246 break; |
1257 case DICTIONARY_ELEMENTS: | 1247 case DICTIONARY_ELEMENTS: |
1258 CopyDictionaryToDoubleElements( | 1248 CopyDictionaryToDoubleElements(*from, from_start, *to, to_start, |
1259 from, from_start, to, to_start, copy_size); | 1249 copy_size); |
1260 break; | 1250 break; |
1261 case SLOPPY_ARGUMENTS_ELEMENTS: | 1251 case SLOPPY_ARGUMENTS_ELEMENTS: |
1262 UNREACHABLE(); | 1252 UNREACHABLE(); |
1263 | 1253 |
1264 #define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \ | 1254 #define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \ |
1265 case EXTERNAL_##TYPE##_ELEMENTS: \ | 1255 case EXTERNAL_##TYPE##_ELEMENTS: \ |
1266 case TYPE##_ELEMENTS: \ | 1256 case TYPE##_ELEMENTS: \ |
1267 UNREACHABLE(); | 1257 UNREACHABLE(); |
1268 TYPED_ARRAYS(TYPED_ARRAY_CASE) | 1258 TYPED_ARRAYS(TYPED_ARRAY_CASE) |
1269 #undef TYPED_ARRAY_CASE | 1259 #undef TYPED_ARRAY_CASE |
(...skipping 720 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1990 UNREACHABLE(); | 1980 UNREACHABLE(); |
1991 break; | 1981 break; |
1992 } | 1982 } |
1993 | 1983 |
1994 array->set_elements(*elms); | 1984 array->set_elements(*elms); |
1995 array->set_length(Smi::FromInt(number_of_elements)); | 1985 array->set_length(Smi::FromInt(number_of_elements)); |
1996 return array; | 1986 return array; |
1997 } | 1987 } |
1998 | 1988 |
1999 } } // namespace v8::internal | 1989 } } // namespace v8::internal |
OLD | NEW |