Chromium Code Reviews| Index: src/isolate.cc | 
| diff --git a/src/isolate.cc b/src/isolate.cc | 
| index 3542b994ff3338ffd3860b763f49b4730dfe6d54..802057eaa789bf3bd812eda991172665dcdc2978 100644 | 
| --- a/src/isolate.cc | 
| +++ b/src/isolate.cc | 
| @@ -1144,7 +1144,7 @@ void Isolate::DoThrow(Object* exception, MessageLocation* location) { | 
| } | 
| -bool Isolate::IsExternallyCaught() { | 
| +bool Isolate::HasExternallyCaught() { | 
| ASSERT(has_pending_exception()); | 
| if ((thread_local_top()->catcher_ == NULL) || | 
| @@ -1154,10 +1154,11 @@ bool Isolate::IsExternallyCaught() { | 
| return false; | 
| } | 
| - if (!is_catchable_by_javascript(pending_exception())) { | 
| - return true; | 
| - } | 
| + return true; | 
| +} | 
| + | 
| +bool Isolate::IsFinallyOnTop() { | 
| // Get the address of the external handler so we can compare the address to | 
| // determine which one is closer to the top of the stack. | 
| Address external_handler_address = | 
| @@ -1177,18 +1178,18 @@ bool Isolate::IsExternallyCaught() { | 
| StackHandler::FromAddress(Isolate::handler(thread_local_top())); | 
| while (handler != NULL && handler->address() < external_handler_address) { | 
| ASSERT(!handler->is_catch()); | 
| - if (handler->is_finally()) return false; | 
| + if (handler->is_finally()) return true; | 
| handler = handler->next(); | 
| } | 
| - return true; | 
| + return false; | 
| } | 
| void Isolate::ReportPendingMessages() { | 
| ASSERT(has_pending_exception()); | 
| - PropagatePendingExceptionToExternalTryCatch(); | 
| + bool canClearMessage = PropagatePendingExceptionToExternalTryCatch(); | 
| HandleScope scope(this); | 
| if (thread_local_top_.pending_exception_ == | 
| @@ -1215,7 +1216,8 @@ void Isolate::ReportPendingMessages() { | 
| } | 
| } | 
| } | 
| - clear_pending_message(); | 
| + if (canClearMessage) | 
| + clear_pending_message(); | 
| } | 
| @@ -1722,13 +1724,17 @@ void Isolate::InitializeThreadLocal() { | 
| } | 
| -void Isolate::PropagatePendingExceptionToExternalTryCatch() { | 
| +bool Isolate::PropagatePendingExceptionToExternalTryCatch() { | 
| ASSERT(has_pending_exception()); | 
| - bool external_caught = IsExternallyCaught(); | 
| - thread_local_top_.external_caught_exception_ = external_caught; | 
| + bool has_externaly_caught = HasExternallyCaught(); | 
| 
 
vsevik
2014/06/02 09:19:55
has_external_try_catch
 
 | 
| + bool is_finally_on_top = IsFinallyOnTop(); | 
| - if (!external_caught) return; | 
| + bool next_externaly_caught = has_externaly_caught && !is_finally_on_top; | 
| 
 
vsevik
2014/06/02 09:19:55
should_propagate_now
 
 | 
| + thread_local_top_.external_caught_exception_ = next_externaly_caught; | 
| + | 
| + if (!has_externaly_caught) return true; | 
| 
 
vsevik
2014/06/02 09:19:55
if (!should_propagate_now) return !has_external_tr
 
 | 
| + if (is_finally_on_top) return false; | 
| if (thread_local_top_.pending_exception_ == | 
| heap()->termination_exception()) { | 
| @@ -1745,13 +1751,14 @@ void Isolate::PropagatePendingExceptionToExternalTryCatch() { | 
| handler->has_terminated_ = false; | 
| handler->exception_ = pending_exception(); | 
| // Propagate to the external try-catch only if we got an actual message. | 
| - if (thread_local_top_.pending_message_obj_->IsTheHole()) return; | 
| + if (thread_local_top_.pending_message_obj_->IsTheHole()) return true; | 
| handler->message_obj_ = thread_local_top_.pending_message_obj_; | 
| handler->message_script_ = thread_local_top_.pending_message_script_; | 
| handler->message_start_pos_ = thread_local_top_.pending_message_start_pos_; | 
| handler->message_end_pos_ = thread_local_top_.pending_message_end_pos_; | 
| } | 
| + return true; | 
| } |