| 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_X64 | 5 #if V8_TARGET_ARCH_X64 | 
| 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 1858 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 1869   __ jmp(&done_no_smi_convert); | 1869   __ jmp(&done_no_smi_convert); | 
| 1870 | 1870 | 
| 1871   __ bind(&done); | 1871   __ bind(&done); | 
| 1872   __ Integer32ToSmi(rdx, rdx); | 1872   __ Integer32ToSmi(rdx, rdx); | 
| 1873 | 1873 | 
| 1874   __ bind(&done_no_smi_convert); | 1874   __ bind(&done_no_smi_convert); | 
| 1875 } | 1875 } | 
| 1876 | 1876 | 
| 1877 | 1877 | 
| 1878 static void EmitContinueIfStrictOrNative(MacroAssembler* masm, Label* cont) { | 1878 static void EmitContinueIfStrictOrNative(MacroAssembler* masm, Label* cont) { | 
| 1879   // ----------- S t a t e ------------- |  | 
| 1880   // -- rdi : the function to call |  | 
| 1881   // -- rdx : the function's shared function info |  | 
| 1882   // ----------------------------------- |  | 
| 1883   // Assume that SharedFunctionInfo is already loaded into rdx. |  | 
| 1884   // Do not transform the receiver for strict mode functions. | 1879   // Do not transform the receiver for strict mode functions. | 
| 1885   __ testb(FieldOperand(rdx, SharedFunctionInfo::kStrictModeByteOffset), | 1880   __ movp(rcx, FieldOperand(rdi, JSFunction::kSharedFunctionInfoOffset)); | 
|  | 1881   __ testb(FieldOperand(rcx, SharedFunctionInfo::kStrictModeByteOffset), | 
| 1886            Immediate(1 << SharedFunctionInfo::kStrictModeBitWithinByte)); | 1882            Immediate(1 << SharedFunctionInfo::kStrictModeBitWithinByte)); | 
| 1887   __ j(not_equal, cont); | 1883   __ j(not_equal, cont); | 
| 1888 | 1884 | 
| 1889   // Do not transform the receiver for natives. | 1885   // Do not transform the receiver for natives. | 
| 1890   __ testb(FieldOperand(rdx, SharedFunctionInfo::kNativeByteOffset), | 1886   // SharedFunctionInfo is already loaded into rcx. | 
|  | 1887   __ testb(FieldOperand(rcx, SharedFunctionInfo::kNativeByteOffset), | 
| 1891            Immediate(1 << SharedFunctionInfo::kNativeBitWithinByte)); | 1888            Immediate(1 << SharedFunctionInfo::kNativeBitWithinByte)); | 
| 1892   __ j(not_equal, cont); | 1889   __ j(not_equal, cont); | 
| 1893 } | 1890 } | 
| 1894 | 1891 | 
| 1895 | 1892 | 
| 1896 static void EmitSlowCase(MacroAssembler* masm, StackArgumentsAccessor* args, | 1893 static void EmitSlowCase(MacroAssembler* masm, StackArgumentsAccessor* args, | 
| 1897                          int argc) { | 1894                          int argc) { | 
| 1898   __ Set(rax, argc); | 1895   __ Set(rax, argc); | 
| 1899   __ Jump(masm->isolate()->builtins()->Call(), RelocInfo::CODE_TARGET); | 1896   __ Jump(masm->isolate()->builtins()->Call(), RelocInfo::CODE_TARGET); | 
| 1900 } | 1897 } | 
| 1901 | 1898 | 
| 1902 | 1899 | 
| 1903 static void EmitWrapCase(MacroAssembler* masm, | 1900 static void EmitWrapCase(MacroAssembler* masm, | 
| 1904                          StackArgumentsAccessor* args, | 1901                          StackArgumentsAccessor* args, | 
| 1905                          Label* cont) { | 1902                          Label* cont) { | 
| 1906   // Wrap the receiver and patch it back onto the stack. | 1903   // Wrap the receiver and patch it back onto the stack. | 
| 1907   { FrameScope frame_scope(masm, StackFrame::INTERNAL); | 1904   { FrameScope frame_scope(masm, StackFrame::INTERNAL); | 
| 1908     __ Push(rdi); | 1905     __ Push(rdi); | 
| 1909     ToObjectStub stub(masm->isolate()); | 1906     ToObjectStub stub(masm->isolate()); | 
| 1910     __ CallStub(&stub); | 1907     __ CallStub(&stub); | 
| 1911     __ Pop(rdi); | 1908     __ Pop(rdi); | 
| 1912   } | 1909   } | 
| 1913   __ movp(args->GetReceiverOperand(), rax); | 1910   __ movp(args->GetReceiverOperand(), rax); | 
| 1914   __ jmp(cont); | 1911   __ jmp(cont); | 
| 1915 } | 1912 } | 
| 1916 | 1913 | 
| 1917 | 1914 | 
| 1918 static void EmitClassConstructorCallCheck(MacroAssembler* masm) { |  | 
| 1919   // ----------- S t a t e ------------- |  | 
| 1920   // -- rdi : the function to call |  | 
| 1921   // -- rdx : the function's shared function info |  | 
| 1922   // ----------------------------------- |  | 
| 1923   // ClassConstructor Check: ES6 section 9.2.1 [[Call]] |  | 
| 1924   Label non_class_constructor; |  | 
| 1925   // Check whether the current function is a classConstructor |  | 
| 1926   __ testb(FieldOperand(rdx, SharedFunctionInfo::kFunctionKindByteOffset), |  | 
| 1927            Immediate(SharedFunctionInfo::kClassConstructorBitsWithinByte)); |  | 
| 1928   __ j(zero, &non_class_constructor, Label::kNear); |  | 
| 1929   // If we call a classConstructor Function throw a TypeError |  | 
| 1930   // indirectly via the CallFunction builtin. |  | 
| 1931   __ Jump(masm->isolate()->builtins()->CallFunction(), RelocInfo::CODE_TARGET); |  | 
| 1932   __ bind(&non_class_constructor); |  | 
| 1933 } |  | 
| 1934 |  | 
| 1935 |  | 
| 1936 static void CallFunctionNoFeedback(MacroAssembler* masm, | 1915 static void CallFunctionNoFeedback(MacroAssembler* masm, | 
| 1937                                    int argc, bool needs_checks, | 1916                                    int argc, bool needs_checks, | 
| 1938                                    bool call_as_method) { | 1917                                    bool call_as_method) { | 
| 1939   // ----------- S t a t e ------------- | 1918   // rdi : the function to call | 
| 1940   // -- rdi : the function to call |  | 
| 1941   // ----------------------------------- |  | 
| 1942 | 1919 | 
| 1943   // wrap_and_call can only be true if we are compiling a monomorphic method. | 1920   // wrap_and_call can only be true if we are compiling a monomorphic method. | 
| 1944   Label slow, wrap, cont; | 1921   Label slow, wrap, cont; | 
| 1945   StackArgumentsAccessor args(rsp, argc); | 1922   StackArgumentsAccessor args(rsp, argc); | 
| 1946 | 1923 | 
| 1947   if (needs_checks) { | 1924   if (needs_checks) { | 
| 1948     // Check that the function really is a JavaScript function. | 1925     // Check that the function really is a JavaScript function. | 
| 1949     __ JumpIfSmi(rdi, &slow); | 1926     __ JumpIfSmi(rdi, &slow); | 
| 1950 | 1927 | 
| 1951     // Goto slow case if we do not have a function. | 1928     // Goto slow case if we do not have a function. | 
| 1952     __ CmpObjectType(rdi, JS_FUNCTION_TYPE, rcx); | 1929     __ CmpObjectType(rdi, JS_FUNCTION_TYPE, rcx); | 
| 1953     __ j(not_equal, &slow); | 1930     __ j(not_equal, &slow); | 
| 1954   } | 1931   } | 
| 1955 | 1932 | 
| 1956   __ movp(rdx, FieldOperand(rdi, JSFunction::kSharedFunctionInfoOffset)); |  | 
| 1957   EmitClassConstructorCallCheck(masm); |  | 
| 1958 |  | 
| 1959   // Fast-case: Just invoke the function. | 1933   // Fast-case: Just invoke the function. | 
| 1960   ParameterCount actual(argc); | 1934   ParameterCount actual(argc); | 
| 1961 | 1935 | 
| 1962   if (call_as_method) { | 1936   if (call_as_method) { | 
| 1963     if (needs_checks) { | 1937     if (needs_checks) { | 
| 1964       EmitContinueIfStrictOrNative(masm, &cont); | 1938       EmitContinueIfStrictOrNative(masm, &cont); | 
| 1965     } | 1939     } | 
| 1966 | 1940 | 
| 1967     // Load the receiver from the stack. | 1941     // Load the receiver from the stack. | 
| 1968     __ movp(rax, args.GetReceiverOperand()); | 1942     __ movp(rax, args.GetReceiverOperand()); | 
| (...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 2066                     Smi::FromInt(CallICNexus::kCallCountIncrement)); | 2040                     Smi::FromInt(CallICNexus::kCallCountIncrement)); | 
| 2067 | 2041 | 
| 2068   __ movp(rbx, rcx); | 2042   __ movp(rbx, rcx); | 
| 2069   __ movp(rdx, rdi); | 2043   __ movp(rdx, rdi); | 
| 2070   ArrayConstructorStub stub(masm->isolate(), arg_count()); | 2044   ArrayConstructorStub stub(masm->isolate(), arg_count()); | 
| 2071   __ TailCallStub(&stub); | 2045   __ TailCallStub(&stub); | 
| 2072 } | 2046 } | 
| 2073 | 2047 | 
| 2074 | 2048 | 
| 2075 void CallICStub::Generate(MacroAssembler* masm) { | 2049 void CallICStub::Generate(MacroAssembler* masm) { | 
| 2076   // ----------- S t a t e ------------- | 2050   // rdi - function | 
| 2077   // -- rdi - function | 2051   // rdx - slot id | 
| 2078   // -- rdx - slot id | 2052   // rbx - vector | 
| 2079   // -- rbx - vector |  | 
| 2080   // ----------------------------------- |  | 
| 2081   Isolate* isolate = masm->isolate(); | 2053   Isolate* isolate = masm->isolate(); | 
| 2082   const int with_types_offset = | 2054   const int with_types_offset = | 
| 2083       FixedArray::OffsetOfElementAt(TypeFeedbackVector::kWithTypesIndex); | 2055       FixedArray::OffsetOfElementAt(TypeFeedbackVector::kWithTypesIndex); | 
| 2084   const int generic_offset = | 2056   const int generic_offset = | 
| 2085       FixedArray::OffsetOfElementAt(TypeFeedbackVector::kGenericCountIndex); | 2057       FixedArray::OffsetOfElementAt(TypeFeedbackVector::kGenericCountIndex); | 
| 2086   Label extra_checks_or_miss, slow_start; | 2058   Label extra_checks_or_miss, slow_start; | 
| 2087   Label slow, wrap, cont; | 2059   Label slow, wrap, cont; | 
| 2088   Label have_js_function; | 2060   Label have_js_function; | 
| 2089   int argc = arg_count(); | 2061   int argc = arg_count(); | 
| 2090   StackArgumentsAccessor args(rsp, argc); | 2062   StackArgumentsAccessor args(rsp, argc); | 
| (...skipping 24 matching lines...) Expand all  Loading... | 
| 2115   // The compare above could have been a SMI/SMI comparison. Guard against this | 2087   // The compare above could have been a SMI/SMI comparison. Guard against this | 
| 2116   // convincing us that we have a monomorphic JSFunction. | 2088   // convincing us that we have a monomorphic JSFunction. | 
| 2117   __ JumpIfSmi(rdi, &extra_checks_or_miss); | 2089   __ JumpIfSmi(rdi, &extra_checks_or_miss); | 
| 2118 | 2090 | 
| 2119   // Increment the call count for monomorphic function calls. | 2091   // Increment the call count for monomorphic function calls. | 
| 2120   __ SmiAddConstant(FieldOperand(rbx, rdx, times_pointer_size, | 2092   __ SmiAddConstant(FieldOperand(rbx, rdx, times_pointer_size, | 
| 2121                                  FixedArray::kHeaderSize + kPointerSize), | 2093                                  FixedArray::kHeaderSize + kPointerSize), | 
| 2122                     Smi::FromInt(CallICNexus::kCallCountIncrement)); | 2094                     Smi::FromInt(CallICNexus::kCallCountIncrement)); | 
| 2123 | 2095 | 
| 2124   __ bind(&have_js_function); | 2096   __ bind(&have_js_function); | 
| 2125 |  | 
| 2126   __ movp(rdx, FieldOperand(rdi, JSFunction::kSharedFunctionInfoOffset)); |  | 
| 2127   EmitClassConstructorCallCheck(masm); |  | 
| 2128 |  | 
| 2129   if (CallAsMethod()) { | 2097   if (CallAsMethod()) { | 
| 2130     EmitContinueIfStrictOrNative(masm, &cont); | 2098     EmitContinueIfStrictOrNative(masm, &cont); | 
| 2131 | 2099 | 
| 2132     // Load the receiver from the stack. | 2100     // Load the receiver from the stack. | 
| 2133     __ movp(rax, args.GetReceiverOperand()); | 2101     __ movp(rax, args.GetReceiverOperand()); | 
| 2134 | 2102 | 
| 2135     __ JumpIfSmi(rax, &wrap); | 2103     __ JumpIfSmi(rax, &wrap); | 
| 2136 | 2104 | 
| 2137     __ CmpObjectType(rax, FIRST_SPEC_OBJECT_TYPE, rcx); | 2105     __ CmpObjectType(rax, FIRST_SPEC_OBJECT_TYPE, rcx); | 
| 2138     __ j(below, &wrap); | 2106     __ j(below, &wrap); | 
| (...skipping 3488 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 5627                            kStackSpace, nullptr, return_value_operand, NULL); | 5595                            kStackSpace, nullptr, return_value_operand, NULL); | 
| 5628 } | 5596 } | 
| 5629 | 5597 | 
| 5630 | 5598 | 
| 5631 #undef __ | 5599 #undef __ | 
| 5632 | 5600 | 
| 5633 }  // namespace internal | 5601 }  // namespace internal | 
| 5634 }  // namespace v8 | 5602 }  // namespace v8 | 
| 5635 | 5603 | 
| 5636 #endif  // V8_TARGET_ARCH_X64 | 5604 #endif  // V8_TARGET_ARCH_X64 | 
| OLD | NEW | 
|---|