@@ -16,7 +16,29 @@ namespace dart {
1616
1717IMPLEMENT_WRAPPERTYPEINFO (zircon, Handle);
1818
19- Handle::Handle (zx_handle_t handle) : handle_(handle) {}
19+ Handle::Handle (zx_handle_t handle) : handle_(handle) {
20+ tonic::DartState* state = tonic::DartState::Current ();
21+ FML_DCHECK (state);
22+ Dart_Handle zircon_lib = Dart_LookupLibrary (ToDart (" dart:zircon" ));
23+ FML_DCHECK (!tonic::LogIfError (zircon_lib));
24+
25+ Dart_Handle on_wait_completer_type =
26+ Dart_GetClass (zircon_lib, ToDart (" _OnWaitCompleteClosure" ));
27+ FML_DCHECK (!tonic::LogIfError (on_wait_completer_type));
28+ on_wait_completer_type_.Set (state, on_wait_completer_type);
29+
30+ Dart_Handle async_lib = Dart_LookupLibrary (ToDart (" dart:async" ));
31+ FML_DCHECK (!tonic::LogIfError (async_lib));
32+ async_lib_.Set (state, async_lib);
33+
34+ Dart_Handle closure_string = ToDart (" _closure" );
35+ FML_DCHECK (!tonic::LogIfError (closure_string));
36+ closure_string_.Set (state, closure_string);
37+
38+ Dart_Handle schedule_microtask_string = ToDart (" scheduleMicrotask" );
39+ FML_DCHECK (!tonic::LogIfError (schedule_microtask_string));
40+ schedule_microtask_string_.Set (state, schedule_microtask_string);
41+ }
2042
2143Handle::~Handle () {
2244 if (is_valid ()) {
@@ -93,6 +115,36 @@ Dart_Handle Handle::Duplicate(uint32_t rights) {
93115 return ToDart (Create (out_handle));
94116}
95117
118+ void Handle::ScheduleCallback (tonic::DartPersistentValue callback,
119+ zx_status_t status,
120+ const zx_packet_signal_t * signal) {
121+ auto state = callback.dart_state ().lock ();
122+ FML_DCHECK (state);
123+ tonic::DartState::Scope scope (state);
124+
125+ // Make a new _OnWaitCompleteClosure(callback, status, signal->observed).
126+ FML_DCHECK (!callback.is_empty ());
127+ std::vector<Dart_Handle> constructor_args{callback.Release (), ToDart (status),
128+ ToDart (signal->observed )};
129+ Dart_Handle on_wait_complete_closure =
130+ Dart_New (on_wait_completer_type_.Get (), Dart_Null (),
131+ constructor_args.size (), constructor_args.data ());
132+ FML_DCHECK (!tonic::LogIfError (on_wait_complete_closure));
133+
134+ // The _callback field contains the thunk:
135+ // () => callback(status, signal->observed)
136+ Dart_Handle closure =
137+ Dart_GetField (on_wait_complete_closure, closure_string_.Get ());
138+ FML_DCHECK (!tonic::LogIfError (closure));
139+
140+ // Put the thunk on the microtask queue by calling scheduleMicrotask().
141+ std::vector<Dart_Handle> sm_args{closure};
142+ Dart_Handle sm_result =
143+ Dart_Invoke (async_lib_.Get (), schedule_microtask_string_.Get (),
144+ sm_args.size (), sm_args.data ());
145+ FML_DCHECK (!tonic::LogIfError (sm_result));
146+ }
147+
96148// clang-format: off
97149
98150#define FOR_EACH_STATIC_BINDING (V ) V(Handle, CreateInvalid)
0 commit comments