#include "src/execution.h"
#include "src/full-codegen.h"
#include "src/global-handles.h"
-#include "src/ic.h"
-#include "src/ic-inl.h"
#include "src/isolate-inl.h"
#include "src/list.h"
#include "src/log.h"
#include "src/messages.h"
#include "src/natives.h"
-#include "src/stub-cache.h"
#include "include/v8-debug.h"
// TODO(isolates): frames_are_dropped_?
thread_local_.current_debug_scope_ = NULL;
thread_local_.restarter_frame_function_pointer_ = NULL;
- thread_local_.promise_on_stack_ = NULL;
}
Handle<JSFunction> function =
factory->NewFunctionFromSharedFunctionInfo(function_info, context);
- Handle<Object> exception;
- MaybeHandle<Object> result =
- Execution::TryCall(function,
- handle(context->global_proxy()),
- 0,
- NULL,
- &exception);
+ MaybeHandle<Object> maybe_exception;
+ MaybeHandle<Object> result = Execution::TryCall(
+ function, handle(context->global_proxy()), 0, NULL, &maybe_exception);
// Check for caught exceptions.
if (result.is_null()) {
isolate, "error_loading_debugger", &computed_location,
Vector<Handle<Object> >::empty(), Handle<JSArray>());
DCHECK(!isolate->has_pending_exception());
- if (!exception.is_null()) {
+ Handle<Object> exception;
+ if (maybe_exception.ToHandle(&exception)) {
isolate->set_pending_exception(*exception);
MessageHandler::ReportMessage(isolate, NULL, message);
isolate->clear_pending_exception();
// Expose the builtins object in the debugger context.
Handle<String> key = isolate_->factory()->InternalizeOneByteString(
- STATIC_ASCII_VECTOR("builtins"));
+ STATIC_CHAR_VECTOR("builtins"));
Handle<GlobalObject> global =
Handle<GlobalObject>(context->global_object(), isolate_);
Handle<JSBuiltinsObject> builtin =
ClearAllBreakPoints();
ClearStepping();
- // Match unmatched PopPromise calls.
- while (thread_local_.promise_on_stack_) PopPromise();
-
// Return debugger is not loaded.
if (!is_loaded()) return;
// Get the function IsBreakPointTriggered (defined in debug-debugger.js).
Handle<String> is_break_point_triggered_string =
factory->InternalizeOneByteString(
- STATIC_ASCII_VECTOR("IsBreakPointTriggered"));
+ STATIC_CHAR_VECTOR("IsBreakPointTriggered"));
Handle<GlobalObject> debug_global(debug_context()->global_object());
Handle<JSFunction> check_break_point =
Handle<JSFunction>::cast(Object::GetProperty(
Handle<Object> result;
if (!Execution::TryCall(check_break_point,
isolate_->js_builtins_object(),
- ARRAY_SIZE(argv),
+ arraysize(argv),
argv).ToHandle(&result)) {
return false;
}
}
-PromiseOnStack::PromiseOnStack(Isolate* isolate, PromiseOnStack* prev,
- Handle<JSObject> promise)
- : isolate_(isolate), prev_(prev) {
- handler_ = StackHandler::FromAddress(
- Isolate::handler(isolate->thread_local_top()));
- promise_ =
- Handle<JSObject>::cast(isolate->global_handles()->Create(*promise));
-}
-
-
-PromiseOnStack::~PromiseOnStack() {
- isolate_->global_handles()->Destroy(
- Handle<Object>::cast(promise_).location());
-}
-
-
-void Debug::PushPromise(Handle<JSObject> promise) {
- PromiseOnStack* prev = thread_local_.promise_on_stack_;
- thread_local_.promise_on_stack_ = new PromiseOnStack(isolate_, prev, promise);
-}
-
-
-void Debug::PopPromise() {
- if (thread_local_.promise_on_stack_ == NULL) return;
- PromiseOnStack* prev = thread_local_.promise_on_stack_->prev();
- delete thread_local_.promise_on_stack_;
- thread_local_.promise_on_stack_ = prev;
-}
-
-
-Handle<Object> Debug::GetPromiseOnStackOnThrow() {
- Handle<Object> undefined = isolate_->factory()->undefined_value();
- if (thread_local_.promise_on_stack_ == NULL) return undefined;
- StackHandler* promise_try = thread_local_.promise_on_stack_->handler();
- // Find the top-most try-catch handler.
- StackHandler* handler = StackHandler::FromAddress(
- Isolate::handler(isolate_->thread_local_top()));
- do {
- if (handler == promise_try) {
- // Mark the pushed try-catch handler to prevent a later duplicate event
- // triggered with the following reject.
- return thread_local_.promise_on_stack_->promise();
- }
- handler = handler->next();
- // Throwing inside a Promise can be intercepted by an inner try-catch, so
- // we stop at the first try-catch handler.
- } while (handler != NULL && !handler->is_catch());
- return undefined;
-}
-
-
bool Debug::PromiseHasRejectHandler(Handle<JSObject> promise) {
Handle<JSFunction> fun = Handle<JSFunction>::cast(
JSObject::GetDataProperty(isolate_->js_builtins_object(),
- isolate_->factory()->NewStringFromStaticAscii(
+ isolate_->factory()->NewStringFromStaticChars(
"PromiseHasRejectHandler")));
Handle<Object> result =
Execution::Call(isolate_, fun, promise, 0, NULL).ToHandleChecked();
// Make sure that the shared full code is compiled with debug
// break slots.
if (!function->shared()->code()->has_debug_break_slots()) {
- MaybeHandle<Code> code = Compiler::GetCodeForDebugging(function);
+ MaybeHandle<Code> code = Compiler::GetDebugCode(function);
// Recompilation can fail. In that case leave the code as it was.
if (!code.is_null()) function->ReplaceCode(*code.ToHandleChecked());
} else {
Deoptimizer::DeoptimizeAll(isolate_);
- Handle<Code> lazy_compile = isolate_->builtins()->CompileUnoptimized();
+ Handle<Code> lazy_compile = isolate_->builtins()->CompileLazy();
// There will be at least one break point when we are done.
has_break_points_ = true;
Factory* factory = isolate_->factory();
Handle<GlobalObject> global(isolate_->global_object());
JSObject::SetProperty(global,
- factory->NewStringFromAsciiChecked("next_handle_"),
- handle(Smi::FromInt(0), isolate_),
- SLOPPY).Check();
+ factory->NewStringFromAsciiChecked("next_handle_"),
+ handle(Smi::FromInt(0), isolate_), SLOPPY).Check();
JSObject::SetProperty(global,
- factory->NewStringFromAsciiChecked("mirror_cache_"),
- factory->NewJSArray(0, FAST_ELEMENTS),
- SLOPPY).Check();
+ factory->NewStringFromAsciiChecked("mirror_cache_"),
+ factory->NewJSArray(0, FAST_ELEMENTS), SLOPPY).Check();
}
MaybeHandle<Object> Debug::MakeExecutionState() {
// Create the execution state object.
Handle<Object> argv[] = { isolate_->factory()->NewNumberFromInt(break_id()) };
- return MakeJSObject("MakeExecutionState", ARRAY_SIZE(argv), argv);
+ return MakeJSObject("MakeExecutionState", arraysize(argv), argv);
}
// Create the new break event object.
Handle<Object> argv[] = { isolate_->factory()->NewNumberFromInt(break_id()),
break_points_hit };
- return MakeJSObject("MakeBreakEvent", ARRAY_SIZE(argv), argv);
+ return MakeJSObject("MakeBreakEvent", arraysize(argv), argv);
}
exception,
isolate_->factory()->ToBoolean(uncaught),
promise };
- return MakeJSObject("MakeExceptionEvent", ARRAY_SIZE(argv), argv);
+ return MakeJSObject("MakeExceptionEvent", arraysize(argv), argv);
}
Handle<Object> script_wrapper = Script::GetWrapper(script);
Handle<Object> argv[] = { script_wrapper,
isolate_->factory()->NewNumberFromInt(type) };
- return MakeJSObject("MakeCompileEvent", ARRAY_SIZE(argv), argv);
+ return MakeJSObject("MakeCompileEvent", arraysize(argv), argv);
}
MaybeHandle<Object> Debug::MakePromiseEvent(Handle<JSObject> event_data) {
// Create the promise event object.
Handle<Object> argv[] = { event_data };
- return MakeJSObject("MakePromiseEvent", ARRAY_SIZE(argv), argv);
+ return MakeJSObject("MakePromiseEvent", arraysize(argv), argv);
}
MaybeHandle<Object> Debug::MakeAsyncTaskEvent(Handle<JSObject> task_event) {
// Create the async task event object.
Handle<Object> argv[] = { task_event };
- return MakeJSObject("MakeAsyncTaskEvent", ARRAY_SIZE(argv), argv);
+ return MakeJSObject("MakeAsyncTaskEvent", arraysize(argv), argv);
}
void Debug::OnThrow(Handle<Object> exception, bool uncaught) {
if (in_debug_scope() || ignore_events()) return;
+ // Temporarily clear any scheduled_exception to allow evaluating
+ // JavaScript from the debug event handler.
HandleScope scope(isolate_);
- OnException(exception, uncaught, GetPromiseOnStackOnThrow());
+ Handle<Object> scheduled_exception;
+ if (isolate_->has_scheduled_exception()) {
+ scheduled_exception = handle(isolate_->scheduled_exception(), isolate_);
+ isolate_->clear_scheduled_exception();
+ }
+ OnException(exception, uncaught, isolate_->GetPromiseOnStackOnThrow());
+ if (!scheduled_exception.is_null()) {
+ isolate_->thread_local_top()->scheduled_exception_ = *scheduled_exception;
+ }
}
// Get the function UpdateScriptBreakPoints (defined in debug-debugger.js).
Handle<String> update_script_break_points_string =
isolate_->factory()->InternalizeOneByteString(
- STATIC_ASCII_VECTOR("UpdateScriptBreakPoints"));
+ STATIC_CHAR_VECTOR("UpdateScriptBreakPoints"));
Handle<GlobalObject> debug_global(debug_context()->global_object());
Handle<Object> update_script_break_points =
Object::GetProperty(
Handle<Object> argv[] = { wrapper };
if (Execution::TryCall(Handle<JSFunction>::cast(update_script_break_points),
isolate_->js_builtins_object(),
- ARRAY_SIZE(argv),
+ arraysize(argv),
argv).is_null()) {
return;
}
event_listener_data_ };
Handle<JSReceiver> global(isolate_->global_proxy());
Execution::TryCall(Handle<JSFunction>::cast(event_listener_),
- global, ARRAY_SIZE(argv), argv);
+ global, arraysize(argv), argv);
}
}
Handle<String> request_text = isolate_->factory()->NewStringFromTwoByte(
command_text).ToHandleChecked();
Handle<Object> request_args[] = { request_text };
- Handle<Object> exception;
Handle<Object> answer_value;
Handle<String> answer;
- MaybeHandle<Object> maybe_result = Execution::TryCall(
- process_debug_request, cmd_processor, 1, request_args, &exception);
+ MaybeHandle<Object> maybe_exception;
+ MaybeHandle<Object> maybe_result =
+ Execution::TryCall(process_debug_request, cmd_processor, 1,
+ request_args, &maybe_exception);
if (maybe_result.ToHandle(&answer_value)) {
if (answer_value->IsUndefined()) {
Handle<Object> is_running_args[] = { answer };
maybe_result = Execution::Call(
isolate_, is_running, cmd_processor, 1, is_running_args);
- running = maybe_result.ToHandleChecked()->IsTrue();
+ Handle<Object> result;
+ if (!maybe_result.ToHandle(&result)) break;
+ running = result->IsTrue();
} else {
- answer = Handle<String>::cast(
- Execution::ToString(isolate_, exception).ToHandleChecked());
+ Handle<Object> exception;
+ if (!maybe_exception.ToHandle(&exception)) break;
+ Handle<Object> result;
+ if (!Execution::ToString(isolate_, exception).ToHandle(&result)) break;
+ answer = Handle<String>::cast(result);
}
// Return the result.
// running state (through a continue command) or auto continue is active
// and there are no more commands queued.
} while (!running || has_commands());
+ command_queue_.Clear();
}
isolate_,
fun,
Handle<Object>(debug_context()->global_proxy(), isolate_),
- ARRAY_SIZE(argv),
+ arraysize(argv),
argv);
}