| Index: src/isolate.cc
|
| diff --git a/src/isolate.cc b/src/isolate.cc
|
| index 215296d735cc5b8b9698cfc67d9dc0cfa3bd7208..cfd5a3d8e6c62aac9414feab62e239376efae98d 100644
|
| --- a/src/isolate.cc
|
| +++ b/src/isolate.cc
|
| @@ -79,6 +79,7 @@ void ThreadLocalTop::InitializeInternal() {
|
| save_context_ = NULL;
|
| catcher_ = NULL;
|
| top_lookup_result_ = NULL;
|
| + promise_on_stack_ = NULL;
|
|
|
| // These members are re-initialized later after deserialization
|
| // is complete.
|
| @@ -100,6 +101,12 @@ void ThreadLocalTop::Initialize() {
|
| }
|
|
|
|
|
| +void ThreadLocalTop::Free() {
|
| + // Match unmatched PopPromise calls.
|
| + while (promise_on_stack_) isolate_->PopPromise();
|
| +}
|
| +
|
| +
|
| base::Thread::LocalStorageKey Isolate::isolate_key_;
|
| base::Thread::LocalStorageKey Isolate::thread_id_key_;
|
| base::Thread::LocalStorageKey Isolate::per_isolate_thread_data_key_;
|
| @@ -1289,6 +1296,48 @@ bool Isolate::OptionalRescheduleException(bool is_bottom_call) {
|
| }
|
|
|
|
|
| +void Isolate::PushPromise(Handle<JSObject> promise) {
|
| + ThreadLocalTop* tltop = thread_local_top();
|
| + PromiseOnStack* prev = tltop->promise_on_stack_;
|
| + StackHandler* handler = StackHandler::FromAddress(Isolate::handler(tltop));
|
| + Handle<JSObject> global_handle =
|
| + Handle<JSObject>::cast(global_handles()->Create(*promise));
|
| + tltop->promise_on_stack_ = new PromiseOnStack(handler, global_handle, prev);
|
| +}
|
| +
|
| +
|
| +void Isolate::PopPromise() {
|
| + ThreadLocalTop* tltop = thread_local_top();
|
| + if (tltop->promise_on_stack_ == NULL) return;
|
| + PromiseOnStack* prev = tltop->promise_on_stack_->prev();
|
| + Handle<Object> global_handle = tltop->promise_on_stack_->promise();
|
| + delete tltop->promise_on_stack_;
|
| + tltop->promise_on_stack_ = prev;
|
| + global_handles()->Destroy(global_handle.location());
|
| +}
|
| +
|
| +
|
| +Handle<Object> Isolate::GetPromiseOnStackOnThrow() {
|
| + Handle<Object> undefined = factory()->undefined_value();
|
| + ThreadLocalTop* tltop = thread_local_top();
|
| + if (tltop->promise_on_stack_ == NULL) return undefined;
|
| + StackHandler* promise_try = tltop->promise_on_stack_->handler();
|
| + // Find the top-most try-catch handler.
|
| + StackHandler* handler = StackHandler::FromAddress(Isolate::handler(tltop));
|
| + do {
|
| + if (handler == promise_try) {
|
| + // Mark the pushed try-catch handler to prevent a later duplicate event
|
| + // triggered with the following reject.
|
| + return tltop->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;
|
| +}
|
| +
|
| +
|
| void Isolate::SetCaptureStackTraceForUncaughtExceptions(
|
| bool capture,
|
| int frame_limit,
|
| @@ -1552,6 +1601,8 @@ void Isolate::Deinit() {
|
|
|
| debug()->Unload();
|
|
|
| + FreeThreadResources();
|
| +
|
| if (concurrent_recompilation_enabled()) {
|
| optimizing_compiler_thread_->Stop();
|
| delete optimizing_compiler_thread_;
|
|
|