| OLD | NEW |
| 1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 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 4470 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4481 __ Ret(); | 4481 __ Ret(); |
| 4482 | 4482 |
| 4483 __ bind(&slowcase); | 4483 __ bind(&slowcase); |
| 4484 __ TailCallRuntime(Runtime::kRegExpConstructResult, 3, 1); | 4484 __ TailCallRuntime(Runtime::kRegExpConstructResult, 3, 1); |
| 4485 } | 4485 } |
| 4486 | 4486 |
| 4487 | 4487 |
| 4488 void CallFunctionStub::Generate(MacroAssembler* masm) { | 4488 void CallFunctionStub::Generate(MacroAssembler* masm) { |
| 4489 Label slow; | 4489 Label slow; |
| 4490 | 4490 |
| 4491 // If the receiver might be a value (string, number or boolean) check for this | 4491 // The receiver might implicitly be the global object. This is |
| 4492 // and box it if it is. | 4492 // indicated by passing the hole as the receiver to the call |
| 4493 if (ReceiverMightBeValue()) { | 4493 // function stub. |
| 4494 if (ReceiverMightBeImplicit()) { |
| 4495 Label call; |
| 4494 // Get the receiver from the stack. | 4496 // Get the receiver from the stack. |
| 4495 // function, receiver [, arguments] | 4497 // function, receiver [, arguments] |
| 4496 Label receiver_is_value, receiver_is_js_object; | 4498 __ ldr(r4, MemOperand(sp, argc_ * kPointerSize)); |
| 4497 __ ldr(r1, MemOperand(sp, argc_ * kPointerSize)); | 4499 // Call as function is indicated with the hole. |
| 4498 | 4500 __ CompareRoot(r4, Heap::kTheHoleValueRootIndex); |
| 4499 // Check if receiver is a smi (which is a number value). | 4501 __ b(ne, &call); |
| 4500 __ JumpIfSmi(r1, &receiver_is_value); | 4502 // Patch the receiver on the stack with the global receiver object. |
| 4501 | 4503 __ ldr(r1, MemOperand(cp, Context::SlotOffset(Context::GLOBAL_INDEX))); |
| 4502 // Check if the receiver is a valid JS object. | 4504 __ ldr(r1, FieldMemOperand(r1, GlobalObject::kGlobalReceiverOffset)); |
| 4503 __ CompareObjectType(r1, r2, r2, FIRST_JS_OBJECT_TYPE); | 4505 __ str(r1, MemOperand(sp, argc_ * kPointerSize)); |
| 4504 __ b(ge, &receiver_is_js_object); | 4506 __ bind(&call); |
| 4505 | |
| 4506 // Call the runtime to box the value. | |
| 4507 __ bind(&receiver_is_value); | |
| 4508 __ EnterInternalFrame(); | |
| 4509 __ push(r1); | |
| 4510 __ InvokeBuiltin(Builtins::TO_OBJECT, CALL_FUNCTION); | |
| 4511 __ LeaveInternalFrame(); | |
| 4512 __ str(r0, MemOperand(sp, argc_ * kPointerSize)); | |
| 4513 | |
| 4514 __ bind(&receiver_is_js_object); | |
| 4515 } | 4507 } |
| 4516 | 4508 |
| 4517 // Get the function to call from the stack. | 4509 // Get the function to call from the stack. |
| 4518 // function, receiver [, arguments] | 4510 // function, receiver [, arguments] |
| 4519 __ ldr(r1, MemOperand(sp, (argc_ + 1) * kPointerSize)); | 4511 __ ldr(r1, MemOperand(sp, (argc_ + 1) * kPointerSize)); |
| 4520 | 4512 |
| 4521 // Check that the function is really a JavaScript function. | 4513 // Check that the function is really a JavaScript function. |
| 4522 // r1: pushed function (to be verified) | 4514 // r1: pushed function (to be verified) |
| 4523 __ JumpIfSmi(r1, &slow); | 4515 __ JumpIfSmi(r1, &slow); |
| 4524 // Get the map of the function object. | 4516 // Get the map of the function object. |
| 4525 __ CompareObjectType(r1, r2, r2, JS_FUNCTION_TYPE); | 4517 __ CompareObjectType(r1, r2, r2, JS_FUNCTION_TYPE); |
| 4526 __ b(ne, &slow); | 4518 __ b(ne, &slow); |
| 4527 | 4519 |
| 4528 // Fast-case: Invoke the function now. | 4520 // Fast-case: Invoke the function now. |
| 4529 // r1: pushed function | 4521 // r1: pushed function |
| 4530 ParameterCount actual(argc_); | 4522 ParameterCount actual(argc_); |
| 4531 __ InvokeFunction(r1, actual, JUMP_FUNCTION); | 4523 |
| 4524 if (ReceiverMightBeImplicit()) { |
| 4525 Label call_as_function; |
| 4526 __ CompareRoot(r4, Heap::kTheHoleValueRootIndex); |
| 4527 __ b(eq, &call_as_function); |
| 4528 __ InvokeFunction(r1, actual, JUMP_FUNCTION); |
| 4529 __ bind(&call_as_function); |
| 4530 } |
| 4531 __ InvokeFunction(r1, |
| 4532 actual, |
| 4533 JUMP_FUNCTION, |
| 4534 NullCallWrapper(), |
| 4535 CALL_AS_FUNCTION); |
| 4532 | 4536 |
| 4533 // Slow-case: Non-function called. | 4537 // Slow-case: Non-function called. |
| 4534 __ bind(&slow); | 4538 __ bind(&slow); |
| 4535 // CALL_NON_FUNCTION expects the non-function callee as receiver (instead | 4539 // CALL_NON_FUNCTION expects the non-function callee as receiver (instead |
| 4536 // of the original receiver from the call site). | 4540 // of the original receiver from the call site). |
| 4537 __ str(r1, MemOperand(sp, argc_ * kPointerSize)); | 4541 __ str(r1, MemOperand(sp, argc_ * kPointerSize)); |
| 4538 __ mov(r0, Operand(argc_)); // Setup the number of arguments. | 4542 __ mov(r0, Operand(argc_)); // Setup the number of arguments. |
| 4539 __ mov(r2, Operand(0, RelocInfo::NONE)); | 4543 __ mov(r2, Operand(0, RelocInfo::NONE)); |
| 4540 __ GetBuiltinEntry(r3, Builtins::CALL_NON_FUNCTION); | 4544 __ GetBuiltinEntry(r3, Builtins::CALL_NON_FUNCTION); |
| 4541 __ Jump(masm->isolate()->builtins()->ArgumentsAdaptorTrampoline(), | 4545 __ Jump(masm->isolate()->builtins()->ArgumentsAdaptorTrampoline(), |
| (...skipping 1845 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6387 __ mov(result, Operand(0)); | 6391 __ mov(result, Operand(0)); |
| 6388 __ Ret(); | 6392 __ Ret(); |
| 6389 } | 6393 } |
| 6390 | 6394 |
| 6391 | 6395 |
| 6392 #undef __ | 6396 #undef __ |
| 6393 | 6397 |
| 6394 } } // namespace v8::internal | 6398 } } // namespace v8::internal |
| 6395 | 6399 |
| 6396 #endif // V8_TARGET_ARCH_ARM | 6400 #endif // V8_TARGET_ARCH_ARM |
| OLD | NEW |