Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(91)

Side by Side Diff: src/arm/builtins-arm.cc

Issue 1542963002: [runtime] Introduce dedicated JSBoundFunction to represent bound functions. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@FunctionConstructor
Patch Set: arm port. Created 4 years, 12 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 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_ARM 5 #if V8_TARGET_ARCH_ARM
6 6
7 #include "src/codegen.h" 7 #include "src/codegen.h"
8 #include "src/debug/debug.h" 8 #include "src/debug/debug.h"
9 #include "src/deoptimizer.h" 9 #include "src/deoptimizer.h"
10 #include "src/full-codegen/full-codegen.h" 10 #include "src/full-codegen/full-codegen.h"
(...skipping 1876 matching lines...) Expand 10 before | Expand all | Expand 10 after
1887 __ bind(&class_constructor); 1887 __ bind(&class_constructor);
1888 { 1888 {
1889 FrameScope frame(masm, StackFrame::INTERNAL); 1889 FrameScope frame(masm, StackFrame::INTERNAL);
1890 __ push(r1); 1890 __ push(r1);
1891 __ CallRuntime(Runtime::kThrowConstructorNonCallableError, 1); 1891 __ CallRuntime(Runtime::kThrowConstructorNonCallableError, 1);
1892 } 1892 }
1893 } 1893 }
1894 1894
1895 1895
1896 // static 1896 // static
1897 void Builtins::Generate_CallBoundFunction(MacroAssembler* masm) {
1898 // ----------- S t a t e -------------
1899 // -- r0 : the number of arguments (not including the receiver)
1900 // -- r1 : the function to call (checked to be a JSBoundFunction)
1901 // -----------------------------------
1902 __ AssertBoundFunction(r1);
1903
1904 // Patch the receiver to [[BoundThis]].
1905 {
1906 __ ldr(ip, FieldMemOperand(r1, JSBoundFunction::kBoundThisOffset));
1907 __ str(ip, MemOperand(sp, r0, LSL, kPointerSizeLog2));
1908 }
1909
1910 // Load [[BoundArguments]] into r2 and length of that into r4.
1911 __ ldr(r2, FieldMemOperand(r1, JSBoundFunction::kBoundArgumentsOffset));
1912 __ ldr(r4, FieldMemOperand(r2, FixedArray::kLengthOffset));
1913 __ SmiUntag(r4);
1914
1915 // ----------- S t a t e -------------
1916 // -- r0 : the number of arguments (not including the receiver)
1917 // -- r1 : the function to call (checked to be a JSBoundFunction)
1918 // -- r2 : the [[BoundArguments]] (implemented as FixedArray)
1919 // -- r4 : the number of [[BoundArguments]]
1920 // -----------------------------------
1921
1922 // Reserve stack space for the [[BoundArguments]].
1923 {
1924 Label done;
1925 __ sub(sp, sp, Operand(r4, LSL, kPointerSizeLog2));
1926 // Check the stack for overflow. We are not trying to catch interruptions
1927 // (i.e. debug break and preemption) here, so check the "real stack limit".
1928 __ CompareRoot(sp, Heap::kRealStackLimitRootIndex);
1929 __ b(gt, &done); // Signed comparison.
1930 // Restore the stack pointer.
1931 __ add(sp, sp, Operand(r4, LSL, kPointerSizeLog2));
1932 {
1933 FrameScope scope(masm, StackFrame::MANUAL);
1934 __ EnterFrame(StackFrame::INTERNAL);
1935 __ CallRuntime(Runtime::kThrowStackOverflow, 0);
1936 }
1937 __ bind(&done);
1938 }
1939
1940 // Relocate arguments down the stack.
1941 {
1942 Label loop, done_loop;
1943 __ mov(r5, Operand(0));
1944 __ bind(&loop);
1945 __ cmp(r5, r0);
1946 __ b(gt, &done_loop);
1947 __ ldr(ip, MemOperand(sp, r4, LSL, kPointerSizeLog2));
1948 __ str(ip, MemOperand(sp, r5, LSL, kPointerSizeLog2));
1949 __ add(r4, r4, Operand(1));
1950 __ add(r5, r5, Operand(1));
1951 __ b(&loop);
1952 __ bind(&done_loop);
1953 }
1954
1955 // Copy [[BoundArguments]] to the stack (below the arguments).
1956 {
1957 Label loop, done_loop;
1958 __ ldr(r4, FieldMemOperand(r2, FixedArray::kLengthOffset));
1959 __ SmiUntag(r4);
1960 __ add(r2, r2, Operand(FixedArray::kHeaderSize - kHeapObjectTag));
1961 __ bind(&loop);
1962 __ sub(r4, r4, Operand(1), SetCC);
1963 __ b(lt, &done_loop);
1964 __ ldr(ip, MemOperand(r2, r4, LSL, kPointerSizeLog2));
1965 __ str(ip, MemOperand(sp, r0, LSL, kPointerSizeLog2));
1966 __ add(r0, r0, Operand(1));
1967 __ b(&loop);
1968 __ bind(&done_loop);
1969 }
1970
1971 // Call the [[BoundTargetFunction]] via the Call builtin.
1972 __ ldr(r1, FieldMemOperand(r1, JSBoundFunction::kBoundTargetFunctionOffset));
1973 __ mov(ip, Operand(ExternalReference(Builtins::kCall_ReceiverIsAny,
1974 masm->isolate())));
1975 __ ldr(ip, MemOperand(ip));
1976 __ add(pc, ip, Operand(Code::kHeaderSize - kHeapObjectTag));
1977 }
1978
1979
1980 // static
1897 void Builtins::Generate_Call(MacroAssembler* masm, ConvertReceiverMode mode) { 1981 void Builtins::Generate_Call(MacroAssembler* masm, ConvertReceiverMode mode) {
1898 // ----------- S t a t e ------------- 1982 // ----------- S t a t e -------------
1899 // -- r0 : the number of arguments (not including the receiver) 1983 // -- r0 : the number of arguments (not including the receiver)
1900 // -- r1 : the target to call (can be any Object). 1984 // -- r1 : the target to call (can be any Object).
1901 // ----------------------------------- 1985 // -----------------------------------
1902 1986
1903 Label non_callable, non_function, non_smi; 1987 Label non_callable, non_function, non_smi;
1904 __ JumpIfSmi(r1, &non_callable); 1988 __ JumpIfSmi(r1, &non_callable);
1905 __ bind(&non_smi); 1989 __ bind(&non_smi);
1906 __ CompareObjectType(r1, r4, r5, JS_FUNCTION_TYPE); 1990 __ CompareObjectType(r1, r4, r5, JS_FUNCTION_TYPE);
1907 __ Jump(masm->isolate()->builtins()->CallFunction(mode), 1991 __ Jump(masm->isolate()->builtins()->CallFunction(mode),
1908 RelocInfo::CODE_TARGET, eq); 1992 RelocInfo::CODE_TARGET, eq);
1993 __ cmp(r5, Operand(JS_BOUND_FUNCTION_TYPE));
1994 __ Jump(masm->isolate()->builtins()->CallBoundFunction(),
1995 RelocInfo::CODE_TARGET, eq);
1909 __ cmp(r5, Operand(JS_PROXY_TYPE)); 1996 __ cmp(r5, Operand(JS_PROXY_TYPE));
1910 __ b(ne, &non_function); 1997 __ b(ne, &non_function);
1911 1998
1912 // 1. Runtime fallback for Proxy [[Call]]. 1999 // 1. Runtime fallback for Proxy [[Call]].
1913 __ Push(r1); 2000 __ Push(r1);
1914 // Increase the arguments size to include the pushed function and the 2001 // Increase the arguments size to include the pushed function and the
1915 // existing receiver on the stack. 2002 // existing receiver on the stack.
1916 __ add(r0, r0, Operand(2)); 2003 __ add(r0, r0, Operand(2));
1917 // Tail-call to the runtime. 2004 // Tail-call to the runtime.
1918 __ JumpToExternalReference( 2005 __ JumpToExternalReference(
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
1958 2045
1959 // Tail call to the function-specific construct stub (still in the caller 2046 // Tail call to the function-specific construct stub (still in the caller
1960 // context at this point). 2047 // context at this point).
1961 __ ldr(r4, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset)); 2048 __ ldr(r4, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset));
1962 __ ldr(r4, FieldMemOperand(r4, SharedFunctionInfo::kConstructStubOffset)); 2049 __ ldr(r4, FieldMemOperand(r4, SharedFunctionInfo::kConstructStubOffset));
1963 __ add(pc, r4, Operand(Code::kHeaderSize - kHeapObjectTag)); 2050 __ add(pc, r4, Operand(Code::kHeaderSize - kHeapObjectTag));
1964 } 2051 }
1965 2052
1966 2053
1967 // static 2054 // static
2055 void Builtins::Generate_ConstructBoundFunction(MacroAssembler* masm) {
2056 // ----------- S t a t e -------------
2057 // -- r0 : the number of arguments (not including the receiver)
2058 // -- r1 : the function to call (checked to be a JSBoundFunction)
2059 // -- r3 : the new target (checked to be a constructor)
2060 // -----------------------------------
2061 __ AssertBoundFunction(r1);
2062
2063 // Load [[BoundArguments]] into r2 and length of that into r4.
2064 __ ldr(r2, FieldMemOperand(r1, JSBoundFunction::kBoundArgumentsOffset));
2065 __ ldr(r4, FieldMemOperand(r2, FixedArray::kLengthOffset));
2066 __ SmiUntag(r4);
2067
2068 // ----------- S t a t e -------------
2069 // -- r0 : the number of arguments (not including the receiver)
2070 // -- r1 : the function to call (checked to be a JSBoundFunction)
2071 // -- r2 : the [[BoundArguments]] (implemented as FixedArray)
2072 // -- r3 : the new target (checked to be a constructor)
2073 // -- r4 : the number of [[BoundArguments]]
2074 // -----------------------------------
2075
2076 // Reserve stack space for the [[BoundArguments]].
2077 {
2078 Label done;
2079 __ sub(sp, sp, Operand(r4, LSL, kPointerSizeLog2));
2080 // Check the stack for overflow. We are not trying to catch interruptions
2081 // (i.e. debug break and preemption) here, so check the "real stack limit".
2082 __ CompareRoot(sp, Heap::kRealStackLimitRootIndex);
2083 __ b(gt, &done); // Signed comparison.
2084 // Restore the stack pointer.
2085 __ add(sp, sp, Operand(r4, LSL, kPointerSizeLog2));
2086 {
2087 FrameScope scope(masm, StackFrame::MANUAL);
2088 __ EnterFrame(StackFrame::INTERNAL);
2089 __ CallRuntime(Runtime::kThrowStackOverflow, 0);
2090 }
2091 __ bind(&done);
2092 }
2093
2094 // Relocate arguments down the stack.
2095 {
2096 Label loop, done_loop;
2097 __ mov(r5, Operand(0));
2098 __ bind(&loop);
2099 __ cmp(r5, r0);
2100 __ b(ge, &done_loop);
2101 __ ldr(ip, MemOperand(sp, r4, LSL, kPointerSizeLog2));
2102 __ str(ip, MemOperand(sp, r5, LSL, kPointerSizeLog2));
2103 __ add(r4, r4, Operand(1));
2104 __ add(r5, r5, Operand(1));
2105 __ b(&loop);
2106 __ bind(&done_loop);
2107 }
2108
2109 // Copy [[BoundArguments]] to the stack (below the arguments).
2110 {
2111 Label loop, done_loop;
2112 __ ldr(r4, FieldMemOperand(r2, FixedArray::kLengthOffset));
2113 __ SmiUntag(r4);
2114 __ add(r2, r2, Operand(FixedArray::kHeaderSize - kHeapObjectTag));
2115 __ bind(&loop);
2116 __ sub(r4, r4, Operand(1), SetCC);
2117 __ b(lt, &done_loop);
2118 __ ldr(ip, MemOperand(r2, r4, LSL, kPointerSizeLog2));
2119 __ str(ip, MemOperand(sp, r0, LSL, kPointerSizeLog2));
2120 __ add(r0, r0, Operand(1));
2121 __ b(&loop);
2122 __ bind(&done_loop);
2123 }
2124
2125 // Patch new.target to [[BoundTargetFunction]] if new.target equals target.
2126 {
2127 __ cmp(r1, r3);
2128 __ ldr(r3, FieldMemOperand(r1, JSBoundFunction::kBoundTargetFunctionOffset),
2129 eq);
2130 }
2131
2132 // Construct the [[BoundTargetFunction]] via the Construct builtin.
2133 __ ldr(r1, FieldMemOperand(r1, JSBoundFunction::kBoundTargetFunctionOffset));
2134 __ mov(ip, Operand(ExternalReference(Builtins::kConstruct, masm->isolate())));
2135 __ ldr(ip, MemOperand(ip));
2136 __ add(pc, ip, Operand(Code::kHeaderSize - kHeapObjectTag));
2137 }
2138
2139
2140 // static
1968 void Builtins::Generate_ConstructProxy(MacroAssembler* masm) { 2141 void Builtins::Generate_ConstructProxy(MacroAssembler* masm) {
1969 // ----------- S t a t e ------------- 2142 // ----------- S t a t e -------------
1970 // -- r0 : the number of arguments (not including the receiver) 2143 // -- r0 : the number of arguments (not including the receiver)
1971 // -- r1 : the constructor to call (checked to be a JSProxy) 2144 // -- r1 : the constructor to call (checked to be a JSProxy)
1972 // -- r3 : the new target (either the same as the constructor or 2145 // -- r3 : the new target (either the same as the constructor or
1973 // the JSFunction on which new was invoked initially) 2146 // the JSFunction on which new was invoked initially)
1974 // ----------------------------------- 2147 // -----------------------------------
1975 2148
1976 // Call into the Runtime for Proxy [[Construct]]. 2149 // Call into the Runtime for Proxy [[Construct]].
1977 __ Push(r1); 2150 __ Push(r1);
(...skipping 22 matching lines...) Expand all
2000 // Dispatch based on instance type. 2173 // Dispatch based on instance type.
2001 __ CompareObjectType(r1, r4, r5, JS_FUNCTION_TYPE); 2174 __ CompareObjectType(r1, r4, r5, JS_FUNCTION_TYPE);
2002 __ Jump(masm->isolate()->builtins()->ConstructFunction(), 2175 __ Jump(masm->isolate()->builtins()->ConstructFunction(),
2003 RelocInfo::CODE_TARGET, eq); 2176 RelocInfo::CODE_TARGET, eq);
2004 2177
2005 // Check if target has a [[Construct]] internal method. 2178 // Check if target has a [[Construct]] internal method.
2006 __ ldrb(r2, FieldMemOperand(r4, Map::kBitFieldOffset)); 2179 __ ldrb(r2, FieldMemOperand(r4, Map::kBitFieldOffset));
2007 __ tst(r2, Operand(1 << Map::kIsConstructor)); 2180 __ tst(r2, Operand(1 << Map::kIsConstructor));
2008 __ b(eq, &non_constructor); 2181 __ b(eq, &non_constructor);
2009 2182
2183 // Only dispatch to bound functions after checking whether they are
2184 // constructors.
2185 __ cmp(r5, Operand(JS_BOUND_FUNCTION_TYPE));
2186 __ Jump(masm->isolate()->builtins()->ConstructBoundFunction(),
2187 RelocInfo::CODE_TARGET, eq);
2188
2010 // Only dispatch to proxies after checking whether they are constructors. 2189 // Only dispatch to proxies after checking whether they are constructors.
2011 __ cmp(r5, Operand(JS_PROXY_TYPE)); 2190 __ cmp(r5, Operand(JS_PROXY_TYPE));
2012 __ Jump(masm->isolate()->builtins()->ConstructProxy(), RelocInfo::CODE_TARGET, 2191 __ Jump(masm->isolate()->builtins()->ConstructProxy(), RelocInfo::CODE_TARGET,
2013 eq); 2192 eq);
2014 2193
2015 // Called Construct on an exotic Object with a [[Construct]] internal method. 2194 // Called Construct on an exotic Object with a [[Construct]] internal method.
2016 { 2195 {
2017 // Overwrite the original receiver with the (original) target. 2196 // Overwrite the original receiver with the (original) target.
2018 __ str(r1, MemOperand(sp, r0, LSL, kPointerSizeLog2)); 2197 __ str(r1, MemOperand(sp, r0, LSL, kPointerSizeLog2));
2019 // Let the "call_as_constructor_delegate" take care of the rest. 2198 // Let the "call_as_constructor_delegate" take care of the rest.
(...skipping 155 matching lines...) Expand 10 before | Expand all | Expand 10 after
2175 } 2354 }
2176 } 2355 }
2177 2356
2178 2357
2179 #undef __ 2358 #undef __
2180 2359
2181 } // namespace internal 2360 } // namespace internal
2182 } // namespace v8 2361 } // namespace v8
2183 2362
2184 #endif // V8_TARGET_ARCH_ARM 2363 #endif // V8_TARGET_ARCH_ARM
OLDNEW
« no previous file with comments | « src/api-natives.cc ('k') | src/arm/code-stubs-arm.cc » ('j') | src/objects-debug.cc » ('J')

Powered by Google App Engine
This is Rietveld 408576698