Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/native_entry.h" | 5 #include "vm/native_entry.h" |
| 6 | 6 |
| 7 #include "include/dart_api.h" | 7 #include "include/dart_api.h" |
| 8 | 8 |
| 9 #include "vm/bootstrap.h" | 9 #include "vm/bootstrap.h" |
| 10 #include "vm/code_patcher.h" | 10 #include "vm/code_patcher.h" |
| (...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 84 uword NativeEntry::NativeCallWrapperEntry() { | 84 uword NativeEntry::NativeCallWrapperEntry() { |
| 85 uword entry = reinterpret_cast<uword>(NativeEntry::NativeCallWrapper); | 85 uword entry = reinterpret_cast<uword>(NativeEntry::NativeCallWrapper); |
| 86 #if defined(USING_SIMULATOR) | 86 #if defined(USING_SIMULATOR) |
| 87 entry = Simulator::RedirectExternalReference( | 87 entry = Simulator::RedirectExternalReference( |
| 88 entry, Simulator::kNativeCall, NativeEntry::kNumCallWrapperArguments); | 88 entry, Simulator::kNativeCall, NativeEntry::kNumCallWrapperArguments); |
| 89 #endif | 89 #endif |
| 90 return entry; | 90 return entry; |
| 91 } | 91 } |
| 92 | 92 |
| 93 | 93 |
| 94 void NativeEntry::PropagateErrors(NativeArguments* arguments) { | |
| 95 RawObject* raw_retval = arguments->ReturnValue(); | |
| 96 if (raw_retval->IsHeapObject() && | |
| 97 RawObject::IsErrorClassId(raw_retval->GetClassId())) { | |
| 98 Thread* thread = arguments->thread(); | |
| 99 const Object* error; | |
| 100 { | |
| 101 // We use a NoSafepointScope to make sure that the raw_retval | |
| 102 // is preserved while we are unwinding scopes. | |
| 103 NoSafepointScope no_safepoint; | |
| 104 thread->UnwindScopes(thread->top_exit_frame_info()); | |
| 105 // The thread->zone() now is different here than before we unwound. | |
| 106 error = &Object::Handle(thread->zone(), raw_retval); | |
| 107 } | |
|
siva
2016/02/03 16:50:00
Why do you declare it as:
const Object* error;
w
turnidge
2016/02/03 19:13:46
Done.
| |
| 108 Exceptions::PropagateError(Error::Cast(*error)); | |
| 109 UNREACHABLE(); | |
| 110 } | |
| 111 } | |
| 112 | |
| 113 | |
| 94 void NativeEntry::NativeCallWrapper(Dart_NativeArguments args, | 114 void NativeEntry::NativeCallWrapper(Dart_NativeArguments args, |
| 95 Dart_NativeFunction func) { | 115 Dart_NativeFunction func) { |
| 96 CHECK_STACK_ALIGNMENT; | 116 CHECK_STACK_ALIGNMENT; |
| 97 VERIFY_ON_TRANSITION; | 117 VERIFY_ON_TRANSITION; |
| 98 NativeArguments* arguments = reinterpret_cast<NativeArguments*>(args); | 118 NativeArguments* arguments = reinterpret_cast<NativeArguments*>(args); |
| 99 /* Tell MemorySanitizer 'arguments' is initialized by generated code. */ | 119 /* Tell MemorySanitizer 'arguments' is initialized by generated code. */ |
| 100 MSAN_UNPOISON(arguments, sizeof(*arguments)); | 120 MSAN_UNPOISON(arguments, sizeof(*arguments)); |
| 101 Thread* thread = arguments->thread(); | 121 Thread* thread = arguments->thread(); |
| 102 if (!arguments->IsNativeAutoSetupScope()) { | 122 if (!arguments->IsNativeAutoSetupScope()) { |
| 103 TransitionGeneratedToNative transition(thread); | 123 TransitionGeneratedToNative transition(thread); |
| 104 func(args); | 124 func(args); |
| 125 PropagateErrors(arguments); | |
|
siva
2016/02/03 16:50:00
Might be more efficient to have an inlinable funct
turnidge
2016/02/03 19:13:46
Done.
| |
| 105 } else { | 126 } else { |
| 106 Isolate* isolate = thread->isolate(); | 127 Isolate* isolate = thread->isolate(); |
| 107 ApiState* state = isolate->api_state(); | 128 ApiState* state = isolate->api_state(); |
| 108 ASSERT(state != NULL); | 129 ASSERT(state != NULL); |
| 109 ApiLocalScope* current_top_scope = thread->api_top_scope(); | 130 ApiLocalScope* current_top_scope = thread->api_top_scope(); |
| 110 ApiLocalScope* scope = thread->api_reusable_scope(); | 131 ApiLocalScope* scope = thread->api_reusable_scope(); |
| 111 TRACE_NATIVE_CALL("0x%" Px "", reinterpret_cast<uintptr_t>(func)); | 132 TRACE_NATIVE_CALL("0x%" Px "", reinterpret_cast<uintptr_t>(func)); |
| 112 TransitionGeneratedToNative transition(thread); | 133 TransitionGeneratedToNative transition(thread); |
| 113 if (scope == NULL) { | 134 if (scope == NULL) { |
| 114 scope = new ApiLocalScope(current_top_scope, | 135 scope = new ApiLocalScope(current_top_scope, |
| 115 thread->top_exit_frame_info()); | 136 thread->top_exit_frame_info()); |
| 116 ASSERT(scope != NULL); | 137 ASSERT(scope != NULL); |
| 117 } else { | 138 } else { |
| 118 scope->Reinit(thread, | 139 scope->Reinit(thread, |
| 119 current_top_scope, | 140 current_top_scope, |
| 120 thread->top_exit_frame_info()); | 141 thread->top_exit_frame_info()); |
| 121 thread->set_api_reusable_scope(NULL); | 142 thread->set_api_reusable_scope(NULL); |
| 122 } | 143 } |
| 123 thread->set_api_top_scope(scope); // New scope is now the top scope. | 144 thread->set_api_top_scope(scope); // New scope is now the top scope. |
| 124 | 145 |
| 125 func(args); | 146 func(args); |
| 147 PropagateErrors(arguments); | |
| 126 | 148 |
| 127 ASSERT(current_top_scope == scope->previous()); | 149 ASSERT(current_top_scope == scope->previous()); |
| 128 thread->set_api_top_scope(current_top_scope); // Reset top scope to prev. | 150 thread->set_api_top_scope(current_top_scope); // Reset top scope to prev. |
| 129 if (thread->api_reusable_scope() == NULL) { | 151 if (thread->api_reusable_scope() == NULL) { |
| 130 scope->Reset(thread); // Reset the old scope which we just exited. | 152 scope->Reset(thread); // Reset the old scope which we just exited. |
| 131 thread->set_api_reusable_scope(scope); | 153 thread->set_api_reusable_scope(scope); |
| 132 } else { | 154 } else { |
| 133 ASSERT(thread->api_reusable_scope() != scope); | 155 ASSERT(thread->api_reusable_scope() != scope); |
| 134 delete scope; | 156 delete scope; |
| 135 } | 157 } |
| (...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 251 if (call_through_wrapper) { | 273 if (call_through_wrapper) { |
| 252 NativeEntry::NativeCallWrapper( | 274 NativeEntry::NativeCallWrapper( |
| 253 args, reinterpret_cast<Dart_NativeFunction>(target_function)); | 275 args, reinterpret_cast<Dart_NativeFunction>(target_function)); |
| 254 } else { | 276 } else { |
| 255 target_function(arguments); | 277 target_function(arguments); |
| 256 } | 278 } |
| 257 } | 279 } |
| 258 | 280 |
| 259 | 281 |
| 260 } // namespace dart | 282 } // namespace dart |
| OLD | NEW |