| OLD | NEW |
| 1 // Copyright 2006-2009 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2009 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 313 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 324 // of the receiver and use the result; see ECMA-262 section 13.2.2-7 | 324 // of the receiver and use the result; see ECMA-262 section 13.2.2-7 |
| 325 // on page 74. | 325 // on page 74. |
| 326 Label use_receiver, exit; | 326 Label use_receiver, exit; |
| 327 | 327 |
| 328 // If the result is a smi, it is *not* an object in the ECMA sense. | 328 // If the result is a smi, it is *not* an object in the ECMA sense. |
| 329 __ test(eax, Immediate(kSmiTagMask)); | 329 __ test(eax, Immediate(kSmiTagMask)); |
| 330 __ j(zero, &use_receiver, not_taken); | 330 __ j(zero, &use_receiver, not_taken); |
| 331 | 331 |
| 332 // If the type of the result (stored in its map) is less than | 332 // If the type of the result (stored in its map) is less than |
| 333 // FIRST_JS_OBJECT_TYPE, it is not an object in the ECMA sense. | 333 // FIRST_JS_OBJECT_TYPE, it is not an object in the ECMA sense. |
| 334 __ mov(ecx, FieldOperand(eax, HeapObject::kMapOffset)); | 334 __ CmpObjectType(eax, FIRST_JS_OBJECT_TYPE, ecx); |
| 335 __ movzx_b(ecx, FieldOperand(ecx, Map::kInstanceTypeOffset)); | 335 __ j(above_equal, &exit, not_taken); |
| 336 __ cmp(ecx, FIRST_JS_OBJECT_TYPE); | |
| 337 __ j(greater_equal, &exit, not_taken); | |
| 338 | 336 |
| 339 // Throw away the result of the constructor invocation and use the | 337 // Throw away the result of the constructor invocation and use the |
| 340 // on-stack receiver as the result. | 338 // on-stack receiver as the result. |
| 341 __ bind(&use_receiver); | 339 __ bind(&use_receiver); |
| 342 __ mov(eax, Operand(esp, 0)); | 340 __ mov(eax, Operand(esp, 0)); |
| 343 | 341 |
| 344 // Restore the arguments count and leave the construct frame. | 342 // Restore the arguments count and leave the construct frame. |
| 345 __ bind(&exit); | 343 __ bind(&exit); |
| 346 __ mov(ebx, Operand(esp, kPointerSize)); // get arguments count | 344 __ mov(ebx, Operand(esp, kPointerSize)); // get arguments count |
| 347 __ LeaveConstructFrame(); | 345 __ LeaveConstructFrame(); |
| (...skipping 114 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 462 | 460 |
| 463 __ mov(ebx, Operand(esp, eax, times_4, 0)); // First argument. | 461 __ mov(ebx, Operand(esp, eax, times_4, 0)); // First argument. |
| 464 __ test(ebx, Immediate(kSmiTagMask)); | 462 __ test(ebx, Immediate(kSmiTagMask)); |
| 465 __ j(zero, &convert_to_object); | 463 __ j(zero, &convert_to_object); |
| 466 | 464 |
| 467 __ cmp(ebx, Factory::null_value()); | 465 __ cmp(ebx, Factory::null_value()); |
| 468 __ j(equal, &use_global_receiver); | 466 __ j(equal, &use_global_receiver); |
| 469 __ cmp(ebx, Factory::undefined_value()); | 467 __ cmp(ebx, Factory::undefined_value()); |
| 470 __ j(equal, &use_global_receiver); | 468 __ j(equal, &use_global_receiver); |
| 471 | 469 |
| 470 // We don't use IsObjectJSObjectType here because we jump on success. |
| 472 __ mov(ecx, FieldOperand(ebx, HeapObject::kMapOffset)); | 471 __ mov(ecx, FieldOperand(ebx, HeapObject::kMapOffset)); |
| 473 __ movzx_b(ecx, FieldOperand(ecx, Map::kInstanceTypeOffset)); | 472 __ movzx_b(ecx, FieldOperand(ecx, Map::kInstanceTypeOffset)); |
| 474 __ cmp(ecx, FIRST_JS_OBJECT_TYPE); | 473 __ sub(Operand(ecx), Immediate(FIRST_JS_OBJECT_TYPE)); |
| 475 __ j(below, &convert_to_object); | 474 __ cmp(ecx, LAST_JS_OBJECT_TYPE - FIRST_JS_OBJECT_TYPE); |
| 476 __ cmp(ecx, LAST_JS_OBJECT_TYPE); | |
| 477 __ j(below_equal, &shift_arguments); | 475 __ j(below_equal, &shift_arguments); |
| 478 | 476 |
| 479 __ bind(&convert_to_object); | 477 __ bind(&convert_to_object); |
| 480 __ EnterInternalFrame(); // In order to preserve argument count. | 478 __ EnterInternalFrame(); // In order to preserve argument count. |
| 481 __ SmiTag(eax); | 479 __ SmiTag(eax); |
| 482 __ push(eax); | 480 __ push(eax); |
| 483 | 481 |
| 484 __ push(ebx); | 482 __ push(ebx); |
| 485 __ InvokeBuiltin(Builtins::TO_OBJECT, CALL_FUNCTION); | 483 __ InvokeBuiltin(Builtins::TO_OBJECT, CALL_FUNCTION); |
| 486 __ mov(ebx, eax); | 484 __ mov(ebx, eax); |
| (...skipping 123 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 610 __ mov(ebx, Operand(ebp, 3 * kPointerSize)); | 608 __ mov(ebx, Operand(ebp, 3 * kPointerSize)); |
| 611 __ test(ebx, Immediate(kSmiTagMask)); | 609 __ test(ebx, Immediate(kSmiTagMask)); |
| 612 __ j(zero, &call_to_object); | 610 __ j(zero, &call_to_object); |
| 613 __ cmp(ebx, Factory::null_value()); | 611 __ cmp(ebx, Factory::null_value()); |
| 614 __ j(equal, &use_global_receiver); | 612 __ j(equal, &use_global_receiver); |
| 615 __ cmp(ebx, Factory::undefined_value()); | 613 __ cmp(ebx, Factory::undefined_value()); |
| 616 __ j(equal, &use_global_receiver); | 614 __ j(equal, &use_global_receiver); |
| 617 | 615 |
| 618 // If given receiver is already a JavaScript object then there's no | 616 // If given receiver is already a JavaScript object then there's no |
| 619 // reason for converting it. | 617 // reason for converting it. |
| 618 // We don't use IsObjectJSObjectType here because we jump on success. |
| 620 __ mov(ecx, FieldOperand(ebx, HeapObject::kMapOffset)); | 619 __ mov(ecx, FieldOperand(ebx, HeapObject::kMapOffset)); |
| 621 __ movzx_b(ecx, FieldOperand(ecx, Map::kInstanceTypeOffset)); | 620 __ movzx_b(ecx, FieldOperand(ecx, Map::kInstanceTypeOffset)); |
| 622 __ cmp(ecx, FIRST_JS_OBJECT_TYPE); | 621 __ sub(Operand(ecx), Immediate(FIRST_JS_OBJECT_TYPE)); |
| 623 __ j(less, &call_to_object); | 622 __ cmp(ecx, LAST_JS_OBJECT_TYPE - FIRST_JS_OBJECT_TYPE); |
| 624 __ cmp(ecx, LAST_JS_OBJECT_TYPE); | 623 __ j(below_equal, &push_receiver); |
| 625 __ j(less_equal, &push_receiver); | |
| 626 | 624 |
| 627 // Convert the receiver to an object. | 625 // Convert the receiver to an object. |
| 628 __ bind(&call_to_object); | 626 __ bind(&call_to_object); |
| 629 __ push(ebx); | 627 __ push(ebx); |
| 630 __ InvokeBuiltin(Builtins::TO_OBJECT, CALL_FUNCTION); | 628 __ InvokeBuiltin(Builtins::TO_OBJECT, CALL_FUNCTION); |
| 631 __ mov(ebx, Operand(eax)); | 629 __ mov(ebx, Operand(eax)); |
| 632 __ jmp(&push_receiver); | 630 __ jmp(&push_receiver); |
| 633 | 631 |
| 634 // Use the current global receiver object as the receiver. | 632 // Use the current global receiver object as the receiver. |
| 635 __ bind(&use_global_receiver); | 633 __ bind(&use_global_receiver); |
| (...skipping 618 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1254 __ bind(&dont_adapt_arguments); | 1252 __ bind(&dont_adapt_arguments); |
| 1255 __ jmp(Operand(edx)); | 1253 __ jmp(Operand(edx)); |
| 1256 } | 1254 } |
| 1257 | 1255 |
| 1258 | 1256 |
| 1259 #undef __ | 1257 #undef __ |
| 1260 | 1258 |
| 1261 } } // namespace v8::internal | 1259 } } // namespace v8::internal |
| 1262 | 1260 |
| 1263 #endif // V8_TARGET_ARCH_IA32 | 1261 #endif // V8_TARGET_ARCH_IA32 |
| OLD | NEW |