From 2f920c2f73ae58b754ccf1d897f1104e0cc3a4c6 Mon Sep 17 00:00:00 2001 From: Yves Orton Date: Thu, 16 Mar 2023 23:54:07 +0100 Subject: scope.c - add mortal_destructor_sv() and mortal_svfunc_x() The function SAVEDESTRUCTOR_X() (save_destructor_x) can be used to execute a C function at the end of the current psuedo-block. Prior to this patch there was no "mortal" equivalent that would execute at the end of the current statement. We offer a collection of functions which are intended to free SV's at either point in time, but only support callbacks at the end of the current pseudo-block. This patch adds two such functions, "mortal_destructor_sv" which can be used to trigger a perl code reference to execute at the end of the current statement, and "mortal_svfunc_x" which can be used to trigger an SVFUNC_t C function at the end of the current statement. Both functions differ from save_destructor_x() in that instead of supporting a void pointer argument they both require their argument to be some sort of SV pointer. The Perl callback function triggered by "mortal_destructor_sv" may be provided no arguments, a single argument or a list of arguments, depending on the type of argument provided to mortal_destructor_sv(): when the argument is a raw AV (with no SV ref wrapping it), then the contents of the AV are passed in as a list of arguments. When the argument is anything else but NULL, the argument is provided as a single argument, and when it is NULL the perl function is called with no arguments. Both functions are implemented on top of a mortal SV (unseen by the user) which has PERL_MAGIC_destruct magic associated with it, which triggers the destructor behavior when the SV is freed. Both functions are provided with macros to match the normal SAVExx() API, with MORTALDESTRUCTOR_SV() wrapping mortal_destructor_sv() and MORTALSVFUNC_X() wrapping mortal_svfunc_x(). The heart of this logic cribbed from Leon Timmermans' Variable-OnDestruct. See the code at: https://metacpan.org/dist/Variable-OnDestruct/source/lib/Variable/OnDestruct.xs#L6-17 I am very grateful to him for his help on this. Any errors or omissions in this code are my fault, not his. --- mg_names.inc | 1 + 1 file changed, 1 insertion(+) (limited to 'mg_names.inc') diff --git a/mg_names.inc b/mg_names.inc index 5dd0c9ae0e..e46c71faf6 100644 --- a/mg_names.inc +++ b/mg_names.inc @@ -44,6 +44,7 @@ { PERL_MAGIC_vstring, "vstring(V)" }, { PERL_MAGIC_vec, "vec(v)" }, { PERL_MAGIC_utf8, "utf8(w)" }, + { PERL_MAGIC_destruct, "destruct(X)" }, { PERL_MAGIC_substr, "substr(x)" }, { PERL_MAGIC_nonelem, "nonelem(Y)" }, { PERL_MAGIC_defelem, "defelem(y)" }, -- cgit v1.2.1