gnome-perl-introspection r24 - trunk/Glib-Object-Introspection/xs
- From: tsch svn gnome org
- To: svn-commits-list gnome org
- Subject: gnome-perl-introspection r24 - trunk/Glib-Object-Introspection/xs
- Date: Sun, 2 Nov 2008 21:08:25 +0000 (UTC)
Author: tsch
Date: Sun Nov 2 21:08:24 2008
New Revision: 24
URL: http://svn.gnome.org/viewvc/gnome-perl-introspection?rev=24&view=rev
Log:
Track the rename GI_TYPE_TAG_SYMBOL => GI_TYPE_TAG_INTERFACE. Adapt to the
changed semantics of methods: the instance is not an explicit argument anymore.
Use g_typelib_symbol instead of manually mocking about with g_module_*. Adapt
to the new GError semantics, which aren't an explicit argument anymore either.
Modified:
trunk/Glib-Object-Introspection/xs/IdlBoxedInfo.xs
trunk/Glib-Object-Introspection/xs/IdlFunctionInfo.xs
Modified: trunk/Glib-Object-Introspection/xs/IdlBoxedInfo.xs
==============================================================================
--- trunk/Glib-Object-Introspection/xs/IdlBoxedInfo.xs (original)
+++ trunk/Glib-Object-Introspection/xs/IdlBoxedInfo.xs Sun Nov 2 21:08:24 2008
@@ -138,7 +138,7 @@
ACCESS_VALUE (gchar*, gperl_sv_from_filename, gperl_filename_from_sv);
break;
- case GI_TYPE_TAG_SYMBOL:
+ case GI_TYPE_TAG_INTERFACE:
{
if (g_field_info_get_flags (field_info) & GI_FIELD_IS_READABLE) {
RETVAL = gperl_i11n_pointer_to_sv (field_type_info, G_STRUCT_MEMBER_P (pointer, offset), FALSE);
Modified: trunk/Glib-Object-Introspection/xs/IdlFunctionInfo.xs
==============================================================================
--- trunk/Glib-Object-Introspection/xs/IdlFunctionInfo.xs (original)
+++ trunk/Glib-Object-Introspection/xs/IdlFunctionInfo.xs Sun Nov 2 21:08:24 2008
@@ -226,6 +226,48 @@
/* ------------------------------------------------------------------------- */
+static void *
+instance_sv_to_pointer (GIFunctionInfo *function_info, SV *sv)
+{
+ // We do *not* own container.
+ GIBaseInfo *container = g_base_info_get_container (
+ (GIBaseInfo *) function_info);
+ GIInfoType info_type = g_base_info_get_type (container);
+
+#ifdef NOISY
+ warn ("instance_sv_to_pointer: container name: %s, info type: %d",
+ g_base_info_get_name (container),
+ info_type);
+#endif
+
+ void *pointer = NULL;
+
+ switch (info_type) {
+ case GI_INFO_TYPE_OBJECT:
+ pointer = gperl_get_object (sv);
+ break;
+
+ case GI_INFO_TYPE_BOXED:
+ {
+ GType type = gperl_i11n_get_gtype (
+ (GIRegisteredTypeInfo *) container);
+ pointer = gperl_get_boxed_check (sv, type);
+ break;
+ }
+
+ case GI_INFO_TYPE_ENUM:
+ case GI_INFO_TYPE_FLAGS:
+ case GI_INFO_TYPE_CALLBACK:
+ case GI_INFO_TYPE_UNRESOLVED:
+ default:
+ croak ("instance_sv_to_pointer: Don't know how to handle info type %d", info_type);
+ }
+
+ return pointer;
+}
+
+/* ------------------------------------------------------------------------- */
+
static void
sv_to_arg (SV * sv,
GArgument * arg,
@@ -236,7 +278,7 @@
if (!sv || !SvOK (sv))
/* Interfaces need to be able to handle undef separately. */
- if (!may_be_null && tag != GI_TYPE_TAG_SYMBOL)
+ if (!may_be_null && tag != GI_TYPE_TAG_INTERFACE)
croak ("undefined value for a mandatory argument encountered");
switch (tag) {
@@ -308,7 +350,7 @@
croak ("FIXME - GI_TYPE_TAG_ARRAY");
break;
- case GI_TYPE_TAG_SYMBOL:
+ case GI_TYPE_TAG_INTERFACE:
arg->v_pointer = gperl_i11n_sv_to_pointer (info, sv);
break;
@@ -409,7 +451,7 @@
case GI_TYPE_TAG_ARRAY:
croak ("FIXME - GI_TYPE_TAG_ARRAY");
- case GI_TYPE_TAG_SYMBOL:
+ case GI_TYPE_TAG_INTERFACE:
return gperl_i11n_pointer_to_sv (info, arg->v_pointer, own);
case GI_TYPE_TAG_GLIST:
@@ -443,8 +485,7 @@
croak ("FIXME - GI_TYPE_TAG_GHASH");
case GI_TYPE_TAG_ERROR:
- if (arg->v_pointer)
- gperl_croak_gerror (NULL, arg->v_pointer);
+ croak ("FIXME - GI_TYPE_TAG_ERROR");
break;
case GI_TYPE_TAG_SSIZE:
@@ -551,7 +592,7 @@
break;
case GI_TYPE_TAG_ARRAY:
- case GI_TYPE_TAG_SYMBOL:
+ case GI_TYPE_TAG_INTERFACE:
case GI_TYPE_TAG_GLIST:
case GI_TYPE_TAG_GSLIST:
case GI_TYPE_TAG_GHASH:
@@ -648,7 +689,7 @@
break;
case GI_TYPE_TAG_ARRAY:
- case GI_TYPE_TAG_SYMBOL:
+ case GI_TYPE_TAG_INTERFACE:
case GI_TYPE_TAG_GLIST:
case GI_TYPE_TAG_GSLIST:
case GI_TYPE_TAG_GHASH:
@@ -740,7 +781,7 @@
case GI_TYPE_TAG_UTF8:
case GI_TYPE_TAG_FILENAME:
case GI_TYPE_TAG_ARRAY:
- case GI_TYPE_TAG_SYMBOL:
+ case GI_TYPE_TAG_INTERFACE:
case GI_TYPE_TAG_GLIST:
case GI_TYPE_TAG_GSLIST:
case GI_TYPE_TAG_GHASH:
@@ -1101,51 +1142,75 @@
ffi_type *return_type_ffi = NULL;
gpointer *args = NULL;
gpointer func_pointer = NULL;
- GModule *module = NULL;
const gchar *symbol = NULL;
int have_args;
- int n_args;
+ int n_args, n_invoke_args;
int n_in_args;
int n_out_args;
int i, out_i;
GITypeInfo ** out_arg_type = NULL;
GITypeInfo * return_type_info = NULL;
- gboolean has_return_value;
+ gboolean throws, is_method, has_return_value;
GArgument return_value;
GArgument * in_args = NULL;
GArgument * out_args = NULL;
+ GError * local_error = NULL;
symbol = g_function_info_get_symbol (info);
-#ifdef NOISY
- warn ("invoke: %s\n", symbol);
-#endif
-
- module = g_module_open (NULL, 0);
- if (!g_module_symbol (module, symbol, &func_pointer)) {
+ if (!g_typelib_symbol (g_base_info_get_typelib((GIBaseInfo *) info),
+ symbol, &func_pointer))
+ {
croak ("Could not locate symbol %s", symbol);
}
#define OFFSET 1
have_args = items - OFFSET;
- n_args = g_callable_info_get_n_args ((GICallableInfo *) info);
+
+ n_invoke_args = n_args = g_callable_info_get_n_args ((GICallableInfo *) info);
+
+ throws = g_function_info_get_flags (info) & GI_FUNCTION_THROWS;
+ if (throws) {
+ n_invoke_args++;
+ }
+
+ is_method =
+ (g_function_info_get_flags (info) & GI_FUNCTION_IS_METHOD)
+ && !(g_function_info_get_flags (info) & GI_FUNCTION_IS_CONSTRUCTOR);
+ if (is_method) {
+ n_invoke_args++;
+ }
+
+#ifdef NOISY
+ warn ("invoke: %s -> n_args %d, n_invoke_args %d, have_args %d\n",
+ symbol, n_args, n_invoke_args, have_args);
+#endif
/* to allow us to make only one pass through the arg list, allocate
* enough space for all args in both the out and in lists. we'll
* only use as much as we need. since function argument lists are
* typically small, this shouldn't be a big problem. */
- if (n_args) {
- in_args = gperl_alloc_temp (sizeof (GArgument) * n_args);
- out_args = gperl_alloc_temp (sizeof (GArgument) * n_args);
- out_arg_type = gperl_alloc_temp (sizeof (GITypeInfo*) * n_args);
+ if (n_invoke_args) {
+ in_args = gperl_alloc_temp (sizeof (GArgument) * n_invoke_args);
+ out_args = gperl_alloc_temp (sizeof (GArgument) * n_invoke_args);
+ out_arg_type = gperl_alloc_temp (sizeof (GITypeInfo*) * n_invoke_args);
- arg_types = gperl_alloc_temp (sizeof (ffi_type *) * n_args);
- args = gperl_alloc_temp (sizeof (gpointer) * n_args);
+ arg_types = gperl_alloc_temp (sizeof (ffi_type *) * n_invoke_args);
+ args = gperl_alloc_temp (sizeof (gpointer) * n_invoke_args);
}
n_in_args = n_out_args = 0;
+
+ if (is_method) {
+ gpointer instance = instance_sv_to_pointer (info, ST (0+OFFSET));
+ arg_types[0] = &ffi_type_pointer;
+ args[0] = &instance;
+ n_in_args++;
+ }
+
for (i = 0 ; i < n_args ; i++) {
+ int method_offset = is_method ? 1 : 0;
GIArgInfo * arg_info =
g_callable_info_get_arg ((GICallableInfo *) info, i);
/* In case of out and in-out args, arg_type is unref'ed after
@@ -1159,9 +1224,9 @@
switch (g_arg_info_get_direction (arg_info)) {
case GI_DIRECTION_IN:
- sv_to_arg (ST (i+OFFSET), &in_args[n_in_args], arg_type, may_be_null);
- arg_types[i] = get_ffi_type (arg_type);
- args[i] = &in_args[n_in_args];
+ sv_to_arg (ST (i + method_offset + OFFSET), &in_args[n_in_args], arg_type, may_be_null);
+ arg_types[i + method_offset] = get_ffi_type (arg_type);
+ args[i + method_offset] = &in_args[n_in_args];
g_base_info_unref ((GIBaseInfo *) arg_type);
n_in_args++;
break;
@@ -1169,21 +1234,21 @@
out_args[n_out_args].v_pointer =
gperl_alloc_temp (sizeof (GArgument));
out_arg_type[n_out_args] = arg_type;
- arg_types[i] = &ffi_type_pointer;
- args[i] = &out_args[n_out_args];
+ arg_types[i + method_offset] = &ffi_type_pointer;
+ args[i + method_offset] = &out_args[n_out_args];
n_out_args++;
break;
case GI_DIRECTION_INOUT:
{
GArgument * temp =
gperl_alloc_temp (sizeof (GArgument));
- sv_to_arg (ST (i+OFFSET), temp, arg_type, may_be_null);
+ sv_to_arg (ST (i + method_offset + OFFSET), temp, arg_type, may_be_null);
in_args[n_in_args].v_pointer =
out_args[n_out_args].v_pointer =
temp;
out_arg_type[n_out_args] = arg_type;
- arg_types[i] = &ffi_type_pointer;
- args[i] = &in_args[n_in_args];
+ arg_types[i + method_offset] = &ffi_type_pointer;
+ args[i + method_offset] = &in_args[n_in_args];
n_in_args++;
n_out_args++;
}
@@ -1203,12 +1268,18 @@
croak ("%s needs %d args, got %d", symbol, n_in_args, have_args);
#endif
+ if (throws) {
+ gpointer address = &local_error;
+ args[n_invoke_args - 1] = &address;
+ arg_types[n_invoke_args - 1] = &ffi_type_pointer;
+ }
+
/* find the return value type */
return_type_info = g_callable_info_get_return_type ((GICallableInfo *) info);
return_type_ffi = get_ffi_type (return_type_info);
/* prepare and call the function */
- if (FFI_OK != ffi_prep_cif (&cif, FFI_DEFAULT_ABI, n_args,
+ if (FFI_OK != ffi_prep_cif (&cif, FFI_DEFAULT_ABI, n_invoke_args,
return_type_ffi, arg_types))
{
g_base_info_unref ((GIBaseInfo *) return_type_info);
@@ -1217,6 +1288,10 @@
ffi_call (&cif, func_pointer, &return_value, args);
+ if (local_error) {
+ gperl_croak_gerror (NULL, local_error);
+ }
+
/*
* place return value and output args on the stack
*/
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]