mirror of
https://gitlab.gnome.org/GNOME/glib.git
synced 2025-08-06 09:23:39 +02:00
Create new API for libffi closures
Deprecate the previous API as per discussion in !283.
This commit is contained in:
67
girffi.c
67
girffi.c
@@ -353,7 +353,7 @@ typedef struct {
|
|||||||
} GIClosureWrapper;
|
} GIClosureWrapper;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* g_callable_info_prepare_closure:
|
* g_callable_info_create_closure:
|
||||||
* @callable_info: a callable info from a typelib
|
* @callable_info: a callable info from a typelib
|
||||||
* @cif: a ffi_cif structure
|
* @cif: a ffi_cif structure
|
||||||
* @callback: the ffi callback
|
* @callback: the ffi callback
|
||||||
@@ -362,10 +362,10 @@ typedef struct {
|
|||||||
* Prepares a callback for ffi invocation.
|
* Prepares a callback for ffi invocation.
|
||||||
*
|
*
|
||||||
* Returns: the ffi_closure or NULL on error. The return value
|
* Returns: the ffi_closure or NULL on error. The return value
|
||||||
* should be freed by calling g_callable_info_free_closure().
|
* should be freed by calling g_callable_info_destroy_closure().
|
||||||
*/
|
*/
|
||||||
ffi_closure *
|
ffi_closure *
|
||||||
g_callable_info_prepare_closure (GICallableInfo *callable_info,
|
g_callable_info_create_closure (GICallableInfo *callable_info,
|
||||||
ffi_cif *cif,
|
ffi_cif *cif,
|
||||||
GIFFIClosureCallback callback,
|
GIFFIClosureCallback callback,
|
||||||
gpointer user_data)
|
gpointer user_data)
|
||||||
@@ -389,6 +389,7 @@ g_callable_info_prepare_closure (GICallableInfo *callable_info,
|
|||||||
closure->writable_self = closure;
|
closure->writable_self = closure;
|
||||||
closure->native_address = exec_ptr;
|
closure->native_address = exec_ptr;
|
||||||
|
|
||||||
|
|
||||||
atypes = g_callable_info_get_ffi_arg_types (callable_info, &n_args);
|
atypes = g_callable_info_get_ffi_arg_types (callable_info, &n_args);
|
||||||
status = ffi_prep_cif (cif, FFI_DEFAULT_ABI, n_args,
|
status = ffi_prep_cif (cif, FFI_DEFAULT_ABI, n_args,
|
||||||
g_callable_info_get_ffi_return_type (callable_info),
|
g_callable_info_get_ffi_return_type (callable_info),
|
||||||
@@ -416,7 +417,7 @@ g_callable_info_prepare_closure (GICallableInfo *callable_info,
|
|||||||
* @callable_info: a callable info from a typelib
|
* @callable_info: a callable info from a typelib
|
||||||
* @closure: ffi closure
|
* @closure: ffi closure
|
||||||
*
|
*
|
||||||
* Gets callable code from ffi_closure prepared by g_callable_info_prepare_closure()
|
* Gets callable code from ffi_closure prepared by g_callable_info_create_closure()
|
||||||
*/
|
*/
|
||||||
gpointer *
|
gpointer *
|
||||||
g_callable_info_get_closure_native_address (GICallableInfo *callable_info,
|
g_callable_info_get_closure_native_address (GICallableInfo *callable_info,
|
||||||
@@ -427,14 +428,14 @@ g_callable_info_get_closure_native_address (GICallableInfo *callable_info,
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* g_callable_info_free_closure:
|
* g_callable_info_destroy_closure:
|
||||||
* @callable_info: a callable info from a typelib
|
* @callable_info: a callable info from a typelib
|
||||||
* @closure: ffi closure
|
* @closure: ffi closure
|
||||||
*
|
*
|
||||||
* Frees a ffi_closure returned from g_callable_info_prepare_closure()
|
* Frees a ffi_closure returned from g_callable_info_create_closure()
|
||||||
*/
|
*/
|
||||||
void
|
void
|
||||||
g_callable_info_free_closure (GICallableInfo *callable_info,
|
g_callable_info_destroy_closure (GICallableInfo *callable_info,
|
||||||
ffi_closure *closure)
|
ffi_closure *closure)
|
||||||
{
|
{
|
||||||
GIClosureWrapper *wrapper = (GIClosureWrapper *)closure;
|
GIClosureWrapper *wrapper = (GIClosureWrapper *)closure;
|
||||||
@@ -442,3 +443,55 @@ g_callable_info_free_closure (GICallableInfo *callable_info,
|
|||||||
g_free (wrapper->ffi_closure.cif->arg_types);
|
g_free (wrapper->ffi_closure.cif->arg_types);
|
||||||
ffi_closure_free (wrapper->writable_self);
|
ffi_closure_free (wrapper->writable_self);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* g_callable_info_prepare_closure:
|
||||||
|
* @callable_info: a callable info from a typelib
|
||||||
|
* @cif: a ffi_cif structure
|
||||||
|
* @callback: the ffi callback
|
||||||
|
* @user_data: data to be passed into the callback
|
||||||
|
*
|
||||||
|
* Prepares a callback for ffi invocation. Deprecated
|
||||||
|
*
|
||||||
|
* Returns: the native address of the closre or NULL on error. The return value
|
||||||
|
* should be freed by calling g_callable_info_free_closure().
|
||||||
|
*/
|
||||||
|
ffi_closure *
|
||||||
|
g_callable_info_prepare_closure (GICallableInfo *callable_info,
|
||||||
|
ffi_cif *cif,
|
||||||
|
GIFFIClosureCallback callback,
|
||||||
|
gpointer user_data)
|
||||||
|
{
|
||||||
|
ffi_closure * closure;
|
||||||
|
|
||||||
|
closure = g_callable_info_create_closure(callable_info, cif, callback, user_data);
|
||||||
|
if (!closure)
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
g_warning ("g_callable_info_prepare_closure is deprecated, use g_callable_info_create_closure instead\n");
|
||||||
|
|
||||||
|
/* Return the native pointer which, on some systems and ffi versions without static exec trampolines,
|
||||||
|
* points to the same underlying memory as closure, but via an executable-non-writable mapping.
|
||||||
|
* Deprecated, and kept for backwards compatibility only. Risks segfaults on freeing the closure.
|
||||||
|
*/
|
||||||
|
return (ffi_closure *) g_callable_info_get_closure_native_address(callable_info, closure);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* g_callable_info_free_closure:
|
||||||
|
* @callable_info: a callable info from a typelib
|
||||||
|
* @closure: ffi closure
|
||||||
|
*
|
||||||
|
* Does nothing. (Leaks memory!) Use g_callable_info_destroy_closure() instead,
|
||||||
|
* in conjunction with g_callable_info_create_closure().
|
||||||
|
*
|
||||||
|
* Should free a ffi_closure returned from g_callable_info_prepare_closure(),
|
||||||
|
* which may cause a segfault because the native address is returned instead
|
||||||
|
* of the closure address.
|
||||||
|
*/
|
||||||
|
void g_callable_info_free_closure (GICallableInfo *callable_info, ffi_closure *closure)
|
||||||
|
{
|
||||||
|
g_warning ("g_callable_info_free_closure is deprecated and leaks memory\n");
|
||||||
|
}
|
||||||
|
19
girffi.h
19
girffi.h
@@ -90,18 +90,29 @@ GI_AVAILABLE_IN_ALL
|
|||||||
void g_function_invoker_destroy (GIFunctionInvoker *invoker);
|
void g_function_invoker_destroy (GIFunctionInvoker *invoker);
|
||||||
|
|
||||||
|
|
||||||
GI_AVAILABLE_IN_ALL
|
GI_DEPRECATED_IN_1_72_FOR(g_callable_info_create_closure)
|
||||||
ffi_closure * g_callable_info_prepare_closure (GICallableInfo *callable_info,
|
ffi_closure * g_callable_info_prepare_closure (GICallableInfo *callable_info,
|
||||||
ffi_cif *cif,
|
ffi_cif *cif,
|
||||||
GIFFIClosureCallback callback,
|
GIFFIClosureCallback callback,
|
||||||
gpointer user_data);
|
gpointer user_data);
|
||||||
|
|
||||||
GI_AVAILABLE_IN_1_70
|
GI_DEPRECATED_IN_1_72_FOR(g_callable_info_destroy_closure)
|
||||||
|
void g_callable_info_free_closure (GICallableInfo *callable_info,
|
||||||
|
ffi_closure *closure);
|
||||||
|
|
||||||
|
|
||||||
|
GI_AVAILABLE_IN_1_72
|
||||||
|
ffi_closure * g_callable_info_create_closure (GICallableInfo *callable_info,
|
||||||
|
ffi_cif *cif,
|
||||||
|
GIFFIClosureCallback callback,
|
||||||
|
gpointer user_data);
|
||||||
|
|
||||||
|
GI_AVAILABLE_IN_1_72
|
||||||
gpointer * g_callable_info_get_closure_native_address (GICallableInfo *callable_info,
|
gpointer * g_callable_info_get_closure_native_address (GICallableInfo *callable_info,
|
||||||
ffi_closure *closure);
|
ffi_closure *closure);
|
||||||
|
|
||||||
GI_AVAILABLE_IN_ALL
|
GI_AVAILABLE_IN_1_72
|
||||||
void g_callable_info_free_closure (GICallableInfo *callable_info,
|
void g_callable_info_destroy_closure (GICallableInfo *callable_info,
|
||||||
ffi_closure *closure);
|
ffi_closure *closure);
|
||||||
|
|
||||||
G_END_DECLS
|
G_END_DECLS
|
||||||
|
@@ -171,4 +171,18 @@
|
|||||||
# define GI_AVAILABLE_IN_1_70 _GI_EXTERN
|
# define GI_AVAILABLE_IN_1_70 _GI_EXTERN
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if defined(GLIB_VERSION_2_72) && GLIB_VERSION_MIN_REQUIRED >= GLIB_VERSION_2_72
|
||||||
|
# define GI_DEPRECATED_IN_1_72 GLIB_DEPRECATED
|
||||||
|
# define GI_DEPRECATED_IN_1_72_FOR(f) GLIB_DEPRECATED_FOR(f)
|
||||||
|
#else
|
||||||
|
# define GI_DEPRECATED_IN_1_72 _GI_EXTERN
|
||||||
|
# define GI_DEPRECATED_IN_1_72_FOR(f) _GI_EXTERN
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(GLIB_VERSION_2_72) && GLIB_VERSION_MAX_ALLOWED < GLIB_VERSION_2_72
|
||||||
|
# define GI_AVAILABLE_IN_1_72 GLIB_UNAVAILABLE(2, 72)
|
||||||
|
#else
|
||||||
|
# define GI_AVAILABLE_IN_1_72 _GI_EXTERN
|
||||||
|
#endif
|
||||||
|
|
||||||
#endif /* __GIVERSIONMACROS_H__ */
|
#endif /* __GIVERSIONMACROS_H__ */
|
||||||
|
Reference in New Issue
Block a user