OLD | NEW |
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/runtime-profiler.h" | 5 #include "src/runtime-profiler.h" |
6 | 6 |
7 #include "src/assembler.h" | 7 #include "src/assembler.h" |
8 #include "src/base/platform/platform.h" | 8 #include "src/base/platform/platform.h" |
9 #include "src/bootstrapper.h" | 9 #include "src/bootstrapper.h" |
10 #include "src/code-stubs.h" | 10 #include "src/code-stubs.h" |
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
48 static const int kOSRCodeSizeAllowancePerTick = | 48 static const int kOSRCodeSizeAllowancePerTick = |
49 4 * FullCodeGenerator::kCodeSizeMultiplier; | 49 4 * FullCodeGenerator::kCodeSizeMultiplier; |
50 static const int kOSRCodeSizeAllowancePerTickIgnition = | 50 static const int kOSRCodeSizeAllowancePerTickIgnition = |
51 4 * interpreter::Interpreter::kCodeSizeMultiplier; | 51 4 * interpreter::Interpreter::kCodeSizeMultiplier; |
52 | 52 |
53 // Maximum size in bytes of generated code for a function to be optimized | 53 // Maximum size in bytes of generated code for a function to be optimized |
54 // the very first time it is seen on the stack. | 54 // the very first time it is seen on the stack. |
55 static const int kMaxSizeEarlyOpt = | 55 static const int kMaxSizeEarlyOpt = |
56 5 * FullCodeGenerator::kCodeSizeMultiplier; | 56 5 * FullCodeGenerator::kCodeSizeMultiplier; |
57 | 57 |
| 58 #define OPTIMIZATION_REASON_LIST(V) \ |
| 59 V(DoNotOptimize, "do not optimize") \ |
| 60 V(HotAndStable, "hot and stable") \ |
| 61 V(HotEnoughForBaseline, "hot enough for baseline") \ |
| 62 V(HotWithoutMuchTypeInfo, "not much type info but very hot") \ |
| 63 V(SmallFunction, "small function") |
| 64 |
| 65 enum class OptimizationReason : uint8_t { |
| 66 #define OPTIMIZATION_REASON_CONSTANTS(Constant, message) k##Constant, |
| 67 OPTIMIZATION_REASON_LIST(OPTIMIZATION_REASON_CONSTANTS) |
| 68 #undef OPTIMIZATION_REASON_CONSTANTS |
| 69 }; |
| 70 |
| 71 char const* OptimizationReasonToString(OptimizationReason reason) { |
| 72 static char const* reasons[] = { |
| 73 #define OPTIMIZATION_REASON_TEXTS(Constant, message) message, |
| 74 OPTIMIZATION_REASON_LIST(OPTIMIZATION_REASON_TEXTS) |
| 75 #undef OPTIMIZATION_REASON_TEXTS |
| 76 }; |
| 77 size_t const index = static_cast<size_t>(reason); |
| 78 DCHECK_LT(index, arraysize(reasons)); |
| 79 return reasons[index]; |
| 80 } |
| 81 |
| 82 std::ostream& operator<<(std::ostream& os, OptimizationReason reason) { |
| 83 return os << OptimizationReasonToString(reason); |
| 84 } |
58 | 85 |
59 RuntimeProfiler::RuntimeProfiler(Isolate* isolate) | 86 RuntimeProfiler::RuntimeProfiler(Isolate* isolate) |
60 : isolate_(isolate), | 87 : isolate_(isolate), |
61 any_ic_changed_(false) { | 88 any_ic_changed_(false) { |
62 } | 89 } |
63 | 90 |
64 static void GetICCounts(JSFunction* function, int* ic_with_type_info_count, | 91 static void GetICCounts(JSFunction* function, int* ic_with_type_info_count, |
65 int* ic_generic_count, int* ic_total_count, | 92 int* ic_generic_count, int* ic_total_count, |
66 int* type_info_percentage, int* generic_percentage) { | 93 int* type_info_percentage, int* generic_percentage) { |
67 *ic_total_count = 0; | 94 *ic_total_count = 0; |
68 *ic_generic_count = 0; | 95 *ic_generic_count = 0; |
69 *ic_with_type_info_count = 0; | 96 *ic_with_type_info_count = 0; |
70 if (function->code()->kind() == Code::FUNCTION) { | 97 if (function->code()->kind() == Code::FUNCTION) { |
71 Code* shared_code = function->shared()->code(); | 98 Code* shared_code = function->shared()->code(); |
72 Object* raw_info = shared_code->type_feedback_info(); | 99 Object* raw_info = shared_code->type_feedback_info(); |
73 if (raw_info->IsTypeFeedbackInfo()) { | 100 if (raw_info->IsTypeFeedbackInfo()) { |
74 TypeFeedbackInfo* info = TypeFeedbackInfo::cast(raw_info); | 101 TypeFeedbackInfo* info = TypeFeedbackInfo::cast(raw_info); |
75 *ic_with_type_info_count = info->ic_with_type_info_count(); | 102 *ic_with_type_info_count = info->ic_with_type_info_count(); |
76 *ic_generic_count = info->ic_generic_count(); | 103 *ic_generic_count = info->ic_generic_count(); |
77 *ic_total_count = info->ic_total_count(); | 104 *ic_total_count = info->ic_total_count(); |
78 } | 105 } |
79 } | 106 } |
80 | 107 |
81 // Harvest vector-ics as well | 108 // Harvest vector-ics as well |
82 TypeFeedbackVector* vector = function->feedback_vector(); | 109 TypeFeedbackVector* vector = function->feedback_vector(); |
83 int with = 0, gen = 0; | 110 int with = 0, gen = 0, type_vector_ic_count = 0; |
84 const bool is_interpreted = | 111 const bool is_interpreted = |
85 function->shared()->code()->is_interpreter_trampoline_builtin(); | 112 function->shared()->code()->is_interpreter_trampoline_builtin(); |
86 | 113 |
87 vector->ComputeCounts(&with, &gen, is_interpreted); | 114 vector->ComputeCounts(&with, &gen, &type_vector_ic_count, is_interpreted); |
| 115 if (is_interpreted) { |
| 116 DCHECK_EQ(*ic_total_count, 0); |
| 117 *ic_total_count = type_vector_ic_count; |
| 118 } |
88 *ic_with_type_info_count += with; | 119 *ic_with_type_info_count += with; |
89 *ic_generic_count += gen; | 120 *ic_generic_count += gen; |
90 | 121 |
91 if (*ic_total_count > 0) { | 122 if (*ic_total_count > 0) { |
92 *type_info_percentage = 100 * *ic_with_type_info_count / *ic_total_count; | 123 *type_info_percentage = 100 * *ic_with_type_info_count / *ic_total_count; |
93 *generic_percentage = 100 * *ic_generic_count / *ic_total_count; | 124 *generic_percentage = 100 * *ic_generic_count / *ic_total_count; |
94 } else { | 125 } else { |
95 *type_info_percentage = 100; // Compared against lower bound. | 126 *type_info_percentage = 100; // Compared against lower bound. |
96 *generic_percentage = 0; // Compared against upper bound. | 127 *generic_percentage = 0; // Compared against upper bound. |
97 } | 128 } |
(...skipping 11 matching lines...) Expand all Loading... |
109 GetICCounts(function, &typeinfo, &generic, &total, &type_percentage, | 140 GetICCounts(function, &typeinfo, &generic, &total, &type_percentage, |
110 &generic_percentage); | 141 &generic_percentage); |
111 PrintF(", ICs with typeinfo: %d/%d (%d%%)", typeinfo, total, | 142 PrintF(", ICs with typeinfo: %d/%d (%d%%)", typeinfo, total, |
112 type_percentage); | 143 type_percentage); |
113 PrintF(", generic ICs: %d/%d (%d%%)", generic, total, generic_percentage); | 144 PrintF(", generic ICs: %d/%d (%d%%)", generic, total, generic_percentage); |
114 } | 145 } |
115 PrintF("]\n"); | 146 PrintF("]\n"); |
116 } | 147 } |
117 } | 148 } |
118 | 149 |
119 void RuntimeProfiler::Optimize(JSFunction* function, const char* reason) { | 150 void RuntimeProfiler::Optimize(JSFunction* function, |
120 TraceRecompile(function, reason, "optimized"); | 151 OptimizationReason reason) { |
| 152 DCHECK_NE(reason, OptimizationReason::kDoNotOptimize); |
| 153 TraceRecompile(function, OptimizationReasonToString(reason), "optimized"); |
121 function->AttemptConcurrentOptimization(); | 154 function->AttemptConcurrentOptimization(); |
122 } | 155 } |
123 | 156 |
124 void RuntimeProfiler::Baseline(JSFunction* function, const char* reason) { | 157 void RuntimeProfiler::Baseline(JSFunction* function, |
125 TraceRecompile(function, reason, "baseline"); | 158 OptimizationReason reason) { |
| 159 DCHECK_NE(reason, OptimizationReason::kDoNotOptimize); |
| 160 TraceRecompile(function, OptimizationReasonToString(reason), "baseline"); |
126 | 161 |
127 // TODO(4280): Fix this to check function is compiled for the interpreter | 162 // TODO(4280): Fix this to check function is compiled for the interpreter |
128 // once we have a standard way to check that. For now function will only | 163 // once we have a standard way to check that. For now function will only |
129 // have a bytecode array if compiled for the interpreter. | 164 // have a bytecode array if compiled for the interpreter. |
130 DCHECK(function->shared()->HasBytecodeArray()); | 165 DCHECK(function->shared()->HasBytecodeArray()); |
131 function->MarkForBaseline(); | 166 function->MarkForBaseline(); |
132 } | 167 } |
133 | 168 |
134 void RuntimeProfiler::AttemptOnStackReplacement(JavaScriptFrame* frame, | 169 void RuntimeProfiler::AttemptOnStackReplacement(JavaScriptFrame* frame, |
135 int loop_nesting_levels) { | 170 int loop_nesting_levels) { |
(...skipping 98 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
234 int ticks = shared_code->profiler_ticks(); | 269 int ticks = shared_code->profiler_ticks(); |
235 | 270 |
236 if (ticks >= kProfilerTicksBeforeOptimization) { | 271 if (ticks >= kProfilerTicksBeforeOptimization) { |
237 int typeinfo, generic, total, type_percentage, generic_percentage; | 272 int typeinfo, generic, total, type_percentage, generic_percentage; |
238 GetICCounts(function, &typeinfo, &generic, &total, &type_percentage, | 273 GetICCounts(function, &typeinfo, &generic, &total, &type_percentage, |
239 &generic_percentage); | 274 &generic_percentage); |
240 if (type_percentage >= FLAG_type_info_threshold && | 275 if (type_percentage >= FLAG_type_info_threshold && |
241 generic_percentage <= FLAG_generic_ic_threshold) { | 276 generic_percentage <= FLAG_generic_ic_threshold) { |
242 // If this particular function hasn't had any ICs patched for enough | 277 // If this particular function hasn't had any ICs patched for enough |
243 // ticks, optimize it now. | 278 // ticks, optimize it now. |
244 Optimize(function, "hot and stable"); | 279 Optimize(function, OptimizationReason::kHotAndStable); |
245 } else if (ticks >= kTicksWhenNotEnoughTypeInfo) { | 280 } else if (ticks >= kTicksWhenNotEnoughTypeInfo) { |
246 Optimize(function, "not much type info but very hot"); | 281 Optimize(function, OptimizationReason::kHotWithoutMuchTypeInfo); |
247 } else { | 282 } else { |
248 shared_code->set_profiler_ticks(ticks + 1); | 283 shared_code->set_profiler_ticks(ticks + 1); |
249 if (FLAG_trace_opt_verbose) { | 284 if (FLAG_trace_opt_verbose) { |
250 PrintF("[not yet optimizing "); | 285 PrintF("[not yet optimizing "); |
251 function->PrintName(); | 286 function->PrintName(); |
252 PrintF(", not enough type info: %d/%d (%d%%)]\n", typeinfo, total, | 287 PrintF(", not enough type info: %d/%d (%d%%)]\n", typeinfo, total, |
253 type_percentage); | 288 type_percentage); |
254 } | 289 } |
255 } | 290 } |
256 } else if (!any_ic_changed_ && | 291 } else if (!any_ic_changed_ && |
257 shared_code->instruction_size() < kMaxSizeEarlyOpt) { | 292 shared_code->instruction_size() < kMaxSizeEarlyOpt) { |
258 // If no IC was patched since the last tick and this function is very | 293 // If no IC was patched since the last tick and this function is very |
259 // small, optimistically optimize it now. | 294 // small, optimistically optimize it now. |
260 int typeinfo, generic, total, type_percentage, generic_percentage; | 295 int typeinfo, generic, total, type_percentage, generic_percentage; |
261 GetICCounts(function, &typeinfo, &generic, &total, &type_percentage, | 296 GetICCounts(function, &typeinfo, &generic, &total, &type_percentage, |
262 &generic_percentage); | 297 &generic_percentage); |
263 if (type_percentage >= FLAG_type_info_threshold && | 298 if (type_percentage >= FLAG_type_info_threshold && |
264 generic_percentage <= FLAG_generic_ic_threshold) { | 299 generic_percentage <= FLAG_generic_ic_threshold) { |
265 Optimize(function, "small function"); | 300 Optimize(function, OptimizationReason::kSmallFunction); |
266 } else { | 301 } else { |
267 shared_code->set_profiler_ticks(ticks + 1); | 302 shared_code->set_profiler_ticks(ticks + 1); |
268 } | 303 } |
269 } else { | 304 } else { |
270 shared_code->set_profiler_ticks(ticks + 1); | 305 shared_code->set_profiler_ticks(ticks + 1); |
271 } | 306 } |
272 } | 307 } |
273 | 308 |
274 void RuntimeProfiler::MaybeBaselineIgnition(JSFunction* function, | 309 void RuntimeProfiler::MaybeBaselineIgnition(JSFunction* function, |
275 JavaScriptFrame* frame) { | 310 JavaScriptFrame* frame) { |
276 if (function->IsInOptimizationQueue()) return; | 311 if (function->IsInOptimizationQueue()) return; |
277 | 312 |
| 313 if (FLAG_always_osr) { |
| 314 AttemptOnStackReplacement(frame, AbstractCode::kMaxLoopNestingMarker); |
| 315 // Fall through and do a normal baseline compile as well. |
| 316 } else if (MaybeOSRIgnition(function, frame)) { |
| 317 return; |
| 318 } |
| 319 |
278 SharedFunctionInfo* shared = function->shared(); | 320 SharedFunctionInfo* shared = function->shared(); |
279 int ticks = shared->profiler_ticks(); | 321 int ticks = shared->profiler_ticks(); |
280 | 322 |
281 // TODO(rmcilroy): Also ensure we only OSR top-level code if it is smaller | |
282 // than kMaxToplevelSourceSize. | |
283 | |
284 if (FLAG_always_osr) { | |
285 AttemptOnStackReplacement(frame, AbstractCode::kMaxLoopNestingMarker); | |
286 // Fall through and do a normal baseline compile as well. | |
287 } else if (!frame->is_optimized() && | |
288 (function->IsMarkedForBaseline() || | |
289 function->IsMarkedForOptimization() || | |
290 function->IsMarkedForConcurrentOptimization() || | |
291 function->IsOptimized())) { | |
292 // Attempt OSR if we are still running interpreted code even though the | |
293 // the function has long been marked or even already been optimized. | |
294 int64_t allowance = | |
295 kOSRCodeSizeAllowanceBaseIgnition + | |
296 static_cast<int64_t>(ticks) * kOSRCodeSizeAllowancePerTickIgnition; | |
297 if (shared->bytecode_array()->Size() <= allowance) { | |
298 AttemptOnStackReplacement(frame); | |
299 } | |
300 return; | |
301 } | |
302 | |
303 if (shared->optimization_disabled() && | 323 if (shared->optimization_disabled() && |
304 shared->disable_optimization_reason() == kOptimizationDisabledForTest) { | 324 shared->disable_optimization_reason() == kOptimizationDisabledForTest) { |
305 // Don't baseline functions which have been marked by NeverOptimizeFunction | 325 // Don't baseline functions which have been marked by NeverOptimizeFunction |
306 // in a test. | 326 // in a test. |
307 return; | 327 return; |
308 } | 328 } |
309 | 329 |
310 if (ticks >= kProfilerTicksBeforeBaseline) { | 330 if (ticks >= kProfilerTicksBeforeBaseline) { |
311 Baseline(function, "hot enough for baseline"); | 331 Baseline(function, OptimizationReason::kHotEnoughForBaseline); |
312 } | 332 } |
313 } | 333 } |
314 | 334 |
315 void RuntimeProfiler::MaybeOptimizeIgnition(JSFunction* function, | 335 void RuntimeProfiler::MaybeOptimizeIgnition(JSFunction* function, |
316 JavaScriptFrame* frame) { | 336 JavaScriptFrame* frame) { |
317 if (function->IsInOptimizationQueue()) return; | 337 if (function->IsInOptimizationQueue()) return; |
318 | 338 |
| 339 if (FLAG_always_osr) { |
| 340 AttemptOnStackReplacement(frame, AbstractCode::kMaxLoopNestingMarker); |
| 341 // Fall through and do a normal optimized compile as well. |
| 342 } else if (MaybeOSRIgnition(function, frame)) { |
| 343 return; |
| 344 } |
| 345 |
319 SharedFunctionInfo* shared = function->shared(); | 346 SharedFunctionInfo* shared = function->shared(); |
320 int ticks = shared->profiler_ticks(); | 347 int ticks = shared->profiler_ticks(); |
321 | 348 |
322 // TODO(rmcilroy): Also ensure we only OSR top-level code if it is smaller | |
323 // than kMaxToplevelSourceSize. | |
324 | |
325 if (FLAG_always_osr) { | |
326 AttemptOnStackReplacement(frame, AbstractCode::kMaxLoopNestingMarker); | |
327 // Fall through and do a normal optimized compile as well. | |
328 } else if (!frame->is_optimized() && | |
329 (function->IsMarkedForBaseline() || | |
330 function->IsMarkedForOptimization() || | |
331 function->IsMarkedForConcurrentOptimization() || | |
332 function->IsOptimized())) { | |
333 // Attempt OSR if we are still running interpreted code even though the | |
334 // the function has long been marked or even already been optimized. | |
335 int64_t allowance = | |
336 kOSRCodeSizeAllowanceBaseIgnition + | |
337 static_cast<int64_t>(ticks) * kOSRCodeSizeAllowancePerTickIgnition; | |
338 if (shared->bytecode_array()->Size() <= allowance) { | |
339 AttemptOnStackReplacement(frame); | |
340 } | |
341 return; | |
342 } | |
343 | |
344 if (shared->optimization_disabled()) { | 349 if (shared->optimization_disabled()) { |
345 if (shared->deopt_count() >= FLAG_max_opt_count) { | 350 if (shared->deopt_count() >= FLAG_max_opt_count) { |
346 // If optimization was disabled due to many deoptimizations, | 351 // If optimization was disabled due to many deoptimizations, |
347 // then check if the function is hot and try to reenable optimization. | 352 // then check if the function is hot and try to reenable optimization. |
348 if (ticks >= kProfilerTicksBeforeReenablingOptimization) { | 353 if (ticks >= kProfilerTicksBeforeReenablingOptimization) { |
349 shared->set_profiler_ticks(0); | 354 shared->set_profiler_ticks(0); |
350 shared->TryReenableOptimization(); | 355 shared->TryReenableOptimization(); |
351 } | 356 } |
352 } | 357 } |
353 return; | 358 return; |
354 } | 359 } |
| 360 |
355 if (function->IsOptimized()) return; | 361 if (function->IsOptimized()) return; |
356 | 362 |
| 363 OptimizationReason reason = ShouldOptimizeIgnition(function, frame); |
| 364 |
| 365 if (reason != OptimizationReason::kDoNotOptimize) { |
| 366 Optimize(function, reason); |
| 367 } |
| 368 } |
| 369 |
| 370 bool RuntimeProfiler::MaybeOSRIgnition(JSFunction* function, |
| 371 JavaScriptFrame* frame) { |
| 372 if (!FLAG_ignition_osr) return false; |
| 373 |
| 374 SharedFunctionInfo* shared = function->shared(); |
| 375 int ticks = shared->profiler_ticks(); |
| 376 |
| 377 // TODO(rmcilroy): Also ensure we only OSR top-level code if it is smaller |
| 378 // than kMaxToplevelSourceSize. |
| 379 |
| 380 bool osr_before_baselined = function->IsMarkedForBaseline() && |
| 381 ShouldOptimizeIgnition(function, frame) != |
| 382 OptimizationReason::kDoNotOptimize; |
| 383 if (!frame->is_optimized() && |
| 384 (osr_before_baselined || function->IsMarkedForOptimization() || |
| 385 function->IsMarkedForConcurrentOptimization() || |
| 386 function->IsOptimized())) { |
| 387 // Attempt OSR if we are still running interpreted code even though the |
| 388 // the function has long been marked or even already been optimized. |
| 389 int64_t allowance = |
| 390 kOSRCodeSizeAllowanceBaseIgnition + |
| 391 static_cast<int64_t>(ticks) * kOSRCodeSizeAllowancePerTickIgnition; |
| 392 if (shared->bytecode_array()->Size() <= allowance) { |
| 393 AttemptOnStackReplacement(frame); |
| 394 } |
| 395 return true; |
| 396 } |
| 397 return false; |
| 398 } |
| 399 |
| 400 OptimizationReason RuntimeProfiler::ShouldOptimizeIgnition( |
| 401 JSFunction* function, JavaScriptFrame* frame) { |
| 402 SharedFunctionInfo* shared = function->shared(); |
| 403 int ticks = shared->profiler_ticks(); |
| 404 |
357 if (ticks >= kProfilerTicksBeforeOptimization) { | 405 if (ticks >= kProfilerTicksBeforeOptimization) { |
358 int typeinfo, generic, total, type_percentage, generic_percentage; | 406 int typeinfo, generic, total, type_percentage, generic_percentage; |
359 GetICCounts(function, &typeinfo, &generic, &total, &type_percentage, | 407 GetICCounts(function, &typeinfo, &generic, &total, &type_percentage, |
360 &generic_percentage); | 408 &generic_percentage); |
361 if (type_percentage >= FLAG_type_info_threshold && | 409 if (type_percentage >= FLAG_type_info_threshold && |
362 generic_percentage <= FLAG_generic_ic_threshold) { | 410 generic_percentage <= FLAG_generic_ic_threshold) { |
363 // If this particular function hasn't had any ICs patched for enough | 411 // If this particular function hasn't had any ICs patched for enough |
364 // ticks, optimize it now. | 412 // ticks, optimize it now. |
365 Optimize(function, "hot and stable"); | 413 return OptimizationReason::kHotAndStable; |
366 } else if (ticks >= kTicksWhenNotEnoughTypeInfo) { | 414 } else if (ticks >= kTicksWhenNotEnoughTypeInfo) { |
367 Optimize(function, "not much type info but very hot"); | 415 return OptimizationReason::kHotWithoutMuchTypeInfo; |
368 } else { | 416 } else { |
369 if (FLAG_trace_opt_verbose) { | 417 if (FLAG_trace_opt_verbose) { |
370 PrintF("[not yet optimizing "); | 418 PrintF("[not yet optimizing "); |
371 function->PrintName(); | 419 function->PrintName(); |
372 PrintF(", not enough type info: %d/%d (%d%%)]\n", typeinfo, total, | 420 PrintF(", not enough type info: %d/%d (%d%%)]\n", typeinfo, total, |
373 type_percentage); | 421 type_percentage); |
374 } | 422 } |
| 423 return OptimizationReason::kDoNotOptimize; |
375 } | 424 } |
376 } | 425 } |
377 // TODO(rmcilroy): Consider whether we should optimize small functions when | 426 // TODO(rmcilroy): Consider whether we should optimize small functions when |
378 // they are first seen on the stack (e.g., kMaxSizeEarlyOpt). | 427 // they are first seen on the stack (e.g., kMaxSizeEarlyOpt). |
| 428 return OptimizationReason::kDoNotOptimize; |
379 } | 429 } |
380 | 430 |
381 void RuntimeProfiler::MarkCandidatesForOptimization() { | 431 void RuntimeProfiler::MarkCandidatesForOptimization() { |
382 HandleScope scope(isolate_); | 432 HandleScope scope(isolate_); |
383 | 433 |
384 if (!isolate_->use_crankshaft()) return; | 434 if (!isolate_->use_crankshaft()) return; |
385 | 435 |
386 DisallowHeapAllocation no_gc; | 436 DisallowHeapAllocation no_gc; |
387 | 437 |
388 // Run through the JavaScript frames and collect them. If we already | 438 // Run through the JavaScript frames and collect them. If we already |
(...skipping 27 matching lines...) Expand all Loading... |
416 MaybeOptimizeIgnition(function, frame); | 466 MaybeOptimizeIgnition(function, frame); |
417 } | 467 } |
418 } else { | 468 } else { |
419 DCHECK_EQ(next_tier, Compiler::OPTIMIZED); | 469 DCHECK_EQ(next_tier, Compiler::OPTIMIZED); |
420 MaybeOptimizeFullCodegen(function, frame, frame_count); | 470 MaybeOptimizeFullCodegen(function, frame, frame_count); |
421 } | 471 } |
422 } | 472 } |
423 any_ic_changed_ = false; | 473 any_ic_changed_ = false; |
424 } | 474 } |
425 | 475 |
426 | |
427 } // namespace internal | 476 } // namespace internal |
428 } // namespace v8 | 477 } // namespace v8 |
OLD | NEW |