From 45676be3dc27683e0a4cd76f981beecf60ed22fb Mon Sep 17 00:00:00 2001 From: Gabriel Schulhof Date: Mon, 6 Apr 2020 10:16:15 -0700 Subject: n-api: detect deadlocks in thread-safe function We introduce status `napi_would_deadlock` to be used as a return status by `napi_call_threadsafe_function` if the call is made with `napi_tsfn_blocking` on the main thread and the queue is full. PR-URL: https://github.com/nodejs/node/pull/32689 Fixes: https://github.com/nodejs/node/issues/32615 Signed-off-by: Gabriel Schulhof Reviewed-By: James M Snell Reviewed-By: Anna Henningsen Reviewed-By: Colin Ihrig Reviewed-By: David Carlier Reviewed-By: Chengzhong Wu Reviewed-By: Michael Dawson --- doc/api/n-api.md | 21 +++++++++++++++++++-- 1 file changed, 19 insertions(+), 2 deletions(-) (limited to 'doc/api') diff --git a/doc/api/n-api.md b/doc/api/n-api.md index a38ebbd6f86..eda1d94f728 100644 --- a/doc/api/n-api.md +++ b/doc/api/n-api.md @@ -457,6 +457,7 @@ typedef enum { napi_date_expected, napi_arraybuffer_expected, napi_detachable_arraybuffer_expected, + napi_would_deadlock, } napi_status; ``` @@ -5095,6 +5096,12 @@ preventing data from being successfully added to the queue. If set to `napi_call_threadsafe_function()` never blocks if the thread-safe function was created with a maximum queue size of 0. +As a special case, when `napi_call_threadsafe_function()` is called from the +main thread, it will return `napi_would_deadlock` if the queue is full and it +was called with `napi_tsfn_blocking`. The reason for this is that the main +thread is responsible for reducing the number of items in the queue so, if it +waits for room to become available on the queue, then it will deadlock. + The actual call into JavaScript is controlled by the callback given via the `call_js_cb` parameter. `call_js_cb` is invoked on the main thread once for each value that was placed into the queue by a successful call to @@ -5231,6 +5238,12 @@ This API may be called from any thread which makes use of `func`. ```C @@ -5248,9 +5261,13 @@ napi_call_threadsafe_function(napi_threadsafe_function func, `napi_tsfn_nonblocking` to indicate that the call should return immediately with a status of `napi_queue_full` whenever the queue is full. +This API will return `napi_would_deadlock` if called with `napi_tsfn_blocking` +from the main thread and the queue is full. + This API will return `napi_closing` if `napi_release_threadsafe_function()` was -called with `abort` set to `napi_tsfn_abort` from any thread. The value is only -added to the queue if the API returns `napi_ok`. +called with `abort` set to `napi_tsfn_abort` from any thread. + +The value is only added to the queue if the API returns `napi_ok`. This API may be called from any thread which makes use of `func`. -- cgit v1.2.3