Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(598)

Side by Side Diff: src/builtins.cc

Issue 3970005: Make Failure inherit from MaybeObject instead of Object. (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: '' Created 10 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/bootstrapper.cc ('k') | src/code-stubs.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2006-2008 the V8 project authors. All rights reserved. 1 // Copyright 2006-2008 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after
114 // 114 //
115 // BUILTIN(name) { 115 // BUILTIN(name) {
116 // ... 116 // ...
117 // } 117 // }
118 // 118 //
119 // In the body of the builtin function the arguments can be accessed 119 // In the body of the builtin function the arguments can be accessed
120 // through the BuiltinArguments object args. 120 // through the BuiltinArguments object args.
121 121
122 #ifdef DEBUG 122 #ifdef DEBUG
123 123
124 #define BUILTIN(name) \ 124 #define BUILTIN(name) \
125 static Object* Builtin_Impl_##name(name##ArgumentsType args); \ 125 MUST_USE_RESULT static MaybeObject* Builtin_Impl_##name( \
126 static Object* Builtin_##name(name##ArgumentsType args) { \ 126 name##ArgumentsType args); \
127 args.Verify(); \ 127 MUST_USE_RESULT static MaybeObject* Builtin_##name( \
128 return Builtin_Impl_##name(args); \ 128 name##ArgumentsType args) { \
129 } \ 129 args.Verify(); \
130 static Object* Builtin_Impl_##name(name##ArgumentsType args) 130 return Builtin_Impl_##name(args); \
131 } \
132 MUST_USE_RESULT static MaybeObject* Builtin_Impl_##name( \
133 name##ArgumentsType args)
131 134
132 #else // For release mode. 135 #else // For release mode.
133 136
134 #define BUILTIN(name) \ 137 #define BUILTIN(name) \
135 static Object* Builtin_##name(name##ArgumentsType args) 138 static MaybeObject* Builtin_##name(name##ArgumentsType args)
136 139
137 #endif 140 #endif
138 141
139 142
140 static inline bool CalledAsConstructor() { 143 static inline bool CalledAsConstructor() {
141 #ifdef DEBUG 144 #ifdef DEBUG
142 // Calculate the result using a full stack frame iterator and check 145 // Calculate the result using a full stack frame iterator and check
143 // that the state of the stack is as we assume it to be in the 146 // that the state of the stack is as we assume it to be in the
144 // code below. 147 // code below.
145 StackFrameIterator it; 148 StackFrameIterator it;
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
182 BUILTIN(ArrayCodeGeneric) { 185 BUILTIN(ArrayCodeGeneric) {
183 Counters::array_function_runtime.Increment(); 186 Counters::array_function_runtime.Increment();
184 187
185 JSArray* array; 188 JSArray* array;
186 if (CalledAsConstructor()) { 189 if (CalledAsConstructor()) {
187 array = JSArray::cast(*args.receiver()); 190 array = JSArray::cast(*args.receiver());
188 } else { 191 } else {
189 // Allocate the JS Array 192 // Allocate the JS Array
190 JSFunction* constructor = 193 JSFunction* constructor =
191 Top::context()->global_context()->array_function(); 194 Top::context()->global_context()->array_function();
192 Object* obj = Heap::AllocateJSObject(constructor); 195 Object* obj;
193 if (obj->IsFailure()) return obj; 196 { MaybeObject* maybe_obj = Heap::AllocateJSObject(constructor);
197 if (!maybe_obj->ToObject(&obj)) return maybe_obj;
198 }
194 array = JSArray::cast(obj); 199 array = JSArray::cast(obj);
195 } 200 }
196 201
197 // 'array' now contains the JSArray we should initialize. 202 // 'array' now contains the JSArray we should initialize.
198 ASSERT(array->HasFastElements()); 203 ASSERT(array->HasFastElements());
199 204
200 // Optimize the case where there is one argument and the argument is a 205 // Optimize the case where there is one argument and the argument is a
201 // small smi. 206 // small smi.
202 if (args.length() == 2) { 207 if (args.length() == 2) {
203 Object* obj = args[1]; 208 Object* obj = args[1];
204 if (obj->IsSmi()) { 209 if (obj->IsSmi()) {
205 int len = Smi::cast(obj)->value(); 210 int len = Smi::cast(obj)->value();
206 if (len >= 0 && len < JSObject::kInitialMaxFastElementArray) { 211 if (len >= 0 && len < JSObject::kInitialMaxFastElementArray) {
207 Object* obj = Heap::AllocateFixedArrayWithHoles(len); 212 Object* obj;
208 if (obj->IsFailure()) return obj; 213 { MaybeObject* maybe_obj = Heap::AllocateFixedArrayWithHoles(len);
214 if (!maybe_obj->ToObject(&obj)) return maybe_obj;
215 }
209 array->SetContent(FixedArray::cast(obj)); 216 array->SetContent(FixedArray::cast(obj));
210 return array; 217 return array;
211 } 218 }
212 } 219 }
213 // Take the argument as the length. 220 // Take the argument as the length.
214 obj = array->Initialize(0); 221 { MaybeObject* maybe_obj = array->Initialize(0);
215 if (obj->IsFailure()) return obj; 222 if (!maybe_obj->ToObject(&obj)) return maybe_obj;
223 }
216 return array->SetElementsLength(args[1]); 224 return array->SetElementsLength(args[1]);
217 } 225 }
218 226
219 // Optimize the case where there are no parameters passed. 227 // Optimize the case where there are no parameters passed.
220 if (args.length() == 1) { 228 if (args.length() == 1) {
221 return array->Initialize(JSArray::kPreallocatedArrayElements); 229 return array->Initialize(JSArray::kPreallocatedArrayElements);
222 } 230 }
223 231
224 // Take the arguments as elements. 232 // Take the arguments as elements.
225 int number_of_elements = args.length() - 1; 233 int number_of_elements = args.length() - 1;
226 Smi* len = Smi::FromInt(number_of_elements); 234 Smi* len = Smi::FromInt(number_of_elements);
227 Object* obj = Heap::AllocateFixedArrayWithHoles(len->value()); 235 Object* obj;
228 if (obj->IsFailure()) return obj; 236 { MaybeObject* maybe_obj = Heap::AllocateFixedArrayWithHoles(len->value());
237 if (!maybe_obj->ToObject(&obj)) return maybe_obj;
238 }
229 239
230 AssertNoAllocation no_gc; 240 AssertNoAllocation no_gc;
231 FixedArray* elms = FixedArray::cast(obj); 241 FixedArray* elms = FixedArray::cast(obj);
232 WriteBarrierMode mode = elms->GetWriteBarrierMode(no_gc); 242 WriteBarrierMode mode = elms->GetWriteBarrierMode(no_gc);
233 // Fill in the content 243 // Fill in the content
234 for (int index = 0; index < number_of_elements; index++) { 244 for (int index = 0; index < number_of_elements; index++) {
235 elms->set(index, args[index+1], mode); 245 elms->set(index, args[index+1], mode);
236 } 246 }
237 247
238 // Set length and elements on the array. 248 // Set length and elements on the array.
239 array->set_elements(FixedArray::cast(obj)); 249 array->set_elements(FixedArray::cast(obj));
240 array->set_length(len); 250 array->set_length(len);
241 251
242 return array; 252 return array;
243 } 253 }
244 254
245 255
246 MUST_USE_RESULT static Object* AllocateJSArray() { 256 MUST_USE_RESULT static MaybeObject* AllocateJSArray() {
247 JSFunction* array_function = 257 JSFunction* array_function =
248 Top::context()->global_context()->array_function(); 258 Top::context()->global_context()->array_function();
249 Object* result = Heap::AllocateJSObject(array_function); 259 Object* result;
250 if (result->IsFailure()) return result; 260 { MaybeObject* maybe_result = Heap::AllocateJSObject(array_function);
261 if (!maybe_result->ToObject(&result)) return maybe_result;
262 }
251 return result; 263 return result;
252 } 264 }
253 265
254 266
255 MUST_USE_RESULT static Object* AllocateEmptyJSArray() { 267 MUST_USE_RESULT static MaybeObject* AllocateEmptyJSArray() {
256 Object* result = AllocateJSArray(); 268 Object* result;
257 if (result->IsFailure()) return result; 269 { MaybeObject* maybe_result = AllocateJSArray();
270 if (!maybe_result->ToObject(&result)) return maybe_result;
271 }
258 JSArray* result_array = JSArray::cast(result); 272 JSArray* result_array = JSArray::cast(result);
259 result_array->set_length(Smi::FromInt(0)); 273 result_array->set_length(Smi::FromInt(0));
260 result_array->set_elements(Heap::empty_fixed_array()); 274 result_array->set_elements(Heap::empty_fixed_array());
261 return result_array; 275 return result_array;
262 } 276 }
263 277
264 278
265 static void CopyElements(AssertNoAllocation* no_gc, 279 static void CopyElements(AssertNoAllocation* no_gc,
266 FixedArray* dst, 280 FixedArray* dst,
267 int dst_index, 281 int dst_index,
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after
353 ASSERT(array_proto->elements() == Heap::empty_fixed_array()); 367 ASSERT(array_proto->elements() == Heap::empty_fixed_array());
354 // Object.prototype 368 // Object.prototype
355 array_proto = JSObject::cast(array_proto->GetPrototype()); 369 array_proto = JSObject::cast(array_proto->GetPrototype());
356 if (array_proto != global_context->initial_object_prototype()) return false; 370 if (array_proto != global_context->initial_object_prototype()) return false;
357 if (array_proto->elements() != Heap::empty_fixed_array()) return false; 371 if (array_proto->elements() != Heap::empty_fixed_array()) return false;
358 ASSERT(array_proto->GetPrototype()->IsNull()); 372 ASSERT(array_proto->GetPrototype()->IsNull());
359 return true; 373 return true;
360 } 374 }
361 375
362 376
363 static inline Object* EnsureJSArrayWithWritableFastElements(Object* receiver) { 377 MUST_USE_RESULT
378 static inline MaybeObject* EnsureJSArrayWithWritableFastElements(
379 Object* receiver) {
364 if (!receiver->IsJSArray()) return NULL; 380 if (!receiver->IsJSArray()) return NULL;
365 JSArray* array = JSArray::cast(receiver); 381 JSArray* array = JSArray::cast(receiver);
366 HeapObject* elms = HeapObject::cast(array->elements()); 382 HeapObject* elms = HeapObject::cast(array->elements());
367 if (elms->map() == Heap::fixed_array_map()) return elms; 383 if (elms->map() == Heap::fixed_array_map()) return elms;
368 if (elms->map() == Heap::fixed_cow_array_map()) { 384 if (elms->map() == Heap::fixed_cow_array_map()) {
369 return array->EnsureWritableFastElements(); 385 return array->EnsureWritableFastElements();
370 } 386 }
371 return NULL; 387 return NULL;
372 } 388 }
373 389
374 390
375 static inline bool IsJSArrayFastElementMovingAllowed(JSArray* receiver) { 391 static inline bool IsJSArrayFastElementMovingAllowed(JSArray* receiver) {
376 Context* global_context = Top::context()->global_context(); 392 Context* global_context = Top::context()->global_context();
377 JSObject* array_proto = 393 JSObject* array_proto =
378 JSObject::cast(global_context->array_function()->prototype()); 394 JSObject::cast(global_context->array_function()->prototype());
379 return receiver->GetPrototype() == array_proto && 395 return receiver->GetPrototype() == array_proto &&
380 ArrayPrototypeHasNoElements(global_context, array_proto); 396 ArrayPrototypeHasNoElements(global_context, array_proto);
381 } 397 }
382 398
383 399
384 static Object* CallJsBuiltin(const char* name, 400 MUST_USE_RESULT static MaybeObject* CallJsBuiltin(
385 BuiltinArguments<NO_EXTRA_ARGUMENTS> args) { 401 const char* name,
402 BuiltinArguments<NO_EXTRA_ARGUMENTS> args) {
386 HandleScope handleScope; 403 HandleScope handleScope;
387 404
388 Handle<Object> js_builtin = 405 Handle<Object> js_builtin =
389 GetProperty(Handle<JSObject>(Top::global_context()->builtins()), 406 GetProperty(Handle<JSObject>(Top::global_context()->builtins()),
390 name); 407 name);
391 ASSERT(js_builtin->IsJSFunction()); 408 ASSERT(js_builtin->IsJSFunction());
392 Handle<JSFunction> function(Handle<JSFunction>::cast(js_builtin)); 409 Handle<JSFunction> function(Handle<JSFunction>::cast(js_builtin));
393 ScopedVector<Object**> argv(args.length() - 1); 410 ScopedVector<Object**> argv(args.length() - 1);
394 int n_args = args.length() - 1; 411 int n_args = args.length() - 1;
395 for (int i = 0; i < n_args; i++) { 412 for (int i = 0; i < n_args; i++) {
396 argv[i] = args.at<Object>(i + 1).location(); 413 argv[i] = args.at<Object>(i + 1).location();
397 } 414 }
398 bool pending_exception = false; 415 bool pending_exception = false;
399 Handle<Object> result = Execution::Call(function, 416 Handle<Object> result = Execution::Call(function,
400 args.receiver(), 417 args.receiver(),
401 n_args, 418 n_args,
402 argv.start(), 419 argv.start(),
403 &pending_exception); 420 &pending_exception);
404 if (pending_exception) return Failure::Exception(); 421 if (pending_exception) return Failure::Exception();
405 return *result; 422 return *result;
406 } 423 }
407 424
408 425
409 BUILTIN(ArrayPush) { 426 BUILTIN(ArrayPush) {
410 Object* receiver = *args.receiver(); 427 Object* receiver = *args.receiver();
411 Object* elms_obj = EnsureJSArrayWithWritableFastElements(receiver); 428 Object* elms_obj;
412 if (elms_obj == NULL) return CallJsBuiltin("ArrayPush", args); 429 { MaybeObject* maybe_elms_obj =
413 if (elms_obj->IsFailure()) return elms_obj; 430 EnsureJSArrayWithWritableFastElements(receiver);
431 if (maybe_elms_obj == NULL) return CallJsBuiltin("ArrayPush", args);
432 if (!maybe_elms_obj->ToObject(&elms_obj)) return maybe_elms_obj;
433 }
414 FixedArray* elms = FixedArray::cast(elms_obj); 434 FixedArray* elms = FixedArray::cast(elms_obj);
415 JSArray* array = JSArray::cast(receiver); 435 JSArray* array = JSArray::cast(receiver);
416 436
417 int len = Smi::cast(array->length())->value(); 437 int len = Smi::cast(array->length())->value();
418 int to_add = args.length() - 1; 438 int to_add = args.length() - 1;
419 if (to_add == 0) { 439 if (to_add == 0) {
420 return Smi::FromInt(len); 440 return Smi::FromInt(len);
421 } 441 }
422 // Currently fixed arrays cannot grow too big, so 442 // Currently fixed arrays cannot grow too big, so
423 // we should never hit this case. 443 // we should never hit this case.
424 ASSERT(to_add <= (Smi::kMaxValue - len)); 444 ASSERT(to_add <= (Smi::kMaxValue - len));
425 445
426 int new_length = len + to_add; 446 int new_length = len + to_add;
427 447
428 if (new_length > elms->length()) { 448 if (new_length > elms->length()) {
429 // New backing storage is needed. 449 // New backing storage is needed.
430 int capacity = new_length + (new_length >> 1) + 16; 450 int capacity = new_length + (new_length >> 1) + 16;
431 Object* obj = Heap::AllocateUninitializedFixedArray(capacity); 451 Object* obj;
432 if (obj->IsFailure()) return obj; 452 { MaybeObject* maybe_obj = Heap::AllocateUninitializedFixedArray(capacity);
453 if (!maybe_obj->ToObject(&obj)) return maybe_obj;
454 }
433 FixedArray* new_elms = FixedArray::cast(obj); 455 FixedArray* new_elms = FixedArray::cast(obj);
434 456
435 AssertNoAllocation no_gc; 457 AssertNoAllocation no_gc;
436 if (len > 0) { 458 if (len > 0) {
437 CopyElements(&no_gc, new_elms, 0, elms, 0, len); 459 CopyElements(&no_gc, new_elms, 0, elms, 0, len);
438 } 460 }
439 FillWithHoles(new_elms, new_length, capacity); 461 FillWithHoles(new_elms, new_length, capacity);
440 462
441 elms = new_elms; 463 elms = new_elms;
442 array->set_elements(elms); 464 array->set_elements(elms);
443 } 465 }
444 466
445 // Add the provided values. 467 // Add the provided values.
446 AssertNoAllocation no_gc; 468 AssertNoAllocation no_gc;
447 WriteBarrierMode mode = elms->GetWriteBarrierMode(no_gc); 469 WriteBarrierMode mode = elms->GetWriteBarrierMode(no_gc);
448 for (int index = 0; index < to_add; index++) { 470 for (int index = 0; index < to_add; index++) {
449 elms->set(index + len, args[index + 1], mode); 471 elms->set(index + len, args[index + 1], mode);
450 } 472 }
451 473
452 // Set the length. 474 // Set the length.
453 array->set_length(Smi::FromInt(new_length)); 475 array->set_length(Smi::FromInt(new_length));
454 return Smi::FromInt(new_length); 476 return Smi::FromInt(new_length);
455 } 477 }
456 478
457 479
458 BUILTIN(ArrayPop) { 480 BUILTIN(ArrayPop) {
459 Object* receiver = *args.receiver(); 481 Object* receiver = *args.receiver();
460 Object* elms_obj = EnsureJSArrayWithWritableFastElements(receiver); 482 Object* elms_obj;
461 if (elms_obj == NULL) return CallJsBuiltin("ArrayPop", args); 483 { MaybeObject* maybe_elms_obj =
462 if (elms_obj->IsFailure()) return elms_obj; 484 EnsureJSArrayWithWritableFastElements(receiver);
485 if (maybe_elms_obj == NULL) return CallJsBuiltin("ArrayPop", args);
486 if (!maybe_elms_obj->ToObject(&elms_obj)) return maybe_elms_obj;
487 }
463 FixedArray* elms = FixedArray::cast(elms_obj); 488 FixedArray* elms = FixedArray::cast(elms_obj);
464 JSArray* array = JSArray::cast(receiver); 489 JSArray* array = JSArray::cast(receiver);
465 490
466 int len = Smi::cast(array->length())->value(); 491 int len = Smi::cast(array->length())->value();
467 if (len == 0) return Heap::undefined_value(); 492 if (len == 0) return Heap::undefined_value();
468 493
469 // Get top element 494 // Get top element
470 Object* top = elms->get(len - 1); 495 MaybeObject* top = elms->get(len - 1);
471 496
472 // Set the length. 497 // Set the length.
473 array->set_length(Smi::FromInt(len - 1)); 498 array->set_length(Smi::FromInt(len - 1));
474 499
475 if (!top->IsTheHole()) { 500 if (!top->IsTheHole()) {
476 // Delete the top element. 501 // Delete the top element.
477 elms->set_the_hole(len - 1); 502 elms->set_the_hole(len - 1);
478 return top; 503 return top;
479 } 504 }
480 505
481 top = array->GetPrototype()->GetElement(len - 1); 506 top = array->GetPrototype()->GetElement(len - 1);
482 507
483 return top; 508 return top;
484 } 509 }
485 510
486 511
487 BUILTIN(ArrayShift) { 512 BUILTIN(ArrayShift) {
488 Object* receiver = *args.receiver(); 513 Object* receiver = *args.receiver();
489 Object* elms_obj = EnsureJSArrayWithWritableFastElements(receiver); 514 Object* elms_obj;
490 if (elms_obj->IsFailure()) return elms_obj; 515 { MaybeObject* maybe_elms_obj =
516 EnsureJSArrayWithWritableFastElements(receiver);
517 if (!maybe_elms_obj->ToObject(&elms_obj)) return maybe_elms_obj;
518 }
491 if (elms_obj == NULL || 519 if (elms_obj == NULL ||
492 !IsJSArrayFastElementMovingAllowed(JSArray::cast(receiver))) { 520 !IsJSArrayFastElementMovingAllowed(JSArray::cast(receiver))) {
493 return CallJsBuiltin("ArrayShift", args); 521 return CallJsBuiltin("ArrayShift", args);
494 } 522 }
495 FixedArray* elms = FixedArray::cast(elms_obj); 523 FixedArray* elms = FixedArray::cast(elms_obj);
496 JSArray* array = JSArray::cast(receiver); 524 JSArray* array = JSArray::cast(receiver);
497 ASSERT(array->HasFastElements()); 525 ASSERT(array->HasFastElements());
498 526
499 int len = Smi::cast(array->length())->value(); 527 int len = Smi::cast(array->length())->value();
500 if (len == 0) return Heap::undefined_value(); 528 if (len == 0) return Heap::undefined_value();
(...skipping 17 matching lines...) Expand all
518 546
519 // Set the length. 547 // Set the length.
520 array->set_length(Smi::FromInt(len - 1)); 548 array->set_length(Smi::FromInt(len - 1));
521 549
522 return first; 550 return first;
523 } 551 }
524 552
525 553
526 BUILTIN(ArrayUnshift) { 554 BUILTIN(ArrayUnshift) {
527 Object* receiver = *args.receiver(); 555 Object* receiver = *args.receiver();
528 Object* elms_obj = EnsureJSArrayWithWritableFastElements(receiver); 556 Object* elms_obj;
529 if (elms_obj->IsFailure()) return elms_obj; 557 { MaybeObject* maybe_elms_obj =
558 EnsureJSArrayWithWritableFastElements(receiver);
559 if (!maybe_elms_obj->ToObject(&elms_obj)) return maybe_elms_obj;
560 }
530 if (elms_obj == NULL || 561 if (elms_obj == NULL ||
531 !IsJSArrayFastElementMovingAllowed(JSArray::cast(receiver))) { 562 !IsJSArrayFastElementMovingAllowed(JSArray::cast(receiver))) {
532 return CallJsBuiltin("ArrayUnshift", args); 563 return CallJsBuiltin("ArrayUnshift", args);
533 } 564 }
534 FixedArray* elms = FixedArray::cast(elms_obj); 565 FixedArray* elms = FixedArray::cast(elms_obj);
535 JSArray* array = JSArray::cast(receiver); 566 JSArray* array = JSArray::cast(receiver);
536 ASSERT(array->HasFastElements()); 567 ASSERT(array->HasFastElements());
537 568
538 int len = Smi::cast(array->length())->value(); 569 int len = Smi::cast(array->length())->value();
539 int to_add = args.length() - 1; 570 int to_add = args.length() - 1;
540 int new_length = len + to_add; 571 int new_length = len + to_add;
541 // Currently fixed arrays cannot grow too big, so 572 // Currently fixed arrays cannot grow too big, so
542 // we should never hit this case. 573 // we should never hit this case.
543 ASSERT(to_add <= (Smi::kMaxValue - len)); 574 ASSERT(to_add <= (Smi::kMaxValue - len));
544 575
545 if (new_length > elms->length()) { 576 if (new_length > elms->length()) {
546 // New backing storage is needed. 577 // New backing storage is needed.
547 int capacity = new_length + (new_length >> 1) + 16; 578 int capacity = new_length + (new_length >> 1) + 16;
548 Object* obj = Heap::AllocateUninitializedFixedArray(capacity); 579 Object* obj;
549 if (obj->IsFailure()) return obj; 580 { MaybeObject* maybe_obj = Heap::AllocateUninitializedFixedArray(capacity);
581 if (!maybe_obj->ToObject(&obj)) return maybe_obj;
582 }
550 FixedArray* new_elms = FixedArray::cast(obj); 583 FixedArray* new_elms = FixedArray::cast(obj);
551 584
552 AssertNoAllocation no_gc; 585 AssertNoAllocation no_gc;
553 if (len > 0) { 586 if (len > 0) {
554 CopyElements(&no_gc, new_elms, to_add, elms, 0, len); 587 CopyElements(&no_gc, new_elms, to_add, elms, 0, len);
555 } 588 }
556 FillWithHoles(new_elms, new_length, capacity); 589 FillWithHoles(new_elms, new_length, capacity);
557 590
558 elms = new_elms; 591 elms = new_elms;
559 array->set_elements(elms); 592 array->set_elements(elms);
(...skipping 10 matching lines...) Expand all
570 } 603 }
571 604
572 // Set the length. 605 // Set the length.
573 array->set_length(Smi::FromInt(new_length)); 606 array->set_length(Smi::FromInt(new_length));
574 return Smi::FromInt(new_length); 607 return Smi::FromInt(new_length);
575 } 608 }
576 609
577 610
578 BUILTIN(ArraySlice) { 611 BUILTIN(ArraySlice) {
579 Object* receiver = *args.receiver(); 612 Object* receiver = *args.receiver();
580 Object* elms_obj = EnsureJSArrayWithWritableFastElements(receiver); 613 Object* elms_obj;
581 if (elms_obj->IsFailure()) return elms_obj; 614 { MaybeObject* maybe_elms_obj =
615 EnsureJSArrayWithWritableFastElements(receiver);
616 if (!maybe_elms_obj->ToObject(&elms_obj)) return maybe_elms_obj;
617 }
582 if (elms_obj == NULL || 618 if (elms_obj == NULL ||
583 !IsJSArrayFastElementMovingAllowed(JSArray::cast(receiver))) { 619 !IsJSArrayFastElementMovingAllowed(JSArray::cast(receiver))) {
584 return CallJsBuiltin("ArraySlice", args); 620 return CallJsBuiltin("ArraySlice", args);
585 } 621 }
586 FixedArray* elms = FixedArray::cast(elms_obj); 622 FixedArray* elms = FixedArray::cast(elms_obj);
587 JSArray* array = JSArray::cast(receiver); 623 JSArray* array = JSArray::cast(receiver);
588 ASSERT(array->HasFastElements()); 624 ASSERT(array->HasFastElements());
589 625
590 int len = Smi::cast(array->length())->value(); 626 int len = Smi::cast(array->length())->value();
591 627
(...skipping 28 matching lines...) Expand all
620 // ECMAScript 232, 3rd Edition, Section 15.4.4.10, step 8. 656 // ECMAScript 232, 3rd Edition, Section 15.4.4.10, step 8.
621 int final = (relative_end < 0) ? Max(len + relative_end, 0) 657 int final = (relative_end < 0) ? Max(len + relative_end, 0)
622 : Min(relative_end, len); 658 : Min(relative_end, len);
623 659
624 // Calculate the length of result array. 660 // Calculate the length of result array.
625 int result_len = final - k; 661 int result_len = final - k;
626 if (result_len <= 0) { 662 if (result_len <= 0) {
627 return AllocateEmptyJSArray(); 663 return AllocateEmptyJSArray();
628 } 664 }
629 665
630 Object* result = AllocateJSArray(); 666 Object* result;
631 if (result->IsFailure()) return result; 667 { MaybeObject* maybe_result = AllocateJSArray();
668 if (!maybe_result->ToObject(&result)) return maybe_result;
669 }
632 JSArray* result_array = JSArray::cast(result); 670 JSArray* result_array = JSArray::cast(result);
633 671
634 result = Heap::AllocateUninitializedFixedArray(result_len); 672 { MaybeObject* maybe_result =
635 if (result->IsFailure()) return result; 673 Heap::AllocateUninitializedFixedArray(result_len);
674 if (!maybe_result->ToObject(&result)) return maybe_result;
675 }
636 FixedArray* result_elms = FixedArray::cast(result); 676 FixedArray* result_elms = FixedArray::cast(result);
637 677
638 AssertNoAllocation no_gc; 678 AssertNoAllocation no_gc;
639 CopyElements(&no_gc, result_elms, 0, elms, k, result_len); 679 CopyElements(&no_gc, result_elms, 0, elms, k, result_len);
640 680
641 // Set elements. 681 // Set elements.
642 result_array->set_elements(result_elms); 682 result_array->set_elements(result_elms);
643 683
644 // Set the length. 684 // Set the length.
645 result_array->set_length(Smi::FromInt(result_len)); 685 result_array->set_length(Smi::FromInt(result_len));
646 return result_array; 686 return result_array;
647 } 687 }
648 688
649 689
650 BUILTIN(ArraySplice) { 690 BUILTIN(ArraySplice) {
651 Object* receiver = *args.receiver(); 691 Object* receiver = *args.receiver();
652 Object* elms_obj = EnsureJSArrayWithWritableFastElements(receiver); 692 Object* elms_obj;
653 if (elms_obj->IsFailure()) return elms_obj; 693 { MaybeObject* maybe_elms_obj =
694 EnsureJSArrayWithWritableFastElements(receiver);
695 if (!maybe_elms_obj->ToObject(&elms_obj)) return maybe_elms_obj;
696 }
654 if (elms_obj == NULL || 697 if (elms_obj == NULL ||
655 !IsJSArrayFastElementMovingAllowed(JSArray::cast(receiver))) { 698 !IsJSArrayFastElementMovingAllowed(JSArray::cast(receiver))) {
656 return CallJsBuiltin("ArraySplice", args); 699 return CallJsBuiltin("ArraySplice", args);
657 } 700 }
658 FixedArray* elms = FixedArray::cast(elms_obj); 701 FixedArray* elms = FixedArray::cast(elms_obj);
659 JSArray* array = JSArray::cast(receiver); 702 JSArray* array = JSArray::cast(receiver);
660 ASSERT(array->HasFastElements()); 703 ASSERT(array->HasFastElements());
661 704
662 int len = Smi::cast(array->length())->value(); 705 int len = Smi::cast(array->length())->value();
663 706
(...skipping 24 matching lines...) Expand all
688 if (arg2->IsSmi()) { 731 if (arg2->IsSmi()) {
689 delete_count = Smi::cast(arg2)->value(); 732 delete_count = Smi::cast(arg2)->value();
690 } else { 733 } else {
691 return CallJsBuiltin("ArraySplice", args); 734 return CallJsBuiltin("ArraySplice", args);
692 } 735 }
693 } 736 }
694 int actual_delete_count = Min(Max(delete_count, 0), len - actual_start); 737 int actual_delete_count = Min(Max(delete_count, 0), len - actual_start);
695 738
696 JSArray* result_array = NULL; 739 JSArray* result_array = NULL;
697 if (actual_delete_count == 0) { 740 if (actual_delete_count == 0) {
698 Object* result = AllocateEmptyJSArray(); 741 Object* result;
699 if (result->IsFailure()) return result; 742 { MaybeObject* maybe_result = AllocateEmptyJSArray();
743 if (!maybe_result->ToObject(&result)) return maybe_result;
744 }
700 result_array = JSArray::cast(result); 745 result_array = JSArray::cast(result);
701 } else { 746 } else {
702 // Allocate result array. 747 // Allocate result array.
703 Object* result = AllocateJSArray(); 748 Object* result;
704 if (result->IsFailure()) return result; 749 { MaybeObject* maybe_result = AllocateJSArray();
750 if (!maybe_result->ToObject(&result)) return maybe_result;
751 }
705 result_array = JSArray::cast(result); 752 result_array = JSArray::cast(result);
706 753
707 result = Heap::AllocateUninitializedFixedArray(actual_delete_count); 754 { MaybeObject* maybe_result =
708 if (result->IsFailure()) return result; 755 Heap::AllocateUninitializedFixedArray(actual_delete_count);
756 if (!maybe_result->ToObject(&result)) return maybe_result;
757 }
709 FixedArray* result_elms = FixedArray::cast(result); 758 FixedArray* result_elms = FixedArray::cast(result);
710 759
711 AssertNoAllocation no_gc; 760 AssertNoAllocation no_gc;
712 // Fill newly created array. 761 // Fill newly created array.
713 CopyElements(&no_gc, 762 CopyElements(&no_gc,
714 result_elms, 0, 763 result_elms, 0,
715 elms, actual_start, 764 elms, actual_start,
716 actual_delete_count); 765 actual_delete_count);
717 766
718 // Set elements. 767 // Set elements.
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
751 } 800 }
752 } else if (item_count > actual_delete_count) { 801 } else if (item_count > actual_delete_count) {
753 // Currently fixed arrays cannot grow too big, so 802 // Currently fixed arrays cannot grow too big, so
754 // we should never hit this case. 803 // we should never hit this case.
755 ASSERT((item_count - actual_delete_count) <= (Smi::kMaxValue - len)); 804 ASSERT((item_count - actual_delete_count) <= (Smi::kMaxValue - len));
756 805
757 // Check if array need to grow. 806 // Check if array need to grow.
758 if (new_length > elms->length()) { 807 if (new_length > elms->length()) {
759 // New backing storage is needed. 808 // New backing storage is needed.
760 int capacity = new_length + (new_length >> 1) + 16; 809 int capacity = new_length + (new_length >> 1) + 16;
761 Object* obj = Heap::AllocateUninitializedFixedArray(capacity); 810 Object* obj;
762 if (obj->IsFailure()) return obj; 811 { MaybeObject* maybe_obj =
812 Heap::AllocateUninitializedFixedArray(capacity);
813 if (!maybe_obj->ToObject(&obj)) return maybe_obj;
814 }
763 FixedArray* new_elms = FixedArray::cast(obj); 815 FixedArray* new_elms = FixedArray::cast(obj);
764 816
765 AssertNoAllocation no_gc; 817 AssertNoAllocation no_gc;
766 // Copy the part before actual_start as is. 818 // Copy the part before actual_start as is.
767 if (actual_start > 0) { 819 if (actual_start > 0) {
768 CopyElements(&no_gc, new_elms, 0, elms, 0, actual_start); 820 CopyElements(&no_gc, new_elms, 0, elms, 0, actual_start);
769 } 821 }
770 const int to_copy = len - actual_delete_count - actual_start; 822 const int to_copy = len - actual_delete_count - actual_start;
771 if (to_copy > 0) { 823 if (to_copy > 0) {
772 CopyElements(&no_gc, 824 CopyElements(&no_gc,
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after
831 if (result_len > FixedArray::kMaxLength) { 883 if (result_len > FixedArray::kMaxLength) {
832 return CallJsBuiltin("ArrayConcat", args); 884 return CallJsBuiltin("ArrayConcat", args);
833 } 885 }
834 } 886 }
835 887
836 if (result_len == 0) { 888 if (result_len == 0) {
837 return AllocateEmptyJSArray(); 889 return AllocateEmptyJSArray();
838 } 890 }
839 891
840 // Allocate result. 892 // Allocate result.
841 Object* result = AllocateJSArray(); 893 Object* result;
842 if (result->IsFailure()) return result; 894 { MaybeObject* maybe_result = AllocateJSArray();
895 if (!maybe_result->ToObject(&result)) return maybe_result;
896 }
843 JSArray* result_array = JSArray::cast(result); 897 JSArray* result_array = JSArray::cast(result);
844 898
845 result = Heap::AllocateUninitializedFixedArray(result_len); 899 { MaybeObject* maybe_result =
846 if (result->IsFailure()) return result; 900 Heap::AllocateUninitializedFixedArray(result_len);
901 if (!maybe_result->ToObject(&result)) return maybe_result;
902 }
847 FixedArray* result_elms = FixedArray::cast(result); 903 FixedArray* result_elms = FixedArray::cast(result);
848 904
849 // Copy data. 905 // Copy data.
850 AssertNoAllocation no_gc; 906 AssertNoAllocation no_gc;
851 int start_pos = 0; 907 int start_pos = 0;
852 for (int i = 0; i < n_arguments; i++) { 908 for (int i = 0; i < n_arguments; i++) {
853 JSArray* array = JSArray::cast(args[i]); 909 JSArray* array = JSArray::cast(args[i]);
854 int len = Smi::cast(array->length())->value(); 910 int len = Smi::cast(array->length())->value();
855 if (len > 0) { 911 if (len > 0) {
856 FixedArray* elms = FixedArray::cast(array->elements()); 912 FixedArray* elms = FixedArray::cast(array->elements());
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
914 break; 970 break;
915 } 971 }
916 } 972 }
917 if (current == Heap::null_value()) *arg = Heap::undefined_value(); 973 if (current == Heap::null_value()) *arg = Heap::undefined_value();
918 } 974 }
919 return holder; 975 return holder;
920 } 976 }
921 977
922 978
923 template <bool is_construct> 979 template <bool is_construct>
924 static Object* HandleApiCallHelper( 980 MUST_USE_RESULT static MaybeObject* HandleApiCallHelper(
925 BuiltinArguments<NEEDS_CALLED_FUNCTION> args) { 981 BuiltinArguments<NEEDS_CALLED_FUNCTION> args) {
926 ASSERT(is_construct == CalledAsConstructor()); 982 ASSERT(is_construct == CalledAsConstructor());
927 983
928 HandleScope scope; 984 HandleScope scope;
929 Handle<JSFunction> function = args.called_function(); 985 Handle<JSFunction> function = args.called_function();
930 ASSERT(function->shared()->IsApiFunction()); 986 ASSERT(function->shared()->IsApiFunction());
931 987
932 FunctionTemplateInfo* fun_data = function->shared()->get_api_func_data(); 988 FunctionTemplateInfo* fun_data = function->shared()->get_api_func_data();
933 if (is_construct) { 989 if (is_construct) {
934 Handle<FunctionTemplateInfo> desc(fun_data); 990 Handle<FunctionTemplateInfo> desc(fun_data);
(...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after
1072 } 1128 }
1073 1129
1074 RETURN_IF_SCHEDULED_EXCEPTION(); 1130 RETURN_IF_SCHEDULED_EXCEPTION();
1075 return result; 1131 return result;
1076 } 1132 }
1077 1133
1078 1134
1079 // Helper function to handle calls to non-function objects created through the 1135 // Helper function to handle calls to non-function objects created through the
1080 // API. The object can be called as either a constructor (using new) or just as 1136 // API. The object can be called as either a constructor (using new) or just as
1081 // a function (without new). 1137 // a function (without new).
1082 static Object* HandleApiCallAsFunctionOrConstructor( 1138 MUST_USE_RESULT static MaybeObject* HandleApiCallAsFunctionOrConstructor(
1083 bool is_construct_call, 1139 bool is_construct_call,
1084 BuiltinArguments<NO_EXTRA_ARGUMENTS> args) { 1140 BuiltinArguments<NO_EXTRA_ARGUMENTS> args) {
1085 // Non-functions are never called as constructors. Even if this is an object 1141 // Non-functions are never called as constructors. Even if this is an object
1086 // called as a constructor the delegate call is not a construct call. 1142 // called as a constructor the delegate call is not a construct call.
1087 ASSERT(!CalledAsConstructor()); 1143 ASSERT(!CalledAsConstructor());
1088 1144
1089 Handle<Object> receiver = args.at<Object>(0); 1145 Handle<Object> receiver = args.at<Object>(0);
1090 1146
1091 // Get the object called. 1147 // Get the object called.
1092 JSObject* obj = JSObject::cast(*args.receiver()); 1148 JSObject* obj = JSObject::cast(*args.receiver());
(...skipping 381 matching lines...) Expand 10 before | Expand all | Expand 10 after
1474 typedef void (*Generator)(MacroAssembler*, int, BuiltinExtraArguments); 1530 typedef void (*Generator)(MacroAssembler*, int, BuiltinExtraArguments);
1475 Generator g = FUNCTION_CAST<Generator>(functions[i].generator); 1531 Generator g = FUNCTION_CAST<Generator>(functions[i].generator);
1476 // We pass all arguments to the generator, but it may not use all of 1532 // We pass all arguments to the generator, but it may not use all of
1477 // them. This works because the first arguments are on top of the 1533 // them. This works because the first arguments are on top of the
1478 // stack. 1534 // stack.
1479 g(&masm, functions[i].name, functions[i].extra_args); 1535 g(&masm, functions[i].name, functions[i].extra_args);
1480 // Move the code into the object heap. 1536 // Move the code into the object heap.
1481 CodeDesc desc; 1537 CodeDesc desc;
1482 masm.GetCode(&desc); 1538 masm.GetCode(&desc);
1483 Code::Flags flags = functions[i].flags; 1539 Code::Flags flags = functions[i].flags;
1484 Object* code; 1540 Object* code = 0;
1485 { 1541 {
1486 // During startup it's OK to always allocate and defer GC to later. 1542 // During startup it's OK to always allocate and defer GC to later.
1487 // This simplifies things because we don't need to retry. 1543 // This simplifies things because we don't need to retry.
1488 AlwaysAllocateScope __scope__; 1544 AlwaysAllocateScope __scope__;
1489 code = Heap::CreateCode(desc, flags, masm.CodeObject()); 1545 { MaybeObject* maybe_code =
1490 if (code->IsFailure()) { 1546 Heap::CreateCode(desc, flags, masm.CodeObject());
1491 v8::internal::V8::FatalProcessOutOfMemory("CreateCode"); 1547 if (!maybe_code->ToObject(&code)) {
1548 v8::internal::V8::FatalProcessOutOfMemory("CreateCode");
1549 }
1492 } 1550 }
1493 } 1551 }
1494 // Log the event and add the code to the builtins array. 1552 // Log the event and add the code to the builtins array.
1495 PROFILE(CodeCreateEvent(Logger::BUILTIN_TAG, 1553 PROFILE(CodeCreateEvent(Logger::BUILTIN_TAG,
1496 Code::cast(code), functions[i].s_name)); 1554 Code::cast(code), functions[i].s_name));
1497 builtins_[i] = code; 1555 builtins_[i] = code;
1498 #ifdef ENABLE_DISASSEMBLER 1556 #ifdef ENABLE_DISASSEMBLER
1499 if (FLAG_print_builtin_code) { 1557 if (FLAG_print_builtin_code) {
1500 PrintF("Builtin: %s\n", functions[i].s_name); 1558 PrintF("Builtin: %s\n", functions[i].s_name);
1501 Code::cast(code)->Disassemble(functions[i].s_name); 1559 Code::cast(code)->Disassemble(functions[i].s_name);
(...skipping 27 matching lines...) Expand all
1529 for (int i = 0; i < builtin_count; i++) { 1587 for (int i = 0; i < builtin_count; i++) {
1530 Code* entry = Code::cast(builtins_[i]); 1588 Code* entry = Code::cast(builtins_[i]);
1531 if (entry->contains(pc)) { 1589 if (entry->contains(pc)) {
1532 return names_[i]; 1590 return names_[i];
1533 } 1591 }
1534 } 1592 }
1535 } 1593 }
1536 return NULL; 1594 return NULL;
1537 } 1595 }
1538 1596
1539
1540 } } // namespace v8::internal 1597 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/bootstrapper.cc ('k') | src/code-stubs.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698