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