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/debug/liveedit.h" | 5 #include "src/debug/liveedit.h" |
6 | 6 |
7 #include "src/ast/scopeinfo.h" | 7 #include "src/ast/scopeinfo.h" |
8 #include "src/ast/scopes.h" | 8 #include "src/ast/scopes.h" |
9 #include "src/code-stubs.h" | 9 #include "src/code-stubs.h" |
10 #include "src/compilation-cache.h" | 10 #include "src/compilation-cache.h" |
(...skipping 605 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
616 this->SetSmiValueField(kStartPositionOffset_, start_position); | 616 this->SetSmiValueField(kStartPositionOffset_, start_position); |
617 this->SetSmiValueField(kEndPositionOffset_, end_position); | 617 this->SetSmiValueField(kEndPositionOffset_, end_position); |
618 this->SetSmiValueField(kParamNumOffset_, param_num); | 618 this->SetSmiValueField(kParamNumOffset_, param_num); |
619 this->SetSmiValueField(kLiteralNumOffset_, literal_count); | 619 this->SetSmiValueField(kLiteralNumOffset_, literal_count); |
620 this->SetSmiValueField(kParentIndexOffset_, parent_index); | 620 this->SetSmiValueField(kParentIndexOffset_, parent_index); |
621 } | 621 } |
622 | 622 |
623 | 623 |
624 void FunctionInfoWrapper::SetFunctionCode(Handle<Code> function_code, | 624 void FunctionInfoWrapper::SetFunctionCode(Handle<Code> function_code, |
625 Handle<HeapObject> code_scope_info) { | 625 Handle<HeapObject> code_scope_info) { |
| 626 // CompileForLiveEdit must deliver full-codegen code. |
| 627 DCHECK(function_code->kind() == Code::FUNCTION); |
626 Handle<JSValue> code_wrapper = WrapInJSValue(function_code); | 628 Handle<JSValue> code_wrapper = WrapInJSValue(function_code); |
627 this->SetField(kCodeOffset_, code_wrapper); | 629 this->SetField(kCodeOffset_, code_wrapper); |
628 | 630 |
629 Handle<JSValue> scope_wrapper = WrapInJSValue(code_scope_info); | 631 Handle<JSValue> scope_wrapper = WrapInJSValue(code_scope_info); |
630 this->SetField(kCodeScopeInfoOffset_, scope_wrapper); | 632 this->SetField(kCodeScopeInfoOffset_, scope_wrapper); |
631 } | 633 } |
632 | 634 |
633 | 635 |
634 void FunctionInfoWrapper::SetSharedFunctionInfo( | 636 void FunctionInfoWrapper::SetSharedFunctionInfo( |
635 Handle<SharedFunctionInfo> info) { | 637 Handle<SharedFunctionInfo> info) { |
(...skipping 463 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1099 void LiveEdit::ReplaceFunctionCode( | 1101 void LiveEdit::ReplaceFunctionCode( |
1100 Handle<JSArray> new_compile_info_array, | 1102 Handle<JSArray> new_compile_info_array, |
1101 Handle<JSArray> shared_info_array) { | 1103 Handle<JSArray> shared_info_array) { |
1102 Isolate* isolate = new_compile_info_array->GetIsolate(); | 1104 Isolate* isolate = new_compile_info_array->GetIsolate(); |
1103 | 1105 |
1104 FunctionInfoWrapper compile_info_wrapper(new_compile_info_array); | 1106 FunctionInfoWrapper compile_info_wrapper(new_compile_info_array); |
1105 SharedInfoWrapper shared_info_wrapper(shared_info_array); | 1107 SharedInfoWrapper shared_info_wrapper(shared_info_array); |
1106 | 1108 |
1107 Handle<SharedFunctionInfo> shared_info = shared_info_wrapper.GetInfo(); | 1109 Handle<SharedFunctionInfo> shared_info = shared_info_wrapper.GetInfo(); |
1108 | 1110 |
1109 if (shared_info->code()->kind() == Code::FUNCTION) { | 1111 if (shared_info->is_compiled()) { |
1110 Handle<Code> code = compile_info_wrapper.GetFunctionCode(); | 1112 Handle<Code> new_code = compile_info_wrapper.GetFunctionCode(); |
1111 ReplaceCodeObject(Handle<Code>(shared_info->code()), code); | 1113 Handle<Code> old_code(shared_info->code()); |
| 1114 if (shared_info->HasBytecodeArray()) { |
| 1115 // The old code is interpreted. If we clear the bytecode array, the |
| 1116 // interpreter entry trampoline will self-heal and go to compiled code. |
| 1117 shared_info->ClearBytecodeArray(); |
| 1118 shared_info->ReplaceCode(*new_code); |
| 1119 } else { |
| 1120 DCHECK(old_code->kind() == Code::FUNCTION); |
| 1121 ReplaceCodeObject(old_code, new_code); |
| 1122 } |
1112 Handle<Object> code_scope_info = compile_info_wrapper.GetCodeScopeInfo(); | 1123 Handle<Object> code_scope_info = compile_info_wrapper.GetCodeScopeInfo(); |
1113 if (code_scope_info->IsFixedArray()) { | 1124 if (code_scope_info->IsFixedArray()) { |
1114 shared_info->set_scope_info(ScopeInfo::cast(*code_scope_info)); | 1125 shared_info->set_scope_info(ScopeInfo::cast(*code_scope_info)); |
1115 } | 1126 } |
1116 shared_info->DisableOptimization(kLiveEdit); | 1127 shared_info->DisableOptimization(kLiveEdit); |
1117 // Update the type feedback vector, if needed. | 1128 // Update the type feedback vector, if needed. |
1118 MaybeHandle<TypeFeedbackVector> feedback_vector = | 1129 MaybeHandle<TypeFeedbackVector> feedback_vector = |
1119 compile_info_wrapper.GetFeedbackVector(); | 1130 compile_info_wrapper.GetFeedbackVector(); |
1120 if (!feedback_vector.is_null()) { | 1131 if (!feedback_vector.is_null()) { |
1121 shared_info->set_feedback_vector(*feedback_vector.ToHandleChecked()); | 1132 shared_info->set_feedback_vector(*feedback_vector.ToHandleChecked()); |
(...skipping 415 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1537 frame_has_padding = false; | 1548 frame_has_padding = false; |
1538 } else if (pre_top_frame->type() == StackFrame::ARGUMENTS_ADAPTOR) { | 1549 } else if (pre_top_frame->type() == StackFrame::ARGUMENTS_ADAPTOR) { |
1539 // This must be adaptor that remain from the frame dropping that | 1550 // This must be adaptor that remain from the frame dropping that |
1540 // is still on stack. A frame dropper frame must be above it. | 1551 // is still on stack. A frame dropper frame must be above it. |
1541 DCHECK(frames[top_frame_index - 2]->LookupCode() == | 1552 DCHECK(frames[top_frame_index - 2]->LookupCode() == |
1542 isolate->builtins()->builtin(Builtins::kFrameDropper_LiveEdit)); | 1553 isolate->builtins()->builtin(Builtins::kFrameDropper_LiveEdit)); |
1543 pre_top_frame = frames[top_frame_index - 3]; | 1554 pre_top_frame = frames[top_frame_index - 3]; |
1544 top_frame = frames[top_frame_index - 2]; | 1555 top_frame = frames[top_frame_index - 2]; |
1545 *mode = LiveEdit::CURRENTLY_SET_MODE; | 1556 *mode = LiveEdit::CURRENTLY_SET_MODE; |
1546 frame_has_padding = false; | 1557 frame_has_padding = false; |
| 1558 } else if (pre_top_frame_code->kind() == Code::BYTECODE_HANDLER) { |
| 1559 // Interpreted bytecode takes up two stack frames, one for the bytecode |
| 1560 // handler and one for the interpreter entry trampoline. Therefore we shift |
| 1561 // up by one frame. |
| 1562 *mode = LiveEdit::FRAME_DROPPED_IN_DIRECT_CALL; |
| 1563 pre_top_frame = frames[top_frame_index - 2]; |
| 1564 top_frame = frames[top_frame_index - 1]; |
1547 } else { | 1565 } else { |
1548 return "Unknown structure of stack above changing function"; | 1566 return "Unknown structure of stack above changing function"; |
1549 } | 1567 } |
1550 | 1568 |
1551 Address unused_stack_top = top_frame->sp(); | 1569 Address unused_stack_top = top_frame->sp(); |
1552 Address unused_stack_bottom = | 1570 Address unused_stack_bottom = |
1553 bottom_js_frame->fp() - FrameDropperFrameConstants::kFixedFrameSize + | 1571 bottom_js_frame->fp() - FrameDropperFrameConstants::kFixedFrameSize + |
1554 2 * kPointerSize; // Bigger address end is exclusive. | 1572 2 * kPointerSize; // Bigger address end is exclusive. |
1555 | 1573 |
1556 Address* top_frame_pc_address = top_frame->pc_address(); | 1574 Address* top_frame_pc_address = top_frame->pc_address(); |
(...skipping 462 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2019 } | 2037 } |
2020 } | 2038 } |
2021 | 2039 |
2022 | 2040 |
2023 bool LiveEditFunctionTracker::IsActive(Isolate* isolate) { | 2041 bool LiveEditFunctionTracker::IsActive(Isolate* isolate) { |
2024 return isolate->active_function_info_listener() != NULL; | 2042 return isolate->active_function_info_listener() != NULL; |
2025 } | 2043 } |
2026 | 2044 |
2027 } // namespace internal | 2045 } // namespace internal |
2028 } // namespace v8 | 2046 } // namespace v8 |
OLD | NEW |