Chromium Code Reviews| Index: src/runtime.cc |
| diff --git a/src/runtime.cc b/src/runtime.cc |
| index 057e268f7ad0e6ec9f830b449b7963a5eda30934..ef5a9510af25b4341bc7c50cad7802bef8932c4d 100644 |
| --- a/src/runtime.cc |
| +++ b/src/runtime.cc |
| @@ -8292,26 +8292,29 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InstallRecompiledCode) { |
| class ActivationsFinder : public ThreadVisitor { |
| public: |
| - explicit ActivationsFinder(JSFunction* function) |
| - : function_(function), has_activations_(false) {} |
| + JSFunction* function_; |
| + Code* code_; |
| + bool has_function_activations_; |
| + bool has_code_activations_; |
| + |
| + ActivationsFinder(JSFunction* function, Code* code) |
| + : function_(function), |
| + code_(code), |
| + has_function_activations_(false), |
| + has_code_activations_(false) { } |
| void VisitThread(Isolate* isolate, ThreadLocalTop* top) { |
| - if (has_activations_) return; |
| + JavaScriptFrameIterator it(isolate, top); |
| + VisitFrames(&it); |
| + } |
| - for (JavaScriptFrameIterator it(isolate, top); !it.done(); it.Advance()) { |
| - JavaScriptFrame* frame = it.frame(); |
| - if (frame->is_optimized() && frame->function() == function_) { |
| - has_activations_ = true; |
| - return; |
| - } |
| + void VisitFrames(JavaScriptFrameIterator* it) { |
| + for (; !it->done(); it->Advance()) { |
| + JavaScriptFrame* frame = it->frame(); |
| + if (frame->function() == function_) has_function_activations_ = true; |
|
Michael Starzinger
2013/08/21 16:20:28
The "has_function_activations" field seems to be u
titzer
2013/08/21 16:26:29
Correct, twers for debuggin'
|
| + if (code_->contains(frame->pc())) has_code_activations_ = true; |
| } |
| } |
| - |
| - bool has_activations() { return has_activations_; } |
| - |
| - private: |
| - JSFunction* function_; |
| - bool has_activations_; |
| }; |
| @@ -8334,7 +8337,11 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_NotifyDeoptimized) { |
| Deoptimizer* deoptimizer = Deoptimizer::Grab(isolate); |
| ASSERT(AllowHeapAllocation::IsAllowed()); |
| - ASSERT(deoptimizer->compiled_code_kind() == Code::OPTIMIZED_FUNCTION); |
| + Handle<JSFunction> function(deoptimizer->function()); |
| + Handle<Code> optimized_code(deoptimizer->compiled_code()); |
|
Toon Verwaest
2013/08/21 15:33:17
Could we also rename compiled_code() in the deopti
Michael Starzinger
2013/08/21 16:20:28
nit: Use an assignment instead of the copy constru
titzer
2013/08/21 16:20:48
Will have to do that rename in a later CL; wanted
titzer
2013/08/21 16:26:29
Done.
|
| + |
| + ASSERT(optimized_code->kind() == Code::OPTIMIZED_FUNCTION); |
| + ASSERT(type == deoptimizer->bailout_type()); |
| // Make sure to materialize objects before causing any allocation. |
| JavaScriptFrameIterator it(isolate); |
| @@ -8343,10 +8350,6 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_NotifyDeoptimized) { |
| JavaScriptFrame* frame = it.frame(); |
| RUNTIME_ASSERT(frame->function()->IsJSFunction()); |
| - Handle<JSFunction> function(frame->function(), isolate); |
| - Handle<Code> optimized_code(function->code()); |
| - RUNTIME_ASSERT((type != Deoptimizer::EAGER && |
| - type != Deoptimizer::SOFT) || function->IsOptimized()); |
| // Avoid doing too much work when running with --always-opt and keep |
| // the optimized code around. |
| @@ -8354,33 +8357,27 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_NotifyDeoptimized) { |
| return isolate->heap()->undefined_value(); |
| } |
| - // Find other optimized activations of the function or functions that |
| - // share the same optimized code. |
| - bool has_other_activations = false; |
| - while (!it.done()) { |
| - JavaScriptFrame* frame = it.frame(); |
| - JSFunction* other_function = frame->function(); |
| - if (frame->is_optimized() && other_function->code() == function->code()) { |
| - has_other_activations = true; |
| - break; |
| - } |
| - it.Advance(); |
| - } |
| + // TODO(titzer): in the case of SOFT or EAGER deopt, we may want to allow |
| + // the code to be reused a few times before unlinking it from the function. |
|
Toon Verwaest
2013/08/21 15:33:17
I'm not fully sure how this would work yet. Is it
titzer
2013/08/21 16:20:48
Removed.
|
| - if (!has_other_activations) { |
| - ActivationsFinder activations_finder(*function); |
| - isolate->thread_manager()->IterateArchivedThreads(&activations_finder); |
| - has_other_activations = activations_finder.has_activations(); |
| - } |
| + // Search for other activations of the same function and code. |
| + ActivationsFinder activations_finder(*function, *optimized_code); |
| + activations_finder.VisitFrames(&it); |
| + isolate->thread_manager()->IterateArchivedThreads(&activations_finder); |
| - if (!has_other_activations) { |
| + if (!activations_finder.has_code_activations_) { |
| if (FLAG_trace_deopt) { |
| PrintF("[removing optimized code for: "); |
| function->PrintName(); |
| PrintF("]\n"); |
| } |
| - function->ReplaceCode(function->shared()->code()); |
| + if (function->code() == *optimized_code) { |
| + function->ReplaceCode(function->shared()->code()); |
| + } |
| } else { |
| + // TODO(titzer): we should probably do DeoptimizeCodeList(code) |
| + // unconditionally if the code is not already marked for deoptimization. |
| + // If there is an index by shared function info, all the better. |
| Deoptimizer::DeoptimizeFunction(*function); |
| } |
|
Toon Verwaest
2013/08/21 15:33:17
Can't we just unconditionally do
Deoptimizer::Deo
|
| // Evict optimized code for this function from the cache so that it doesn't |