From 3b955790a0f16c27b1fafd8a87aec40127602a9d Mon Sep 17 00:00:00 2001 From: "peter.rybin@gmail.com" Date: Thu, 15 Oct 2009 20:06:08 +0000 Subject: [PATCH] Redo "running" field in debug-delay.js and support "suspend" command It also fixes "backtrace" command so that it didn't give away random stack if we are running Review URL: http://codereview.chromium.org/242034 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@3077 ce2b1a6d-e550-0410-aec6-3dcde31c8c00 --- src/debug-delay.js | 31 ++++++---- src/debug.cc | 37 +++++++----- test/mjsunit/debug-backtrace.js | 22 ++++++- test/mjsunit/debug-changebreakpoint.js | 2 +- test/mjsunit/debug-clearbreakpoint.js | 2 +- test/mjsunit/debug-clearbreakpointgroup.js | 2 +- test/mjsunit/debug-continue.js | 31 +++++----- test/mjsunit/debug-evaluate-recursive.js | 28 ++++----- test/mjsunit/debug-evaluate.js | 7 ++- test/mjsunit/debug-handle.js | 49 ++++++++------- test/mjsunit/debug-mirror-cache.js | 10 ++-- test/mjsunit/debug-references.js | 4 +- test/mjsunit/debug-scopes.js | 4 +- test/mjsunit/debug-scripts-request.js | 2 +- test/mjsunit/debug-setbreakpoint.js | 2 +- test/mjsunit/debug-suspend.js | 96 ++++++++++++++++++++++++++++++ test/mjsunit/regress/regress-1081309.js | 4 +- 17 files changed, 235 insertions(+), 98 deletions(-) create mode 100644 test/mjsunit/debug-suspend.js diff --git a/src/debug-delay.js b/src/debug-delay.js index cb789be..d9447bd 100644 --- a/src/debug-delay.js +++ b/src/debug-delay.js @@ -795,8 +795,8 @@ ExecutionState.prototype.selectedFrame = function() { return this.selected_frame; }; -ExecutionState.prototype.debugCommandProcessor = function(protocol) { - return new DebugCommandProcessor(this, protocol); +ExecutionState.prototype.debugCommandProcessor = function(opt_is_running) { + return new DebugCommandProcessor(this, opt_is_running); }; @@ -1081,9 +1081,9 @@ function MakeScriptObject_(script, include_source) { }; -function DebugCommandProcessor(exec_state) { +function DebugCommandProcessor(exec_state, opt_is_running) { this.exec_state_ = exec_state; - this.running_ = false; + this.running_ = opt_is_running || false; }; @@ -1107,7 +1107,8 @@ function ProtocolMessage(request) { this.type = 'event'; } this.success = true; - this.running = false; + // Handler may set this field to control debugger state. + this.running = undefined; } @@ -1168,11 +1169,7 @@ ProtocolMessage.prototype.toJSONProtocol = function() { if (this.message) { json.message = this.message; } - if (this.running) { - json.running = true; - } else { - json.running = false; - } + json.running = this.running; return JSON.stringify(json); } @@ -1244,6 +1241,8 @@ DebugCommandProcessor.prototype.processDebugJSONRequest = function(json_request) this.scriptsRequest_(request, response); } else if (request.command == 'threads') { this.threadsRequest_(request, response); + } else if (request.command == 'suspend') { + this.suspendRequest_(request, response); } else { throw new Error('Unknown command "' + request.command + '" in request'); } @@ -1258,7 +1257,11 @@ DebugCommandProcessor.prototype.processDebugJSONRequest = function(json_request) // Return the response as a JSON encoded string. try { - this.running_ = response.running; // Store the running state. + if (!IS_UNDEFINED(response.running)) { + // Response controls running state. + this.running_ = response.running; + } + response.running = this.running_; return response.toJSONProtocol(); } catch (e) { // Failed to generate response - return generic error. @@ -1907,6 +1910,12 @@ DebugCommandProcessor.prototype.threadsRequest_ = function(request, response) { }; +DebugCommandProcessor.prototype.suspendRequest_ = function(request, response) { + // TODO(peter.rybin): probably we need some body field here. + response.running = false; +}; + + // Check whether the previously processed command caused the VM to become // running. DebugCommandProcessor.prototype.isRunning = function() { diff --git a/src/debug.cc b/src/debug.cc index d4a0012..d3a6b5b 100644 --- a/src/debug.cc +++ b/src/debug.cc @@ -2212,21 +2212,31 @@ void Debugger::NotifyMessageHandler(v8::DebugEvent event, return; } - // Get the DebugCommandProcessor. - v8::Local api_exec_state = - v8::Utils::ToLocal(Handle::cast(exec_state)); - v8::Local fun_name = - v8::String::New("debugCommandProcessor"); - v8::Local fun = - v8::Function::Cast(*api_exec_state->Get(fun_name)); v8::TryCatch try_catch; - v8::Local cmd_processor = - v8::Object::Cast(*fun->Call(api_exec_state, 0, NULL)); - if (try_catch.HasCaught()) { - PrintLn(try_catch.Exception()); - return; + + // DebugCommandProcessor goes here. + v8::Local cmd_processor; + { + v8::Local api_exec_state = + v8::Utils::ToLocal(Handle::cast(exec_state)); + v8::Local fun_name = + v8::String::New("debugCommandProcessor"); + v8::Local fun = + v8::Function::Cast(*api_exec_state->Get(fun_name)); + + v8::Handle running = + auto_continue ? v8::True() : v8::False(); + static const int kArgc = 1; + v8::Handle argv[kArgc] = { running }; + cmd_processor = v8::Object::Cast(*fun->Call(api_exec_state, kArgc, argv)); + if (try_catch.HasCaught()) { + PrintLn(try_catch.Exception()); + return; + } } + bool running = auto_continue; + // Process requests from the debugger. while (true) { // Wait for new command in the queue. @@ -2267,7 +2277,6 @@ void Debugger::NotifyMessageHandler(v8::DebugEvent event, // Get the response. v8::Local response; - bool running = false; if (!try_catch.HasCaught()) { // Get response string. if (!response_val->IsUndefined()) { @@ -2310,7 +2319,7 @@ void Debugger::NotifyMessageHandler(v8::DebugEvent event, // Return from debug event processing if either the VM is put into the // runnning state (through a continue command) or auto continue is active // and there are no more commands queued. - if (running || (auto_continue && !HasCommands())) { + if (running && !HasCommands()) { return; } } diff --git a/test/mjsunit/debug-backtrace.js b/test/mjsunit/debug-backtrace.js index 0c200ae..d15b2d2 100644 --- a/test/mjsunit/debug-backtrace.js +++ b/test/mjsunit/debug-backtrace.js @@ -69,6 +69,11 @@ ParsedResponse.prototype.body = function() { } +ParsedResponse.prototype.running = function() { + return this.response_.running; +} + + ParsedResponse.prototype.lookup = function(handle) { return this.refs_[handle]; } @@ -88,8 +93,9 @@ function listener(event, exec_state, event_data, data) { var frame; var source; - // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp; + // New copy of debug command processor paused state. + dcp = exec_state.debugCommandProcessor(false); // Get the backtrace. var json; @@ -114,6 +120,7 @@ function listener(event, exec_state, event_data, data) { assertEquals("g", response.lookup(frames[2].func.ref).name); assertEquals(3, frames[3].index); assertEquals("", response.lookup(frames[3].func.ref).name); + assertFalse(response.running(), "expected not running"); // Get backtrace with two frames. json = '{"seq":0,"type":"request","command":"backtrace","arguments":{"fromFrame":1,"toFrame":3}}' @@ -234,6 +241,17 @@ function listener(event, exec_state, event_data, data) { source = response.body(); assertEquals(Debug.findScript(f).source, source.source); + // New copy of debug command processor in running state. + dcp = exec_state.debugCommandProcessor(true); + // Get the backtrace. + json = '{"seq":0,"type":"request","command":"backtrace"}' + resp = dcp.processDebugJSONRequest(json); + response = new ParsedResponse(resp); + // It might be argueable, but we expect response to have body when + // not suspended + assertTrue(!!response.body(), "response should be null"); + assertTrue(response.running(), "expected running"); + listenerCalled = true; } } catch (e) { diff --git a/test/mjsunit/debug-changebreakpoint.js b/test/mjsunit/debug-changebreakpoint.js index 477c908..936523a 100644 --- a/test/mjsunit/debug-changebreakpoint.js +++ b/test/mjsunit/debug-changebreakpoint.js @@ -59,7 +59,7 @@ function listener(event, exec_state, event_data, data) { try { if (event == Debug.DebugEvent.Break) { // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); // Test some illegal clearbreakpoint requests. var request = '{' + base_request + '}' diff --git a/test/mjsunit/debug-clearbreakpoint.js b/test/mjsunit/debug-clearbreakpoint.js index 28920c5..59479f2 100644 --- a/test/mjsunit/debug-clearbreakpoint.js +++ b/test/mjsunit/debug-clearbreakpoint.js @@ -59,7 +59,7 @@ function listener(event, exec_state, event_data, data) { try { if (event == Debug.DebugEvent.Break) { // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); // Test some illegal clearbreakpoint requests. var request = '{' + base_request + '}' diff --git a/test/mjsunit/debug-clearbreakpointgroup.js b/test/mjsunit/debug-clearbreakpointgroup.js index eca9378..aad6c3a 100644 --- a/test/mjsunit/debug-clearbreakpointgroup.js +++ b/test/mjsunit/debug-clearbreakpointgroup.js @@ -60,7 +60,7 @@ function listener(event, exec_state, event_data, data) { try { if (event == Debug.DebugEvent.Break) { // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); // Clear breakpoint group 1. testArguments(dcp, '{"groupId":1}', true); diff --git a/test/mjsunit/debug-continue.js b/test/mjsunit/debug-continue.js index 0c11abc..a501aa9 100644 --- a/test/mjsunit/debug-continue.js +++ b/test/mjsunit/debug-continue.js @@ -44,7 +44,10 @@ function safeEval(code) { } } -function testArguments(dcp, arguments, success) { +function testArguments(exec_state, arguments, success) { + // Get the debug command processor in paused state. + var dcp = exec_state.debugCommandProcessor(false); + // Generate request with the supplied arguments var request; if (arguments) { @@ -65,25 +68,23 @@ function testArguments(dcp, arguments, success) { function listener(event, exec_state, event_data, data) { try { if (event == Debug.DebugEvent.Break) { - // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); // Test simple continue request. - testArguments(dcp, void 0, true); + testArguments(exec_state, void 0, true); // Test some illegal continue requests. - testArguments(dcp, '{"stepaction":"maybe"}', false); - testArguments(dcp, '{"stepcount":-1}', false); + testArguments(exec_state, '{"stepaction":"maybe"}', false); + testArguments(exec_state, '{"stepcount":-1}', false); // Test some legal continue requests. - testArguments(dcp, '{"stepaction":"in"}', true); - testArguments(dcp, '{"stepaction":"min"}', true); - testArguments(dcp, '{"stepaction":"next"}', true); - testArguments(dcp, '{"stepaction":"out"}', true); - testArguments(dcp, '{"stepcount":1}', true); - testArguments(dcp, '{"stepcount":10}', true); - testArguments(dcp, '{"stepcount":"10"}', true); - testArguments(dcp, '{"stepaction":"next","stepcount":10}', true); + testArguments(exec_state, '{"stepaction":"in"}', true); + testArguments(exec_state, '{"stepaction":"min"}', true); + testArguments(exec_state, '{"stepaction":"next"}', true); + testArguments(exec_state, '{"stepaction":"out"}', true); + testArguments(exec_state, '{"stepcount":1}', true); + testArguments(exec_state, '{"stepcount":10}', true); + testArguments(exec_state, '{"stepcount":"10"}', true); + testArguments(exec_state, '{"stepaction":"next","stepcount":10}', true); // Indicate that all was processed. listenerComplete = true; @@ -108,6 +109,6 @@ function g() { Debug.setBreakPoint(g, 0, 0); g(); +assertFalse(exception, "exception in listener") // Make sure that the debug event listener vas invoked. assertTrue(listenerComplete, "listener did not run to completion"); -assertFalse(exception, "exception in listener") diff --git a/test/mjsunit/debug-evaluate-recursive.js b/test/mjsunit/debug-evaluate-recursive.js index 9f037e5..6ee391b 100644 --- a/test/mjsunit/debug-evaluate-recursive.js +++ b/test/mjsunit/debug-evaluate-recursive.js @@ -44,7 +44,10 @@ function safeEval(code) { } } -function testRequest(dcp, arguments, success, result) { +function testRequest(exec_state, arguments, success, result) { + // Get the debug command processor in paused state. + var dcp = exec_state.debugCommandProcessor(false); + // Generate request with the supplied arguments. var request; if (arguments) { @@ -74,23 +77,20 @@ function listener(event, exec_state, event_data, data) { assertEquals(1, exec_state.frame(0).evaluate('f()', true).value()); assertEquals(2, exec_state.frame(0).evaluate('g()', true).value()); - // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); - // Call functions with break using the JSON protocol. Tests that argument // disable_break is default true. - testRequest(dcp, '{"expression":"f()"}', true, 1); - testRequest(dcp, '{"expression":"f()","frame":0}', true, 1); - testRequest(dcp, '{"expression":"g()"}', true, 2); - testRequest(dcp, '{"expression":"g()","frame":0}', true, 2); + testRequest(exec_state, '{"expression":"f()"}', true, 1); + testRequest(exec_state, '{"expression":"f()","frame":0}', true, 1); + testRequest(exec_state, '{"expression":"g()"}', true, 2); + testRequest(exec_state, '{"expression":"g()","frame":0}', true, 2); // Call functions with break using the JSON protocol. Tests passing // argument disable_break is default true. - testRequest(dcp, '{"expression":"f()","disable_break":true}', true, 1); - testRequest(dcp, '{"expression":"f()","frame":0,"disable_break":true}', + testRequest(exec_state, '{"expression":"f()","disable_break":true}', true, 1); + testRequest(exec_state, '{"expression":"f()","frame":0,"disable_break":true}', true, 1); - testRequest(dcp, '{"expression":"g()","disable_break":true}', true, 2); - testRequest(dcp, '{"expression":"g()","frame":0,"disable_break":true}', + testRequest(exec_state, '{"expression":"g()","disable_break":true}', true, 2); + testRequest(exec_state, '{"expression":"g()","frame":0,"disable_break":true}', true, 2); // Indicate that all was processed. @@ -146,9 +146,9 @@ Debug.setBreakPoint(f, 2, 0); // Cause a debug break event. debugger; +assertFalse(exception, "exception in listener") // Make sure that the debug event listener vas invoked. assertTrue(listenerComplete); -assertFalse(exception, "exception in listener") // Remove the debug event listener. Debug.setListener(null); @@ -161,7 +161,7 @@ Debug.setBreakPoint(f, 2, 0); debugger; +assertFalse(exception, "exception in listener") // Make sure that the debug event listener vas invoked. assertTrue(listenerComplete); -assertFalse(exception, "exception in listener") assertEquals(2, break_count); diff --git a/test/mjsunit/debug-evaluate.js b/test/mjsunit/debug-evaluate.js index 5c5734f..c477907 100644 --- a/test/mjsunit/debug-evaluate.js +++ b/test/mjsunit/debug-evaluate.js @@ -59,14 +59,15 @@ function testRequest(dcp, arguments, success, result) { } else { assertFalse(response.success, request + ' -> ' + response.message); } - assertFalse(response.running, request + ' -> expected not running'); + assertEquals(response.running, "unspecified_running_state", + request + ' -> expected not running'); } function listener(event, exec_state, event_data, data) { try { if (event == Debug.DebugEvent.Break) { // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); // Test some illegal evaluate requests. testRequest(dcp, void 0, false); @@ -112,6 +113,6 @@ a = 1; Debug.setBreakPoint(f, 2, 0); g(); +assertFalse(exception, "exception in listener") // Make sure that the debug event listener vas invoked. assertTrue(listenerComplete, "listener did not run to completion"); -assertFalse(exception, "exception in listener") diff --git a/test/mjsunit/debug-handle.js b/test/mjsunit/debug-handle.js index c7ab76a..98875ce 100644 --- a/test/mjsunit/debug-handle.js +++ b/test/mjsunit/debug-handle.js @@ -43,7 +43,10 @@ function safeEval(code) { // Send an evaluation request and return the handle of the result. -function evaluateRequest(dcp, arguments) { +function evaluateRequest(exec_state, arguments) { + // Get the debug command processor. + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); + // The base part of all evaluate requests. var base_request = '"seq":0,"type":"request","command":"evaluate"' @@ -63,7 +66,10 @@ function evaluateRequest(dcp, arguments) { // Send a lookup request and return the evaluated JSON response. -function lookupRequest(dcp, arguments, success) { +function lookupRequest(exec_state, arguments, success) { + // Get the debug command processor. + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); + // The base part of all lookup requests. var base_request = '"seq":0,"type":"request","command":"lookup"' @@ -81,7 +87,7 @@ function lookupRequest(dcp, arguments, success) { } else { assertFalse(response.success, request + ' -> ' + response.message); } - assertFalse(response.running, request + ' -> expected not running'); + assertEquals(response.running, dcp.isRunning(), request + ' -> expected not running'); return response; } @@ -90,26 +96,23 @@ function lookupRequest(dcp, arguments, success) { function listener(event, exec_state, event_data, data) { try { if (event == Debug.DebugEvent.Break) { - // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); - // Test some illegal lookup requests. - lookupRequest(dcp, void 0, false); - lookupRequest(dcp, '{"handles":["a"]}', false); - lookupRequest(dcp, '{"handles":[-1]}', false); + lookupRequest(exec_state, void 0, false); + lookupRequest(exec_state, '{"handles":["a"]}', false); + lookupRequest(exec_state, '{"handles":[-1]}', false); // Evaluate and get some handles. - var handle_o = evaluateRequest(dcp, '{"expression":"o"}'); - var handle_p = evaluateRequest(dcp, '{"expression":"p"}'); - var handle_b = evaluateRequest(dcp, '{"expression":"a"}'); - var handle_a = evaluateRequest(dcp, '{"expression":"b","frame":1}'); + var handle_o = evaluateRequest(exec_state, '{"expression":"o"}'); + var handle_p = evaluateRequest(exec_state, '{"expression":"p"}'); + var handle_b = evaluateRequest(exec_state, '{"expression":"a"}'); + var handle_a = evaluateRequest(exec_state, '{"expression":"b","frame":1}'); assertEquals(handle_o, handle_a); assertEquals(handle_a, handle_b); assertFalse(handle_o == handle_p, "o and p have he same handle"); var response; var count; - response = lookupRequest(dcp, '{"handles":[' + handle_o + ']}', true); + response = lookupRequest(exec_state, '{"handles":[' + handle_o + ']}', true); var obj = response.body[handle_o]; assertTrue(!!obj, 'Object not found: ' + handle_o); assertEquals(handle_o, obj.handle); @@ -127,20 +130,20 @@ function listener(event, exec_state, event_data, data) { } } assertEquals(2, count, 'Either "o" or "p" not found'); - response = lookupRequest(dcp, '{"handles":[' + handle_p + ']}', true); + response = lookupRequest(exec_state, '{"handles":[' + handle_p + ']}', true); obj = response.body[handle_p]; assertTrue(!!obj, 'Object not found: ' + handle_p); assertEquals(handle_p, obj.handle); // Check handles for functions on the stack. - var handle_f = evaluateRequest(dcp, '{"expression":"f"}'); - var handle_g = evaluateRequest(dcp, '{"expression":"g"}'); - var handle_caller = evaluateRequest(dcp, '{"expression":"f.caller"}'); + var handle_f = evaluateRequest(exec_state, '{"expression":"f"}'); + var handle_g = evaluateRequest(exec_state, '{"expression":"g"}'); + var handle_caller = evaluateRequest(exec_state, '{"expression":"f.caller"}'); assertFalse(handle_f == handle_g, "f and g have he same handle"); assertEquals(handle_g, handle_caller, "caller for f should be g"); - response = lookupRequest(dcp, '{"handles":[' + handle_f + ']}', true); + response = lookupRequest(exec_state, '{"handles":[' + handle_f + ']}', true); obj = response.body[handle_f]; assertEquals(handle_f, obj.handle); @@ -151,14 +154,14 @@ function listener(event, exec_state, event_data, data) { switch (obj.properties[i].name) { case 'name': var response_name; - response_name = lookupRequest(dcp, arguments, true); + response_name = lookupRequest(exec_state, arguments, true); assertEquals('string', response_name.body[ref].type); assertEquals("f", response_name.body[ref].value); count++; break; case 'length': var response_length; - response_length = lookupRequest(dcp, arguments, true); + response_length = lookupRequest(exec_state, arguments, true); assertEquals('number', response_length.body[ref].type); assertEquals(1, response_length.body[ref].value); count++; @@ -179,7 +182,7 @@ function listener(event, exec_state, event_data, data) { } var arguments = '{"handles":[' + refs.join(',') + ']}'; - response = lookupRequest(dcp, arguments, true); + response = lookupRequest(exec_state, arguments, true); count = 0; for (i in obj.properties) { var ref = obj.properties[i].ref; @@ -244,6 +247,6 @@ p.o = o; p.p = p; g(o); +assertFalse(exception, "exception in listener") // Make sure that the debug event listener vas invoked. assertTrue(listenerComplete, "listener did not run to completion: " + exception); -assertFalse(exception, "exception in listener") diff --git a/test/mjsunit/debug-mirror-cache.js b/test/mjsunit/debug-mirror-cache.js index d15146f..5b85306 100644 --- a/test/mjsunit/debug-mirror-cache.js +++ b/test/mjsunit/debug-mirror-cache.js @@ -41,7 +41,7 @@ function g() { Debug = debug.Debug listenerCallCount = 0; -listenerExceptionCount = 0; +listenerExceptions = []; function listener(event, exec_state, event_data, data) { @@ -54,8 +54,8 @@ function listener(event, exec_state, event_data, data) { assertEquals(0, debug.next_handle_, "Mirror cache not cleared"); assertEquals(0, debug.mirror_cache_.length, "Mirror cache not cleared"); - // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + // Get the debug command processor in paused state. + var dcp = exec_state.debugCommandProcessor(false); // Make a backtrace request to create some mirrors. var json; @@ -68,7 +68,7 @@ function listener(event, exec_state, event_data, data) { } } catch (e) { print(e); - listenerExceptionCount++; + listenerExceptions.push(e); }; }; @@ -79,7 +79,7 @@ Debug.setListener(listener); debugger; debugger; +assertEquals([], listenerExceptions, "Exception in listener"); // Make sure that the debug event listener vas invoked. assertEquals(2, listenerCallCount, "Listener not called"); -assertEquals(0, listenerExceptionCount, "Exception in listener"); diff --git a/test/mjsunit/debug-references.js b/test/mjsunit/debug-references.js index 1fde1ac..452761c 100644 --- a/test/mjsunit/debug-references.js +++ b/test/mjsunit/debug-references.js @@ -66,14 +66,14 @@ function testRequest(dcp, arguments, success, count) { } else { assertFalse(response.success, request + ' -> ' + response.message); } - assertFalse(response.running, request + ' -> expected not running'); + assertEquals(response.running, dcp.isRunning(), request + ' -> expected not running'); } function listener(event, exec_state, event_data, data) { try { if (event == Debug.DebugEvent.Break) { // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); // Test some illegal references requests. testRequest(dcp, void 0, false); diff --git a/test/mjsunit/debug-scopes.js b/test/mjsunit/debug-scopes.js index e87cbb7..af29df9 100644 --- a/test/mjsunit/debug-scopes.js +++ b/test/mjsunit/debug-scopes.js @@ -92,7 +92,7 @@ function CheckScopeChain(scopes, exec_state) { } // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); // Send a scopes request and check the result. var json; @@ -155,7 +155,7 @@ function CheckScopeContent(content, number, exec_state) { assertEquals(count, scope_size); // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); // Send a scope request for information on a single scope and check the // result. diff --git a/test/mjsunit/debug-scripts-request.js b/test/mjsunit/debug-scripts-request.js index 80b3bce..41bff0e 100644 --- a/test/mjsunit/debug-scripts-request.js +++ b/test/mjsunit/debug-scripts-request.js @@ -60,7 +60,7 @@ function listener(event, exec_state, event_data, data) { try { if (event == Debug.DebugEvent.Break) { // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); // Test illegal scripts requests. testArguments(dcp, '{"types":"xx"}', false); diff --git a/test/mjsunit/debug-setbreakpoint.js b/test/mjsunit/debug-setbreakpoint.js index f8d9b15..08492b4 100644 --- a/test/mjsunit/debug-setbreakpoint.js +++ b/test/mjsunit/debug-setbreakpoint.js @@ -69,7 +69,7 @@ function listener(event, exec_state, event_data, data) { try { if (event == Debug.DebugEvent.Break) { // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp = exec_state.debugCommandProcessor("unspecified_running_state"); // Test some illegal setbreakpoint requests. var request = '{' + base_request + '}' diff --git a/test/mjsunit/debug-suspend.js b/test/mjsunit/debug-suspend.js new file mode 100644 index 0000000..73a2e8c --- /dev/null +++ b/test/mjsunit/debug-suspend.js @@ -0,0 +1,96 @@ +// Copyright 2008 the V8 project authors. All rights reserved. +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following +// disclaimer in the documentation and/or other materials provided +// with the distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived +// from this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +// Flags: --expose-debug-as debug +// Get the Debug object exposed from the debug context global object. +Debug = debug.Debug + +// Simple function which stores the last debug event. +listenerComplete = false; +exception = false; + +var base_backtrace_request = '"seq":0,"type":"request","command":"backtrace"' +var base_suspend_request = '"seq":0,"type":"request","command":"suspend"' + +function safeEval(code) { + try { + return eval('(' + code + ')'); + } catch (e) { + assertEquals(void 0, e); + return undefined; + } +} + +function testArguments(exec_state) { + // Get the debug command processor in running state. + var dcp = exec_state.debugCommandProcessor(true); + + assertTrue(dcp.isRunning()); + + var backtrace_request = '{' + base_backtrace_request + '}' + var backtrace_response = safeEval(dcp.processDebugJSONRequest(backtrace_request)); + + assertTrue(backtrace_response.success); + + assertTrue(backtrace_response.running, backtrace_request + ' -> expected running'); + + assertTrue(dcp.isRunning()); + + var suspend_request = '{' + base_suspend_request + '}' + var suspend_response = safeEval(dcp.processDebugJSONRequest(suspend_request)); + + assertTrue(suspend_response.success); + + assertFalse(suspend_response.running, suspend_request + ' -> expected not running'); + + assertFalse(dcp.isRunning()); +} + +function listener(event, exec_state, event_data, data) { + try { + if (event == Debug.DebugEvent.Break) { + + // Test simple suspend request. + testArguments(exec_state); + + // Indicate that all was processed. + listenerComplete = true; + } + } catch (e) { + exception = e + }; +}; + +// Add the debug event listener. +Debug.setListener(listener); + +// Stop debugger and check that suspend command changes running flag. +debugger; + +assertFalse(exception, "exception in listener") +// Make sure that the debug event listener vas invoked. +assertTrue(listenerComplete, "listener did not run to completion"); diff --git a/test/mjsunit/regress/regress-1081309.js b/test/mjsunit/regress/regress-1081309.js index a771ac0..009ede1 100644 --- a/test/mjsunit/regress/regress-1081309.js +++ b/test/mjsunit/regress/regress-1081309.js @@ -69,7 +69,7 @@ function listener(event, exec_state, event_data, data) { // 0: [anonymous] // Get the debug command processor. - var dcp = exec_state.debugCommandProcessor(); + var dcp = exec_state.debugCommandProcessor(false); // Get the backtrace. var json; @@ -105,6 +105,6 @@ try { // Ignore the exception "Cannot call method 'x' of undefined" } +assertFalse(exception, "exception in listener", exception) // Make sure that the debug event listener vas invoked. assertTrue(listenerCalled, "listener not called"); -assertFalse(exception, "exception in listener", exception) -- 2.7.4