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

Side by Side Diff: src/debug/debug.cc

Issue 2649533002: [wasm] Implement stepping in wasm code (Closed)
Patch Set: Rebase Created 3 years, 11 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/compiler/wasm-compiler.cc ('k') | src/frames.h » ('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/debug/debug.h" 5 #include "src/debug/debug.h"
6 6
7 #include <memory> 7 #include <memory>
8 8
9 #include "src/api.h" 9 #include "src/api.h"
10 #include "src/arguments.h" 10 #include "src/arguments.h"
(...skipping 966 matching lines...) Expand 10 before | Expand all | Expand 10 after
977 DCHECK(in_debug_scope()); 977 DCHECK(in_debug_scope());
978 978
979 // Get the frame where the execution has stopped and skip the debug frame if 979 // Get the frame where the execution has stopped and skip the debug frame if
980 // any. The debug frame will only be present if execution was stopped due to 980 // any. The debug frame will only be present if execution was stopped due to
981 // hitting a break point. In other situations (e.g. unhandled exception) the 981 // hitting a break point. In other situations (e.g. unhandled exception) the
982 // debug frame is not present. 982 // debug frame is not present.
983 StackFrame::Id frame_id = break_frame_id(); 983 StackFrame::Id frame_id = break_frame_id();
984 // If there is no JavaScript stack don't do anything. 984 // If there is no JavaScript stack don't do anything.
985 if (frame_id == StackFrame::NO_ID) return; 985 if (frame_id == StackFrame::NO_ID) return;
986 986
987 JavaScriptFrameIterator frames_it(isolate_, frame_id); 987 StackTraceFrameIterator frames_it(isolate_, frame_id);
988 JavaScriptFrame* frame = frames_it.frame(); 988 StandardFrame* frame = frames_it.frame();
989 989
990 feature_tracker()->Track(DebugFeatureTracker::kStepping); 990 feature_tracker()->Track(DebugFeatureTracker::kStepping);
991 991
992 thread_local_.last_step_action_ = step_action; 992 thread_local_.last_step_action_ = step_action;
993 UpdateHookOnFunctionCall(); 993 UpdateHookOnFunctionCall();
994 994
995 // Handle stepping in wasm functions via the wasm interpreter.
996 if (frame->is_wasm()) {
997 // If the top frame is compiled, we cannot step.
998 if (frame->is_wasm_compiled()) return;
999 WasmInterpreterEntryFrame* wasm_frame =
1000 WasmInterpreterEntryFrame::cast(frame);
1001 wasm_frame->wasm_instance()->debug_info()->PrepareStep(step_action);
1002 return;
1003 }
1004
1005 JavaScriptFrame* js_frame = JavaScriptFrame::cast(frame);
1006
995 // If the function on the top frame is unresolved perform step out. This will 1007 // If the function on the top frame is unresolved perform step out. This will
996 // be the case when calling unknown function and having the debugger stopped 1008 // be the case when calling unknown function and having the debugger stopped
997 // in an unhandled exception. 1009 // in an unhandled exception.
998 if (!frame->function()->IsJSFunction()) { 1010 if (!js_frame->function()->IsJSFunction()) {
999 // Step out: Find the calling JavaScript frame and flood it with 1011 // Step out: Find the calling JavaScript frame and flood it with
1000 // breakpoints. 1012 // breakpoints.
1001 frames_it.Advance(); 1013 frames_it.Advance();
1002 // Fill the function to return to with one-shot break points. 1014 // Fill the function to return to with one-shot break points.
1003 JSFunction* function = frames_it.frame()->function(); 1015 JSFunction* function = JavaScriptFrame::cast(frames_it.frame())->function();
1004 FloodWithOneShot(Handle<JSFunction>(function)); 1016 FloodWithOneShot(handle(function, isolate_));
1005 return; 1017 return;
1006 } 1018 }
1007 1019
1008 // Get the debug info (create it if it does not exist). 1020 // Get the debug info (create it if it does not exist).
1009 auto summary = FrameSummary::GetTop(frame).AsJavaScript(); 1021 auto summary = FrameSummary::GetTop(frame).AsJavaScript();
1010 Handle<JSFunction> function(summary.function()); 1022 Handle<JSFunction> function(summary.function());
1011 Handle<SharedFunctionInfo> shared(function->shared()); 1023 Handle<SharedFunctionInfo> shared(function->shared());
1012 if (!EnsureDebugInfo(shared, function)) { 1024 if (!EnsureDebugInfo(shared, function)) {
1013 // Return if ensuring debug info failed. 1025 // Return if ensuring debug info failed.
1014 return; 1026 return;
1015 } 1027 }
1016 1028
1017 Handle<DebugInfo> debug_info(shared->GetDebugInfo()); 1029 Handle<DebugInfo> debug_info(shared->GetDebugInfo());
1018 BreakLocation location = BreakLocation::FromFrame(debug_info, frame); 1030 BreakLocation location = BreakLocation::FromFrame(debug_info, js_frame);
1019 1031
1020 // Any step at a return is a step-out. 1032 // Any step at a return is a step-out.
1021 if (location.IsReturn()) step_action = StepOut; 1033 if (location.IsReturn()) step_action = StepOut;
1022 // A step-next at a tail call is a step-out. 1034 // A step-next at a tail call is a step-out.
1023 if (location.IsTailCall() && step_action == StepNext) step_action = StepOut; 1035 if (location.IsTailCall() && step_action == StepNext) step_action = StepOut;
1024 // A step-next in blackboxed function is a step-out. 1036 // A step-next in blackboxed function is a step-out.
1025 if (step_action == StepNext && IsBlackboxed(shared)) step_action = StepOut; 1037 if (step_action == StepNext && IsBlackboxed(shared)) step_action = StepOut;
1026 1038
1027 thread_local_.last_statement_position_ = 1039 thread_local_.last_statement_position_ =
1028 summary.abstract_code()->SourceStatementPosition(summary.code_offset()); 1040 summary.abstract_code()->SourceStatementPosition(summary.code_offset());
1029 thread_local_.last_fp_ = frame->UnpaddedFP(); 1041 thread_local_.last_fp_ = frame->UnpaddedFP();
1030 // No longer perform the current async step. 1042 // No longer perform the current async step.
1031 clear_suspended_generator(); 1043 clear_suspended_generator();
1032 1044
1033 switch (step_action) { 1045 switch (step_action) {
1034 case StepNone: 1046 case StepNone:
1035 UNREACHABLE(); 1047 UNREACHABLE();
1036 break; 1048 break;
1037 case StepOut: 1049 case StepOut:
1038 // Advance to caller frame. 1050 // Advance to caller frame.
1039 frames_it.Advance(); 1051 frames_it.Advance();
1040 // Skip native and extension functions on the stack. 1052 // Find top-most function which is subject to debugging.
1041 while ( 1053 while (!frames_it.done()) {
1042 !frames_it.done() && 1054 StandardFrame* caller_frame = frames_it.frame();
1043 (!frames_it.frame()->function()->shared()->IsSubjectToDebugging() || 1055 if (caller_frame->is_wasm()) {
1044 IsBlackboxed(frames_it.frame()->function()->shared()))) { 1056 // TODO(clemensh): Implement stepping out from JS to WASM.
1057 break;
1058 }
1059 Handle<JSFunction> js_caller_function(
1060 JavaScriptFrame::cast(caller_frame)->function(), isolate_);
1061 if (js_caller_function->shared()->IsSubjectToDebugging() &&
1062 !IsBlackboxed(js_caller_function->shared())) {
1063 // Fill the caller function to return to with one-shot break points.
1064 FloodWithOneShot(js_caller_function);
1065 thread_local_.target_fp_ = frames_it.frame()->UnpaddedFP();
1066 break;
1067 }
1045 // Builtin functions are not subject to stepping, but need to be 1068 // Builtin functions are not subject to stepping, but need to be
1046 // deoptimized to include checks for step-in at call sites. 1069 // deoptimized to include checks for step-in at call sites.
1047 Deoptimizer::DeoptimizeFunction(frames_it.frame()->function()); 1070 Deoptimizer::DeoptimizeFunction(*js_caller_function);
1048 frames_it.Advance(); 1071 frames_it.Advance();
1049 } 1072 }
1050 if (!frames_it.done()) {
1051 // Fill the caller function to return to with one-shot break points.
1052 Handle<JSFunction> caller_function(frames_it.frame()->function());
1053 FloodWithOneShot(caller_function);
1054 thread_local_.target_fp_ = frames_it.frame()->UnpaddedFP();
1055 }
1056 // Clear last position info. For stepping out it does not matter. 1073 // Clear last position info. For stepping out it does not matter.
1057 thread_local_.last_statement_position_ = kNoSourcePosition; 1074 thread_local_.last_statement_position_ = kNoSourcePosition;
1058 thread_local_.last_fp_ = 0; 1075 thread_local_.last_fp_ = 0;
1059 break; 1076 break;
1060 case StepNext: 1077 case StepNext:
1061 thread_local_.target_fp_ = frame->UnpaddedFP(); 1078 thread_local_.target_fp_ = frame->UnpaddedFP();
1062 FloodWithOneShot(function); 1079 FloodWithOneShot(function);
1063 break; 1080 break;
1064 case StepIn: 1081 case StepIn:
1082 // TODO(clemensh): Implement stepping from JS into WASM.
1065 FloodWithOneShot(function); 1083 FloodWithOneShot(function);
1066 break; 1084 break;
1067 case StepFrame: 1085 case StepFrame:
1086 // TODO(clemensh): Implement stepping from JS into WASM or vice versa.
1068 // No point in setting one-shot breaks at places where we are not about 1087 // No point in setting one-shot breaks at places where we are not about
1069 // to leave the current frame. 1088 // to leave the current frame.
1070 FloodWithOneShot(function, CALLS_AND_RETURNS); 1089 FloodWithOneShot(function, CALLS_AND_RETURNS);
1071 break; 1090 break;
1072 } 1091 }
1073 } 1092 }
1074 1093
1075 // Simple function for returning the source positions for active break points. 1094 // Simple function for returning the source positions for active break points.
1076 Handle<Object> Debug::GetSourceBreakLocations( 1095 Handle<Object> Debug::GetSourceBreakLocations(
1077 Handle<SharedFunctionInfo> shared, 1096 Handle<SharedFunctionInfo> shared,
(...skipping 1237 matching lines...) Expand 10 before | Expand all | Expand 10 after
2315 return v8::Utils::ToLocal(callback_data_); 2334 return v8::Utils::ToLocal(callback_data_);
2316 } 2335 }
2317 2336
2318 2337
2319 v8::Isolate* EventDetailsImpl::GetIsolate() const { 2338 v8::Isolate* EventDetailsImpl::GetIsolate() const {
2320 return reinterpret_cast<v8::Isolate*>(exec_state_->GetIsolate()); 2339 return reinterpret_cast<v8::Isolate*>(exec_state_->GetIsolate());
2321 } 2340 }
2322 2341
2323 } // namespace internal 2342 } // namespace internal
2324 } // namespace v8 2343 } // namespace v8
OLDNEW
« no previous file with comments | « src/compiler/wasm-compiler.cc ('k') | src/frames.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698