From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from smtp49.i.mail.ru (smtp49.i.mail.ru [94.100.177.109]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by dev.tarantool.org (Postfix) with ESMTPS id 270D74696CA for ; Mon, 20 Apr 2020 01:25:19 +0300 (MSK) From: Leonid Vasiliev Date: Mon, 20 Apr 2020 01:25:09 +0300 Message-Id: In-Reply-To: References: In-Reply-To: References: Subject: [Tarantool-patches] [PATCH V6 07/10] error: export error_unref() function List-Id: Tarantool development patches List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: v.shpilevoy@tarantool.org, alexander.turenko@tarantool.org Cc: tarantool-patches@dev.tarantool.org From: Vladislav Shpilevoy C struct error objects can be created directly only in C. C-side increments their reference counter when pushes to the Lua stack. It is not going to be so convenient soon. error_unpack() function will be used in netbox to decode error object via Lua FFI. Such error object will have 0 refs and no Lua GC callback established. Because it won't be pushed on Lua stack natually, from Lua C. To make such errors alive their reference counter will be incremented and error_unref() will be set as GC callback. Follow up for #4398 --- extra/exports | 1 + src/lib/core/diag.c | 20 ++++++++++++++++++++ src/lib/core/diag.h | 21 ++------------------- 3 files changed, 23 insertions(+), 19 deletions(-) diff --git a/extra/exports b/extra/exports index 9467398..3317ddb 100644 --- a/extra/exports +++ b/extra/exports @@ -242,6 +242,7 @@ box_error_last box_error_clear box_error_set error_set_prev +error_unref box_latch_new box_latch_delete box_latch_lock diff --git a/src/lib/core/diag.c b/src/lib/core/diag.c index e143db1..787f0f8 100644 --- a/src/lib/core/diag.c +++ b/src/lib/core/diag.c @@ -31,6 +31,26 @@ #include "diag.h" #include "fiber.h" +void +error_unref(struct error *e) +{ + assert(e->refs > 0); + struct error *to_delete = e; + while (--to_delete->refs == 0) { + /* Unlink error from lists completely.*/ + struct error *cause = to_delete->cause; + assert(to_delete->effect == NULL); + if (to_delete->cause != NULL) { + to_delete->cause->effect = NULL; + to_delete->cause = NULL; + } + to_delete->destroy(to_delete); + if (cause == NULL) + return; + to_delete = cause; + } +} + int error_set_prev(struct error *e, struct error *prev) { diff --git a/src/lib/core/diag.h b/src/lib/core/diag.h index 7a5454d..beb6a75 100644 --- a/src/lib/core/diag.h +++ b/src/lib/core/diag.h @@ -118,25 +118,8 @@ error_ref(struct error *e) e->refs++; } -static inline void -error_unref(struct error *e) -{ - assert(e->refs > 0); - struct error *to_delete = e; - while (--to_delete->refs == 0) { - /* Unlink error from lists completely.*/ - struct error *cause = to_delete->cause; - assert(to_delete->effect == NULL); - if (to_delete->cause != NULL) { - to_delete->cause->effect = NULL; - to_delete->cause = NULL; - } - to_delete->destroy(to_delete); - if (cause == NULL) - return; - to_delete = cause; - } -} +void +error_unref(struct error *e); /** * Unlink error from its effect. For instance: -- 2.7.4