OLD | NEW |
---|---|
1 // Copyright 2010 the V8 project authors. All rights reserved. | 1 // Copyright 2010 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 2567 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2578 // Check that the receiver isn't a smi. | 2578 // Check that the receiver isn't a smi. |
2579 __ JumpIfSmi(receiver, miss); | 2579 __ JumpIfSmi(receiver, miss); |
2580 | 2580 |
2581 // Check that the maps haven't changed. | 2581 // Check that the maps haven't changed. |
2582 Register reg = | 2582 Register reg = |
2583 CheckPrototypes(object, receiver, holder, scratch1, | 2583 CheckPrototypes(object, receiver, holder, scratch1, |
2584 scratch2, scratch3, name, miss); | 2584 scratch2, scratch3, name, miss); |
2585 | 2585 |
2586 Handle<AccessorInfo> callback_handle(callback); | 2586 Handle<AccessorInfo> callback_handle(callback); |
2587 | 2587 |
2588 __ EnterInternalFrame(); | 2588 // Insert additional parameters into the stack frame above return address. |
2589 // Push the stack address where the list of arguments ends. | 2589 ASSERT(!scratch2.is(reg)); |
2590 __ movq(scratch2, rsp); | 2590 __ pop(scratch2); // Get return address to place it below. |
2591 __ subq(scratch2, Immediate(2 * kPointerSize)); | 2591 |
2592 __ push(scratch2); | |
2593 __ push(receiver); // receiver | 2592 __ push(receiver); // receiver |
2593 ASSERT(!scratch3.is(reg)); | |
2594 __ movq(scratch3, rsp); | |
2594 __ push(reg); // holder | 2595 __ push(reg); // holder |
2595 if (Heap::InNewSpace(callback_handle->data())) { | 2596 if (Heap::InNewSpace(callback_handle->data())) { |
2596 __ Move(scratch2, callback_handle); | 2597 __ Move(scratch1, callback_handle); |
2597 __ push(FieldOperand(scratch2, AccessorInfo::kDataOffset)); // data | 2598 __ push(FieldOperand(scratch1, AccessorInfo::kDataOffset)); // data |
2598 } else { | 2599 } else { |
2599 __ Push(Handle<Object>(callback_handle->data())); | 2600 __ Push(Handle<Object>(callback_handle->data())); |
2600 } | 2601 } |
2602 __ push(scratch3); | |
2601 __ push(name_reg); // name | 2603 __ push(name_reg); // name |
2602 // Save a pointer to where we pushed the arguments pointer. | 2604 // Save a pointer to where we pushed the arguments pointer. |
2603 // This will be passed as the const AccessorInfo& to the C++ callback. | 2605 // This will be passed as the const AccessorInfo& to the C++ callback. |
2604 | 2606 |
2605 #ifdef _WIN64 | 2607 #ifdef _WIN64 |
2606 // Win64 uses first register--rcx--for returned value. | 2608 // Win64 uses first register--rcx--for returned value. |
2607 Register accessor_info_arg = r8; | 2609 Register accessor_info_arg = r8; |
2608 Register name_arg = rdx; | 2610 Register name_arg = rdx; |
2609 #else | 2611 #else |
2610 Register accessor_info_arg = rdx; // temporary, copied to rsi by the stub. | 2612 Register accessor_info_arg = rsi; |
2611 Register name_arg = rdi; | 2613 Register name_arg = rdi; |
2612 #endif | 2614 #endif |
2613 | 2615 |
2614 __ movq(accessor_info_arg, rsp); | 2616 if (!name_arg.is(scratch2)) { |
antonm
2010/11/13 11:34:46
maybe just require that scratch2 is not rdi? or s
SeRya
2010/11/15 12:09:11
Done.
| |
2615 __ addq(accessor_info_arg, Immediate(4 * kPointerSize)); | 2617 __ movq(name_arg, rsp); |
2616 __ movq(name_arg, rsp); | 2618 __ push(scratch2); // Restore return addresss. |
antonm
2010/11/13 11:34:46
addresss -> address
SeRya
2010/11/15 12:09:11
Done.
| |
2619 } else { | |
2620 __ push(scratch2); // Restore return addresss. | |
antonm
2010/11/13 11:34:46
ditto
SeRya
2010/11/15 12:09:11
Done.
| |
2621 __ lea(name_arg, Operand(rsp, kPointerSize)); | |
2622 } | |
2617 | 2623 |
2618 // Do call through the api. | 2624 // Do call through the api. |
2619 ASSERT_EQ(5, ApiGetterEntryStub::kStackSpace); | |
2620 Address getter_address = v8::ToCData<Address>(callback->getter()); | 2625 Address getter_address = v8::ToCData<Address>(callback->getter()); |
2621 ApiFunction fun(getter_address); | 2626 ApiFunction fun(getter_address); |
2622 ApiGetterEntryStub stub(callback_handle, &fun); | 2627 |
2623 #ifdef _WIN64 | 2628 // 3 elements array for v8::Agruments::values_, handler for name and pointer |
2624 // We need to prepare a slot for result handle on stack and put | 2629 // to the values (it considered as smi in GC). |
2625 // a pointer to it into 1st arg register. | 2630 const int kStackSpace = 5; |
2626 __ push(Immediate(0)); | 2631 const int kApiArgc = 2; |
2627 __ movq(rcx, rsp); | 2632 |
2628 #endif | 2633 __ PrepareCallApiFunction(kStackSpace, kApiArgc); |
2634 | |
2635 // If accessor_info_arg is rsi this is safe point to set it up. | |
antonm
2010/11/13 11:34:46
what do you mean by that? may you be more explici
SeRya
2010/11/15 12:09:11
Done.
| |
2636 __ lea(accessor_info_arg, Operand(name_arg, 1 * kPointerSize)); | |
2637 | |
2629 // Emitting a stub call may try to allocate (if the code is not | 2638 // Emitting a stub call may try to allocate (if the code is not |
2630 // already generated). Do not allow the assembler to perform a | 2639 // already generated). Do not allow the assembler to perform a |
2631 // garbage collection but instead return the allocation failure | 2640 // garbage collection but instead return the allocation failure |
2632 // object. | 2641 // object. |
2633 MaybeObject* result = masm()->TryCallStub(&stub); | 2642 MaybeObject* result = masm()->TryCallApiFunctionAndReturn(&fun); |
2634 if (result->IsFailure()) { | 2643 if (result->IsFailure()) { |
2635 *failure = Failure::cast(result); | 2644 *failure = Failure::cast(result); |
2636 return false; | 2645 return false; |
2637 } | 2646 } |
2638 #ifdef _WIN64 | |
2639 // Discard allocated slot. | |
2640 __ addq(rsp, Immediate(kPointerSize)); | |
2641 #endif | |
2642 __ LeaveInternalFrame(); | |
2643 | |
2644 __ ret(0); | |
2645 | |
2646 return true; | 2647 return true; |
2647 } | 2648 } |
2648 | 2649 |
2649 | 2650 |
2650 Register StubCompiler::CheckPrototypes(JSObject* object, | 2651 Register StubCompiler::CheckPrototypes(JSObject* object, |
2651 Register object_reg, | 2652 Register object_reg, |
2652 JSObject* holder, | 2653 JSObject* holder, |
2653 Register holder_reg, | 2654 Register holder_reg, |
2654 Register scratch1, | 2655 Register scratch1, |
2655 Register scratch2, | 2656 Register scratch2, |
(...skipping 309 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2965 // Return the generated code. | 2966 // Return the generated code. |
2966 return GetCode(); | 2967 return GetCode(); |
2967 } | 2968 } |
2968 | 2969 |
2969 | 2970 |
2970 #undef __ | 2971 #undef __ |
2971 | 2972 |
2972 } } // namespace v8::internal | 2973 } } // namespace v8::internal |
2973 | 2974 |
2974 #endif // V8_TARGET_ARCH_X64 | 2975 #endif // V8_TARGET_ARCH_X64 |
OLD | NEW |