| OLD | NEW |
| 1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 the V8 project authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #if V8_TARGET_ARCH_ARM64 | 5 #if V8_TARGET_ARCH_ARM64 |
| 6 | 6 |
| 7 #include "src/bootstrapper.h" | 7 #include "src/bootstrapper.h" |
| 8 #include "src/code-stubs.h" | 8 #include "src/code-stubs.h" |
| 9 #include "src/codegen.h" | 9 #include "src/codegen.h" |
| 10 #include "src/ic/handler-compiler.h" | 10 #include "src/ic/handler-compiler.h" |
| (...skipping 2823 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2834 | 2834 |
| 2835 | 2835 |
| 2836 void CallConstructStub::Generate(MacroAssembler* masm) { | 2836 void CallConstructStub::Generate(MacroAssembler* masm) { |
| 2837 ASM_LOCATION("CallConstructStub::Generate"); | 2837 ASM_LOCATION("CallConstructStub::Generate"); |
| 2838 // x0 : number of arguments | 2838 // x0 : number of arguments |
| 2839 // x1 : the function to call | 2839 // x1 : the function to call |
| 2840 // x2 : feedback vector | 2840 // x2 : feedback vector |
| 2841 // x3 : slot in feedback vector (Smi, for RecordCallTarget) | 2841 // x3 : slot in feedback vector (Smi, for RecordCallTarget) |
| 2842 // x4 : original constructor (for IsSuperConstructorCall) | 2842 // x4 : original constructor (for IsSuperConstructorCall) |
| 2843 Register function = x1; | 2843 Register function = x1; |
| 2844 Label slow, non_function_call; | |
| 2845 | 2844 |
| 2845 Label non_function; |
| 2846 // Check that the function is not a smi. | 2846 // Check that the function is not a smi. |
| 2847 __ JumpIfSmi(function, &non_function_call); | 2847 __ JumpIfSmi(function, &non_function); |
| 2848 // Check that the function is a JSFunction. | 2848 // Check that the function is a JSFunction. |
| 2849 Register object_type = x10; | 2849 Register object_type = x10; |
| 2850 __ JumpIfNotObjectType(function, object_type, object_type, JS_FUNCTION_TYPE, | 2850 __ JumpIfNotObjectType(function, object_type, object_type, JS_FUNCTION_TYPE, |
| 2851 &slow); | 2851 &non_function); |
| 2852 | 2852 |
| 2853 if (RecordCallTarget()) { | 2853 if (RecordCallTarget()) { |
| 2854 GenerateRecordCallTarget(masm, x0, function, x2, x3, x4, x5, x11, x12, | 2854 GenerateRecordCallTarget(masm, x0, function, x2, x3, x4, x5, x11, x12, |
| 2855 IsSuperConstructorCall()); | 2855 IsSuperConstructorCall()); |
| 2856 | 2856 |
| 2857 __ Add(x5, x2, Operand::UntagSmiAndScale(x3, kPointerSizeLog2)); | 2857 __ Add(x5, x2, Operand::UntagSmiAndScale(x3, kPointerSizeLog2)); |
| 2858 Label feedback_register_initialized; | 2858 Label feedback_register_initialized; |
| 2859 // Put the AllocationSite from the feedback vector into x2, or undefined. | 2859 // Put the AllocationSite from the feedback vector into x2, or undefined. |
| 2860 __ Ldr(x2, FieldMemOperand(x5, FixedArray::kHeaderSize)); | 2860 __ Ldr(x2, FieldMemOperand(x5, FixedArray::kHeaderSize)); |
| 2861 __ Ldr(x5, FieldMemOperand(x2, AllocationSite::kMapOffset)); | 2861 __ Ldr(x5, FieldMemOperand(x2, AllocationSite::kMapOffset)); |
| 2862 __ JumpIfRoot(x5, Heap::kAllocationSiteMapRootIndex, | 2862 __ JumpIfRoot(x5, Heap::kAllocationSiteMapRootIndex, |
| 2863 &feedback_register_initialized); | 2863 &feedback_register_initialized); |
| 2864 __ LoadRoot(x2, Heap::kUndefinedValueRootIndex); | 2864 __ LoadRoot(x2, Heap::kUndefinedValueRootIndex); |
| 2865 __ bind(&feedback_register_initialized); | 2865 __ bind(&feedback_register_initialized); |
| 2866 | 2866 |
| 2867 __ AssertUndefinedOrAllocationSite(x2, x5); | 2867 __ AssertUndefinedOrAllocationSite(x2, x5); |
| 2868 } | 2868 } |
| 2869 | 2869 |
| 2870 if (IsSuperConstructorCall()) { | 2870 if (IsSuperConstructorCall()) { |
| 2871 __ Mov(x3, x4); | 2871 __ Mov(x3, x4); |
| 2872 } else { | 2872 } else { |
| 2873 __ Mov(x3, function); | 2873 __ Mov(x3, function); |
| 2874 } | 2874 } |
| 2875 | 2875 |
| 2876 // Jump to the function-specific construct stub. | 2876 // Tail call to the function-specific construct stub (still in the caller |
| 2877 Register jump_reg = x4; | 2877 // context at this point). |
| 2878 Register shared_func_info = jump_reg; | 2878 __ Ldr(x4, FieldMemOperand(x1, JSFunction::kSharedFunctionInfoOffset)); |
| 2879 Register cons_stub = jump_reg; | 2879 __ Ldr(x4, FieldMemOperand(x4, SharedFunctionInfo::kConstructStubOffset)); |
| 2880 Register cons_stub_code = jump_reg; | 2880 __ Add(x4, x4, Code::kHeaderSize - kHeapObjectTag); |
| 2881 __ Ldr(shared_func_info, | 2881 __ Br(x4); |
| 2882 FieldMemOperand(function, JSFunction::kSharedFunctionInfoOffset)); | |
| 2883 __ Ldr(cons_stub, | |
| 2884 FieldMemOperand(shared_func_info, | |
| 2885 SharedFunctionInfo::kConstructStubOffset)); | |
| 2886 __ Add(cons_stub_code, cons_stub, Code::kHeaderSize - kHeapObjectTag); | |
| 2887 __ Br(cons_stub_code); | |
| 2888 | 2882 |
| 2889 __ Bind(&slow); | 2883 __ Bind(&non_function); |
| 2890 { | 2884 __ Mov(x3, function); |
| 2891 __ Cmp(object_type, JS_FUNCTION_PROXY_TYPE); | 2885 __ Jump(isolate()->builtins()->Construct(), RelocInfo::CODE_TARGET); |
| 2892 __ B(ne, &non_function_call); | |
| 2893 // TODO(neis): This doesn't match the ES6 spec for [[Construct]] on proxies. | |
| 2894 __ Ldr(x1, FieldMemOperand(x1, JSFunctionProxy::kConstructTrapOffset)); | |
| 2895 __ Jump(isolate()->builtins()->Call(), RelocInfo::CODE_TARGET); | |
| 2896 | |
| 2897 __ Bind(&non_function_call); | |
| 2898 { | |
| 2899 // Determine the delegate for the target (if any). | |
| 2900 FrameScope scope(masm, StackFrame::INTERNAL); | |
| 2901 __ SmiTag(x0); | |
| 2902 __ Push(x0, x1); | |
| 2903 __ CallRuntime(Runtime::kGetConstructorDelegate, 1); | |
| 2904 __ Mov(x1, x0); | |
| 2905 __ Pop(x0); | |
| 2906 __ SmiUntag(x0); | |
| 2907 } | |
| 2908 // The delegate is always a regular function. | |
| 2909 __ AssertFunction(x1); | |
| 2910 __ Jump(masm->isolate()->builtins()->CallFunction(), | |
| 2911 RelocInfo::CODE_TARGET); | |
| 2912 } | |
| 2913 } | 2886 } |
| 2914 | 2887 |
| 2915 | 2888 |
| 2916 static void EmitLoadTypeFeedbackVector(MacroAssembler* masm, Register vector) { | 2889 static void EmitLoadTypeFeedbackVector(MacroAssembler* masm, Register vector) { |
| 2917 __ Ldr(vector, MemOperand(fp, JavaScriptFrameConstants::kFunctionOffset)); | 2890 __ Ldr(vector, MemOperand(fp, JavaScriptFrameConstants::kFunctionOffset)); |
| 2918 __ Ldr(vector, FieldMemOperand(vector, | 2891 __ Ldr(vector, FieldMemOperand(vector, |
| 2919 JSFunction::kSharedFunctionInfoOffset)); | 2892 JSFunction::kSharedFunctionInfoOffset)); |
| 2920 __ Ldr(vector, FieldMemOperand(vector, | 2893 __ Ldr(vector, FieldMemOperand(vector, |
| 2921 SharedFunctionInfo::kFeedbackVectorOffset)); | 2894 SharedFunctionInfo::kFeedbackVectorOffset)); |
| 2922 } | 2895 } |
| (...skipping 3067 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5990 MemOperand(fp, 6 * kPointerSize), NULL); | 5963 MemOperand(fp, 6 * kPointerSize), NULL); |
| 5991 } | 5964 } |
| 5992 | 5965 |
| 5993 | 5966 |
| 5994 #undef __ | 5967 #undef __ |
| 5995 | 5968 |
| 5996 } // namespace internal | 5969 } // namespace internal |
| 5997 } // namespace v8 | 5970 } // namespace v8 |
| 5998 | 5971 |
| 5999 #endif // V8_TARGET_ARCH_ARM64 | 5972 #endif // V8_TARGET_ARCH_ARM64 |
| OLD | NEW |