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

Side by Side Diff: src/code-stubs-hydrogen.cc

Issue 1878063004: Revert of Visit the Optimized Code Map on first call rather than closure creation. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Created 4 years, 8 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
« no previous file with comments | « src/code-stubs.cc ('k') | src/compiler.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
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 #include "src/code-stubs.h" 5 #include "src/code-stubs.h"
6 6
7 #include "src/bailout-reason.h" 7 #include "src/bailout-reason.h"
8 #include "src/crankshaft/hydrogen.h" 8 #include "src/crankshaft/hydrogen.h"
9 #include "src/crankshaft/lithium.h" 9 #include "src/crankshaft/lithium.h"
10 #include "src/field-index.h" 10 #include "src/field-index.h"
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after
90 HValue* UnmappedCase(HValue* elements, HValue* key, HValue* value); 90 HValue* UnmappedCase(HValue* elements, HValue* key, HValue* value);
91 HValue* EmitKeyedSloppyArguments(HValue* receiver, HValue* key, 91 HValue* EmitKeyedSloppyArguments(HValue* receiver, HValue* key,
92 HValue* value); 92 HValue* value);
93 93
94 HValue* BuildArrayConstructor(ElementsKind kind, 94 HValue* BuildArrayConstructor(ElementsKind kind,
95 AllocationSiteOverrideMode override_mode, 95 AllocationSiteOverrideMode override_mode,
96 ArgumentClass argument_class); 96 ArgumentClass argument_class);
97 HValue* BuildInternalArrayConstructor(ElementsKind kind, 97 HValue* BuildInternalArrayConstructor(ElementsKind kind,
98 ArgumentClass argument_class); 98 ArgumentClass argument_class);
99 99
100 // BuildCheckAndInstallOptimizedCode emits code to install the optimized
101 // function found in the optimized code map at map_index in js_function, if
102 // the function at map_index matches the given native_context. Builder is
103 // left in the "Then()" state after the install.
104 void BuildCheckAndInstallOptimizedCode(HValue* js_function,
105 HValue* native_context,
106 IfBuilder* builder,
107 HValue* optimized_map,
108 HValue* map_index);
109 void BuildInstallOptimizedCode(HValue* js_function, HValue* native_context,
110 HValue* code_object, HValue* literals);
111 void BuildInstallCode(HValue* js_function, HValue* shared_info);
112
113 HInstruction* LoadFromOptimizedCodeMap(HValue* optimized_map,
114 HValue* iterator,
115 int field_offset);
116 void BuildInstallFromOptimizedCodeMap(HValue* js_function,
117 HValue* shared_info,
118 HValue* native_context);
119
100 HValue* BuildToString(HValue* input, bool convert); 120 HValue* BuildToString(HValue* input, bool convert);
101 HValue* BuildToPrimitive(HValue* input, HValue* input_map); 121 HValue* BuildToPrimitive(HValue* input, HValue* input_map);
102 122
103 private: 123 private:
104 HValue* BuildArraySingleArgumentConstructor(JSArrayBuilder* builder); 124 HValue* BuildArraySingleArgumentConstructor(JSArrayBuilder* builder);
105 HValue* BuildArrayNArgumentsConstructor(JSArrayBuilder* builder, 125 HValue* BuildArrayNArgumentsConstructor(JSArrayBuilder* builder,
106 ElementsKind kind); 126 ElementsKind kind);
107 127
108 base::SmartArrayPointer<HParameter*> parameters_; 128 base::SmartArrayPointer<HParameter*> parameters_;
109 HValue* arguments_length_; 129 HValue* arguments_length_;
(...skipping 1876 matching lines...) Expand 10 before | Expand all | Expand 10 after
1986 template <> 2006 template <>
1987 HValue* CodeStubGraphBuilder<ToObjectStub>::BuildCodeStub() { 2007 HValue* CodeStubGraphBuilder<ToObjectStub>::BuildCodeStub() {
1988 HValue* receiver = GetParameter(TypeConversionDescriptor::kArgumentIndex); 2008 HValue* receiver = GetParameter(TypeConversionDescriptor::kArgumentIndex);
1989 return BuildToObject(receiver); 2009 return BuildToObject(receiver);
1990 } 2010 }
1991 2011
1992 2012
1993 Handle<Code> ToObjectStub::GenerateCode() { return DoGenerateCode(this); } 2013 Handle<Code> ToObjectStub::GenerateCode() { return DoGenerateCode(this); }
1994 2014
1995 2015
2016 void CodeStubGraphBuilderBase::BuildCheckAndInstallOptimizedCode(
2017 HValue* js_function,
2018 HValue* native_context,
2019 IfBuilder* builder,
2020 HValue* optimized_map,
2021 HValue* map_index) {
2022 HValue* osr_ast_id_none = Add<HConstant>(BailoutId::None().ToInt());
2023 HValue* context_slot = LoadFromOptimizedCodeMap(
2024 optimized_map, map_index, SharedFunctionInfo::kContextOffset);
2025 context_slot = Add<HLoadNamedField>(context_slot, nullptr,
2026 HObjectAccess::ForWeakCellValue());
2027 HValue* osr_ast_slot = LoadFromOptimizedCodeMap(
2028 optimized_map, map_index, SharedFunctionInfo::kOsrAstIdOffset);
2029 HValue* code_object = LoadFromOptimizedCodeMap(
2030 optimized_map, map_index, SharedFunctionInfo::kCachedCodeOffset);
2031 code_object = Add<HLoadNamedField>(code_object, nullptr,
2032 HObjectAccess::ForWeakCellValue());
2033 builder->If<HCompareObjectEqAndBranch>(native_context,
2034 context_slot);
2035 builder->AndIf<HCompareObjectEqAndBranch>(osr_ast_slot, osr_ast_id_none);
2036 builder->And();
2037 builder->IfNot<HCompareObjectEqAndBranch>(code_object,
2038 graph()->GetConstant0());
2039 builder->Then();
2040 HValue* literals = LoadFromOptimizedCodeMap(optimized_map,
2041 map_index, SharedFunctionInfo::kLiteralsOffset);
2042 literals = Add<HLoadNamedField>(literals, nullptr,
2043 HObjectAccess::ForWeakCellValue());
2044 IfBuilder maybe_deopt(this);
2045 maybe_deopt.If<HCompareObjectEqAndBranch>(literals, graph()->GetConstant0());
2046 maybe_deopt.ThenDeopt(Deoptimizer::kLiteralsWereDisposed);
2047 maybe_deopt.End();
2048
2049 BuildInstallOptimizedCode(js_function, native_context, code_object, literals);
2050
2051 // The builder continues in the "then" after this function.
2052 }
2053
2054
2055 void CodeStubGraphBuilderBase::BuildInstallOptimizedCode(HValue* js_function,
2056 HValue* native_context,
2057 HValue* code_object,
2058 HValue* literals) {
2059 Counters* counters = isolate()->counters();
2060 AddIncrementCounter(counters->fast_new_closure_install_optimized());
2061
2062 // TODO(fschneider): Idea: store proper code pointers in the optimized code
2063 // map and either unmangle them on marking or do nothing as the whole map is
2064 // discarded on major GC anyway.
2065 Add<HStoreCodeEntry>(js_function, code_object);
2066 Add<HStoreNamedField>(js_function, HObjectAccess::ForLiteralsPointer(),
2067 literals);
2068
2069 // Now link a function into a list of optimized functions.
2070 HValue* optimized_functions_list = Add<HLoadNamedField>(
2071 native_context, nullptr,
2072 HObjectAccess::ForContextSlot(Context::OPTIMIZED_FUNCTIONS_LIST));
2073 Add<HStoreNamedField>(js_function,
2074 HObjectAccess::ForNextFunctionLinkPointer(),
2075 optimized_functions_list);
2076
2077 // This store is the only one that should have a write barrier.
2078 Add<HStoreNamedField>(native_context,
2079 HObjectAccess::ForContextSlot(Context::OPTIMIZED_FUNCTIONS_LIST),
2080 js_function);
2081 }
2082
2083
2084 void CodeStubGraphBuilderBase::BuildInstallCode(HValue* js_function,
2085 HValue* shared_info) {
2086 Add<HStoreNamedField>(js_function,
2087 HObjectAccess::ForNextFunctionLinkPointer(),
2088 graph()->GetConstantUndefined());
2089 HValue* code_object = Add<HLoadNamedField>(shared_info, nullptr,
2090 HObjectAccess::ForCodeOffset());
2091 Add<HStoreCodeEntry>(js_function, code_object);
2092 }
2093
2094
2095 HInstruction* CodeStubGraphBuilderBase::LoadFromOptimizedCodeMap(
2096 HValue* optimized_map,
2097 HValue* iterator,
2098 int field_offset) {
2099 // By making sure to express these loads in the form [<hvalue> + constant]
2100 // the keyed load can be hoisted.
2101 DCHECK(field_offset >= 0 && field_offset < SharedFunctionInfo::kEntryLength);
2102 HValue* field_slot = iterator;
2103 if (field_offset > 0) {
2104 HValue* field_offset_value = Add<HConstant>(field_offset);
2105 field_slot = AddUncasted<HAdd>(iterator, field_offset_value);
2106 }
2107 HInstruction* field_entry = Add<HLoadKeyed>(optimized_map, field_slot,
2108 nullptr, nullptr, FAST_ELEMENTS);
2109 return field_entry;
2110 }
2111
2112
2113 void CodeStubGraphBuilderBase::BuildInstallFromOptimizedCodeMap(
2114 HValue* js_function,
2115 HValue* shared_info,
2116 HValue* native_context) {
2117 Counters* counters = isolate()->counters();
2118 Factory* factory = isolate()->factory();
2119 IfBuilder is_optimized(this);
2120 HInstruction* optimized_map = Add<HLoadNamedField>(
2121 shared_info, nullptr, HObjectAccess::ForOptimizedCodeMap());
2122 HValue* null_constant = Add<HConstant>(0);
2123 is_optimized.If<HCompareObjectEqAndBranch>(optimized_map, null_constant);
2124 is_optimized.Then();
2125 {
2126 BuildInstallCode(js_function, shared_info);
2127 }
2128 is_optimized.Else();
2129 {
2130 AddIncrementCounter(counters->fast_new_closure_try_optimized());
2131 // The {optimized_map} points to fixed array of 4-element entries:
2132 // (native context, optimized code, literals, ast-id).
2133 // Iterate through the {optimized_map} backwards. After the loop, if no
2134 // matching optimized code was found, install unoptimized code.
2135 // for(i = map.length() - SharedFunctionInfo::kEntryLength;
2136 // i >= SharedFunctionInfo::kEntriesStart;
2137 // i -= SharedFunctionInfo::kEntryLength) { ... }
2138 HValue* first_entry_index =
2139 Add<HConstant>(SharedFunctionInfo::kEntriesStart);
2140 HValue* shared_function_entry_length =
2141 Add<HConstant>(SharedFunctionInfo::kEntryLength);
2142 LoopBuilder loop_builder(this, context(), LoopBuilder::kPostDecrement,
2143 shared_function_entry_length);
2144 HValue* array_length = Add<HLoadNamedField>(
2145 optimized_map, nullptr, HObjectAccess::ForFixedArrayLength());
2146 HValue* start_pos =
2147 AddUncasted<HSub>(array_length, shared_function_entry_length);
2148 HValue* slot_iterator =
2149 loop_builder.BeginBody(start_pos, first_entry_index, Token::GTE);
2150 {
2151 IfBuilder done_check(this);
2152 BuildCheckAndInstallOptimizedCode(js_function, native_context,
2153 &done_check, optimized_map,
2154 slot_iterator);
2155 // Fall out of the loop
2156 loop_builder.Break();
2157 }
2158 loop_builder.EndBody();
2159
2160 // If {slot_iterator} is less than the first entry index, then we failed to
2161 // find a context-dependent code and try context-independent code next.
2162 IfBuilder no_optimized_code_check(this);
2163 no_optimized_code_check.If<HCompareNumericAndBranch>(
2164 slot_iterator, first_entry_index, Token::LT);
2165 no_optimized_code_check.Then();
2166 {
2167 IfBuilder shared_code_check(this);
2168 HValue* shared_code =
2169 Add<HLoadNamedField>(optimized_map, nullptr,
2170 HObjectAccess::ForOptimizedCodeMapSharedCode());
2171 shared_code = Add<HLoadNamedField>(shared_code, nullptr,
2172 HObjectAccess::ForWeakCellValue());
2173 shared_code_check.IfNot<HCompareObjectEqAndBranch>(
2174 shared_code, graph()->GetConstant0());
2175 shared_code_check.Then();
2176 {
2177 // Store the context-independent optimized code.
2178 HValue* literals = Add<HConstant>(factory->empty_fixed_array());
2179 BuildInstallOptimizedCode(js_function, native_context, shared_code,
2180 literals);
2181 }
2182 shared_code_check.Else();
2183 {
2184 // Store the unoptimized code.
2185 BuildInstallCode(js_function, shared_info);
2186 }
2187 }
2188 }
2189 }
2190
2191
1996 template<> 2192 template<>
1997 HValue* CodeStubGraphBuilder<FastNewClosureStub>::BuildCodeStub() { 2193 HValue* CodeStubGraphBuilder<FastNewClosureStub>::BuildCodeStub() {
1998 Counters* counters = isolate()->counters(); 2194 Counters* counters = isolate()->counters();
1999 Factory* factory = isolate()->factory(); 2195 Factory* factory = isolate()->factory();
2000 HInstruction* empty_fixed_array = 2196 HInstruction* empty_fixed_array =
2001 Add<HConstant>(factory->empty_fixed_array()); 2197 Add<HConstant>(factory->empty_fixed_array());
2002 HValue* shared_info = GetParameter(0); 2198 HValue* shared_info = GetParameter(0);
2003 2199
2004 AddIncrementCounter(counters->fast_new_closure_total()); 2200 AddIncrementCounter(counters->fast_new_closure_total());
2005 2201
(...skipping 19 matching lines...) Expand all
2025 empty_fixed_array); 2221 empty_fixed_array);
2026 Add<HStoreNamedField>(js_function, HObjectAccess::ForLiteralsPointer(), 2222 Add<HStoreNamedField>(js_function, HObjectAccess::ForLiteralsPointer(),
2027 empty_fixed_array); 2223 empty_fixed_array);
2028 Add<HStoreNamedField>(js_function, HObjectAccess::ForPrototypeOrInitialMap(), 2224 Add<HStoreNamedField>(js_function, HObjectAccess::ForPrototypeOrInitialMap(),
2029 graph()->GetConstantHole()); 2225 graph()->GetConstantHole());
2030 Add<HStoreNamedField>( 2226 Add<HStoreNamedField>(
2031 js_function, HObjectAccess::ForSharedFunctionInfoPointer(), shared_info); 2227 js_function, HObjectAccess::ForSharedFunctionInfoPointer(), shared_info);
2032 Add<HStoreNamedField>(js_function, HObjectAccess::ForFunctionContextPointer(), 2228 Add<HStoreNamedField>(js_function, HObjectAccess::ForFunctionContextPointer(),
2033 context()); 2229 context());
2034 2230
2035 Handle<Code> lazy_builtin( 2231 // Initialize the code pointer in the function to be the one found in the
2036 isolate()->builtins()->builtin(Builtins::kCompileLazy)); 2232 // shared function info object. But first check if there is an optimized
2037 HConstant* lazy = Add<HConstant>(lazy_builtin); 2233 // version for our context.
2038 Add<HStoreCodeEntry>(js_function, lazy); 2234 BuildInstallFromOptimizedCodeMap(js_function, shared_info, native_context);
2039 Add<HStoreNamedField>(js_function,
2040 HObjectAccess::ForNextFunctionLinkPointer(),
2041 graph()->GetConstantUndefined());
2042 2235
2043 return js_function; 2236 return js_function;
2044 } 2237 }
2045 2238
2046 2239
2047 Handle<Code> FastNewClosureStub::GenerateCode() { 2240 Handle<Code> FastNewClosureStub::GenerateCode() {
2048 return DoGenerateCode(this); 2241 return DoGenerateCode(this);
2049 } 2242 }
2050 2243
2051 2244
(...skipping 329 matching lines...) Expand 10 before | Expand all | Expand 10 after
2381 return Pop(); 2574 return Pop();
2382 } 2575 }
2383 2576
2384 2577
2385 Handle<Code> KeyedLoadGenericStub::GenerateCode() { 2578 Handle<Code> KeyedLoadGenericStub::GenerateCode() {
2386 return DoGenerateCode(this); 2579 return DoGenerateCode(this);
2387 } 2580 }
2388 2581
2389 } // namespace internal 2582 } // namespace internal
2390 } // namespace v8 2583 } // namespace v8
OLDNEW
« no previous file with comments | « src/code-stubs.cc ('k') | src/compiler.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698