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

Unified Diff: src/debug/debug.cc

Issue 2633803002: [inspector] implemented blackboxing inside v8 (Closed)
Patch Set: addressed comments 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/debug/debug.h ('k') | src/debug/debug-interface.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/debug/debug.cc
diff --git a/src/debug/debug.cc b/src/debug/debug.cc
index 654951870b97fc470d7e9b88ff90519a5904e572..7759d6cc3bbc57623abf8f33ca819e57b578fb78 100644
--- a/src/debug/debug.cc
+++ b/src/debug/debug.cc
@@ -840,7 +840,8 @@ void Debug::FloodWithOneShot(Handle<JSFunction> function,
// Debug utility functions are not subject to debugging.
if (function->native_context() == *debug_context()) return;
- if (!function->shared()->IsSubjectToDebugging()) {
+ if (!function->shared()->IsSubjectToDebugging() ||
+ IsBlackboxed(function->shared())) {
// Builtin functions are not subject to stepping, but need to be
// deoptimized, because optimized code does not check for debug
// step in at call sites.
@@ -959,7 +960,8 @@ void Debug::PrepareStepOnThrow() {
// Find the closest Javascript frame we can flood with one-shots.
while (!it.done() &&
- !it.frame()->function()->shared()->IsSubjectToDebugging()) {
+ (!it.frame()->function()->shared()->IsSubjectToDebugging() ||
+ IsBlackboxed(it.frame()->function()->shared()))) {
it.Advance();
}
@@ -1019,6 +1021,8 @@ void Debug::PrepareStep(StepAction step_action) {
if (location.IsReturn()) step_action = StepOut;
// A step-next at a tail call is a step-out.
if (location.IsTailCall() && step_action == StepNext) step_action = StepOut;
+ // A step-next in blackboxed function is a step-out.
+ if (step_action == StepNext && IsBlackboxed(shared)) step_action = StepOut;
thread_local_.last_statement_position_ =
summary.abstract_code()->SourceStatementPosition(summary.code_offset());
@@ -1034,8 +1038,10 @@ void Debug::PrepareStep(StepAction step_action) {
// Advance to caller frame.
frames_it.Advance();
// Skip native and extension functions on the stack.
- while (!frames_it.done() &&
- !frames_it.frame()->function()->shared()->IsSubjectToDebugging()) {
+ while (
+ !frames_it.done() &&
+ (!frames_it.frame()->function()->shared()->IsSubjectToDebugging() ||
+ IsBlackboxed(frames_it.frame()->function()->shared()))) {
// Builtin functions are not subject to stepping, but need to be
// deoptimized to include checks for step-in at call sites.
Deoptimizer::DeoptimizeFunction(frames_it.frame()->function());
@@ -1751,15 +1757,18 @@ void Debug::OnException(Handle<Object> exception, Handle<Object> promise) {
}
{
- // Check whether the break location is muted.
JavaScriptFrameIterator it(isolate_);
- if (!it.done() && IsMutedAtCurrentLocation(it.frame())) return;
+ // Check whether the top frame is blackboxed or the break location is muted.
+ if (!it.done() && (IsBlackboxed(it.frame()->function()->shared()) ||
+ IsMutedAtCurrentLocation(it.frame()))) {
+ return;
+ }
}
DebugScope debug_scope(this);
if (debug_scope.failed()) return;
- if (debug_event_listener_) {
+ if (debug_delegate_) {
HandleScope scope(isolate_);
// Create the execution state.
@@ -1767,7 +1776,7 @@ void Debug::OnException(Handle<Object> exception, Handle<Object> promise) {
// Bail out and don't call debugger if exception.
if (!MakeExecutionState().ToHandle(&exec_state)) return;
- debug_event_listener_->ExceptionThrown(
+ debug_delegate_->ExceptionThrown(
GetDebugEventContext(isolate_),
v8::Utils::ToLocal(Handle<JSObject>::cast(exec_state)),
v8::Utils::ToLocal(exception), promise->IsJSObject(), uncaught);
@@ -1797,7 +1806,7 @@ void Debug::OnDebugBreak(Handle<Object> break_points_hit) {
PrintBreakLocation();
#endif // DEBUG
- if (debug_event_listener_) {
+ if (debug_delegate_) {
HandleScope scope(isolate_);
// Create the execution state.
@@ -1807,7 +1816,7 @@ void Debug::OnDebugBreak(Handle<Object> break_points_hit) {
bool previous = in_debug_event_listener_;
in_debug_event_listener_ = true;
- debug_event_listener_->BreakProgramRequested(
+ debug_delegate_->BreakProgramRequested(
GetDebugEventContext(isolate_),
v8::Utils::ToLocal(Handle<JSObject>::cast(exec_state)),
v8::Utils::ToLocal(break_points_hit));
@@ -1891,11 +1900,46 @@ int Debug::NextAsyncTaskId(Handle<JSObject> promise) {
return async_id->value();
}
+namespace {
+debug::Location GetDebugLocation(Handle<Script> script, int source_position) {
+ Script::PositionInfo info;
+ Script::GetPositionInfo(script, source_position, &info, Script::WITH_OFFSET);
+ return debug::Location(info.line, info.column);
+}
+} // namespace
+
+bool Debug::IsBlackboxed(SharedFunctionInfo* shared) {
+ HandleScope scope(isolate_);
+ Handle<SharedFunctionInfo> shared_function_info(shared);
+ return IsBlackboxed(shared_function_info);
+}
+
+bool Debug::IsBlackboxed(Handle<SharedFunctionInfo> shared) {
+ if (!debug_delegate_) return false;
+ if (!shared->computed_debug_is_blackboxed()) {
+ bool is_blackboxed = false;
+ if (shared->script()->IsScript()) {
+ HandleScope handle_scope(isolate_);
+ Handle<Script> script(Script::cast(shared->script()));
+ if (script->type() == i::Script::TYPE_NORMAL) {
+ debug::Location start =
+ GetDebugLocation(script, shared->start_position());
+ debug::Location end = GetDebugLocation(script, shared->end_position());
+ is_blackboxed = debug_delegate_->IsFunctionBlackboxed(
+ ToApiHandle<debug::Script>(script), start, end);
+ }
+ }
+ shared->set_debug_is_blackboxed(is_blackboxed);
+ shared->set_computed_debug_is_blackboxed(true);
+ }
+ return shared->debug_is_blackboxed();
+}
+
void Debug::OnAsyncTaskEvent(debug::PromiseDebugActionType type, int id) {
if (in_debug_scope() || ignore_events()) return;
- if (debug_event_listener_) {
- debug_event_listener_->PromiseEventOccurred(type, id);
+ if (debug_delegate_) {
+ debug_delegate_->PromiseEventOccurred(type, id);
if (!non_inspector_listener_exists()) return;
}
@@ -1967,9 +2011,9 @@ void Debug::ProcessCompileEvent(v8::DebugEvent event, Handle<Script> script) {
DebugScope debug_scope(this);
if (debug_scope.failed()) return;
- if (debug_event_listener_) {
- debug_event_listener_->ScriptCompiled(ToApiHandle<debug::Script>(script),
- event != v8::AfterCompile);
+ if (debug_delegate_) {
+ debug_delegate_->ScriptCompiled(ToApiHandle<debug::Script>(script),
+ event != v8::AfterCompile);
if (!non_inspector_listener_exists()) return;
}
@@ -2013,15 +2057,13 @@ void Debug::SetEventListener(Handle<Object> callback,
UpdateState();
}
-
-void Debug::SetDebugEventListener(debug::DebugEventListener* listener) {
- debug_event_listener_ = listener;
+void Debug::SetDebugDelegate(debug::DebugDelegate* delegate) {
+ debug_delegate_ = delegate;
UpdateState();
}
void Debug::UpdateState() {
- bool is_active =
- !event_listener_.is_null() || debug_event_listener_ != nullptr;
+ bool is_active = !event_listener_.is_null() || debug_delegate_ != nullptr;
if (is_active || in_debug_scope()) {
// Note that the debug context could have already been loaded to
// bootstrap test cases.
@@ -2078,6 +2120,11 @@ void Debug::HandleDebugBreak() {
if (fun && fun->IsJSFunction()) {
// Don't stop in builtin functions.
if (!JSFunction::cast(fun)->shared()->IsSubjectToDebugging()) return;
+ if (isolate_->stack_guard()->CheckDebugBreak() &&
+ IsBlackboxed(JSFunction::cast(fun)->shared())) {
+ Deoptimizer::DeoptimizeFunction(JSFunction::cast(fun));
+ return;
+ }
JSGlobalObject* global =
JSFunction::cast(fun)->context()->global_object();
// Don't stop in debugger functions.
« no previous file with comments | « src/debug/debug.h ('k') | src/debug/debug-interface.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698