@@ -134,6 +134,48 @@ RetainedObjectInfo* WrapperInfo(uint16_t class_id, Local<Value> wrapper) {
134
134
// end RetainedAsyncInfo
135
135
136
136
137
+ static void DestroyIdsCb (uv_idle_t * handle) {
138
+ uv_idle_stop (handle);
139
+
140
+ Environment* env = Environment::from_destroy_ids_idle_handle (handle);
141
+
142
+ HandleScope handle_scope (env->isolate ());
143
+ Context::Scope context_scope (env->context ());
144
+ Local<Function> fn = env->async_hooks_destroy_function ();
145
+
146
+ TryCatch try_catch (env->isolate ());
147
+
148
+ std::vector<double > destroy_ids_list;
149
+ destroy_ids_list.swap (*env->destroy_ids_list ());
150
+ for (auto current_id : destroy_ids_list) {
151
+ // Want each callback to be cleaned up after itself, instead of cleaning
152
+ // them all up after the while() loop completes.
153
+ HandleScope scope (env->isolate ());
154
+ Local<Value> argv = Number::New (env->isolate (), current_id);
155
+ MaybeLocal<Value> ret = fn->Call (
156
+ env->context (), Undefined (env->isolate ()), 1 , &argv);
157
+
158
+ if (ret.IsEmpty ()) {
159
+ ClearFatalExceptionHandlers (env);
160
+ FatalException (env->isolate (), try_catch);
161
+ }
162
+ }
163
+
164
+ env->destroy_ids_list ()->clear ();
165
+ }
166
+
167
+
168
+ static void PushBackDestroyId (Environment* env, double id) {
169
+ if (env->async_hooks ()->fields ()[AsyncHooks::kDestroy ] == 0 )
170
+ return ;
171
+
172
+ if (env->destroy_ids_list ()->empty ())
173
+ uv_idle_start (env->destroy_ids_idle_handle (), DestroyIdsCb);
174
+
175
+ env->destroy_ids_list ()->push_back (id);
176
+ }
177
+
178
+
137
179
static void SetupHooks (const FunctionCallbackInfo<Value>& args) {
138
180
Environment* env = Environment::GetCurrent (args);
139
181
@@ -170,6 +212,42 @@ void AsyncWrap::GetAsyncId(const FunctionCallbackInfo<Value>& args) {
170
212
}
171
213
172
214
215
+ void AsyncWrap::PushAsyncIds (const FunctionCallbackInfo<Value>& args) {
216
+ Environment* env = Environment::GetCurrent (args);
217
+ // No need for CHECK(IsNumber()) on args because if FromJust() doesn't fail
218
+ // then the checks in push_ids() and pop_ids() will.
219
+ double async_id = args[0 ]->NumberValue (env->context ()).FromJust ();
220
+ double trigger_id = args[1 ]->NumberValue (env->context ()).FromJust ();
221
+ env->async_hooks ()->push_ids (async_id, trigger_id);
222
+ }
223
+
224
+
225
+ void AsyncWrap::PopAsyncIds (const FunctionCallbackInfo<Value>& args) {
226
+ Environment* env = Environment::GetCurrent (args);
227
+ double async_id = args[0 ]->NumberValue (env->context ()).FromJust ();
228
+ args.GetReturnValue ().Set (env->async_hooks ()->pop_ids (async_id));
229
+ }
230
+
231
+
232
+ void AsyncWrap::ClearIdStack (const FunctionCallbackInfo<Value>& args) {
233
+ Environment* env = Environment::GetCurrent (args);
234
+ env->async_hooks ()->clear_id_stack ();
235
+ }
236
+
237
+
238
+ void AsyncWrap::AsyncReset (const FunctionCallbackInfo<Value>& args) {
239
+ AsyncWrap* wrap;
240
+ ASSIGN_OR_RETURN_UNWRAP (&wrap, args.Holder ());
241
+ wrap->AsyncReset ();
242
+ }
243
+
244
+
245
+ void AsyncWrap::QueueDestroyId (const FunctionCallbackInfo<Value>& args) {
246
+ CHECK (args[0 ]->IsNumber ());
247
+ PushBackDestroyId (Environment::GetCurrent (args), args[0 ]->NumberValue ());
248
+ }
249
+
250
+
173
251
void AsyncWrap::Initialize (Local<Object> target,
174
252
Local<Value> unused,
175
253
Local<Context> context) {
@@ -178,6 +256,10 @@ void AsyncWrap::Initialize(Local<Object> target,
178
256
HandleScope scope (isolate);
179
257
180
258
env->SetMethod (target, " setupHooks" , SetupHooks);
259
+ env->SetMethod (target, " pushAsyncIds" , PushAsyncIds);
260
+ env->SetMethod (target, " popAsyncIds" , PopAsyncIds);
261
+ env->SetMethod (target, " clearIdStack" , ClearIdStack);
262
+ env->SetMethod (target, " addIdToDestroyList" , QueueDestroyId);
181
263
182
264
v8::PropertyAttribute ReadOnlyDontDelete =
183
265
static_cast <v8::PropertyAttribute>(v8::ReadOnly | v8::DontDelete);
@@ -252,37 +334,6 @@ void AsyncWrap::Initialize(Local<Object> target,
252
334
}
253
335
254
336
255
- void AsyncWrap::DestroyIdsCb (uv_idle_t * handle) {
256
- uv_idle_stop (handle);
257
-
258
- Environment* env = Environment::from_destroy_ids_idle_handle (handle);
259
-
260
- HandleScope handle_scope (env->isolate ());
261
- Context::Scope context_scope (env->context ());
262
- Local<Function> fn = env->async_hooks_destroy_function ();
263
-
264
- TryCatch try_catch (env->isolate ());
265
-
266
- std::vector<double > destroy_ids_list;
267
- destroy_ids_list.swap (*env->destroy_ids_list ());
268
- for (auto current_id : destroy_ids_list) {
269
- // Want each callback to be cleaned up after itself, instead of cleaning
270
- // them all up after the while() loop completes.
271
- HandleScope scope (env->isolate ());
272
- Local<Value> argv = Number::New (env->isolate (), current_id);
273
- MaybeLocal<Value> ret = fn->Call (
274
- env->context (), Undefined (env->isolate ()), 1 , &argv);
275
-
276
- if (ret.IsEmpty ()) {
277
- ClearFatalExceptionHandlers (env);
278
- FatalException (env->isolate (), try_catch);
279
- }
280
- }
281
-
282
- env->destroy_ids_list ()->clear ();
283
- }
284
-
285
-
286
337
void LoadAsyncWrapperInfo (Environment* env) {
287
338
HeapProfiler* heap_profiler = env->isolate ()->GetHeapProfiler ();
288
339
#define V (PROVIDER ) \
@@ -310,21 +361,14 @@ AsyncWrap::AsyncWrap(Environment* env,
310
361
311
362
312
363
AsyncWrap::~AsyncWrap () {
313
- if (env ()->async_hooks ()->fields ()[AsyncHooks::kDestroy ] == 0 ) {
314
- return ;
315
- }
316
-
317
- if (env ()->destroy_ids_list ()->empty ())
318
- uv_idle_start (env ()->destroy_ids_idle_handle (), DestroyIdsCb);
319
-
320
- env ()->destroy_ids_list ()->push_back (get_id ());
364
+ PushBackDestroyId (env (), get_id ());
321
365
}
322
366
323
367
324
368
// Generalized call for both the constructor and for handles that are pooled
325
369
// and reused over their lifetime. This way a new uid can be assigned when
326
370
// the resource is pulled out of the pool and put back into use.
327
- void AsyncWrap::Reset () {
371
+ void AsyncWrap::AsyncReset () {
328
372
AsyncHooks* async_hooks = env ()->async_hooks ();
329
373
async_id_ = env ()->new_async_id ();
330
374
trigger_id_ = env ()->get_init_trigger_id ();
0 commit comments