diff options
author | Jasper St. Pierre <jstpierre@mecheye.net> | 2012-01-19 22:24:17 -0500 |
---|---|---|
committer | Jasper St. Pierre <jstpierre@mecheye.net> | 2012-01-25 20:57:10 -0500 |
commit | f1dc3188f5e7a3e9d9d5cd26879024441dcb26b4 (patch) | |
tree | 4d74c63b25e8b1f4938c80a8dcc020553087a232 | |
parent | 97f0be7db9674a13630b73d4d4412d228a37322c (diff) | |
download | gjs-f1dc3188f5e7a3e9d9d5cd26879024441dcb26b4.tar.gz |
Represent GTypes as a new boxed wrapper type
We can't natively represent a pointer as a regular value in JS (we have at
most 30-bit integers or doubles), so to store GTypes correctly, we need to
box them. Create a new native object that simply represents a GType, give
it a 'g_type_name' wrapper, and fix up the rest of the world so we no longer
treat a GType as a special integer.
https://bugzilla.gnome.org/show_bug.cgi?id=668427
-rw-r--r-- | Makefile.am | 6 | ||||
-rw-r--r-- | gi/arg.c | 105 | ||||
-rw-r--r-- | gi/enumeration.c | 3 | ||||
-rw-r--r-- | gi/gtype.c | 171 | ||||
-rw-r--r-- | gi/gtype.h | 50 | ||||
-rw-r--r-- | gi/object.c | 31 | ||||
-rw-r--r-- | gi/object.h | 2 | ||||
-rw-r--r-- | gi/param.c | 19 | ||||
-rw-r--r-- | test/js/testGIMarshalling.js | 29 |
9 files changed, 349 insertions, 67 deletions
diff --git a/Makefile.am b/Makefile.am index ddf30d17..83c6ebb3 100644 --- a/Makefile.am +++ b/Makefile.am @@ -50,7 +50,8 @@ nobase_gjs_module_include_HEADERS = \ gi/enumeration.h \ gi/function.h \ gi/keep-alive.h \ - gi/interface.h + gi/interface.h \ + gi/gtype.h noinst_HEADERS += \ gjs/jsapi-private.h \ @@ -133,7 +134,8 @@ libgjs_la_SOURCES += \ gi/repo.c \ gi/union.c \ gi/value.c \ - gi/interface.c + gi/interface.c \ + gi/gtype.c if ENABLE_DTRACE gjs_gi_probes.h: gi/gjs_gi_probes.d @@ -24,6 +24,7 @@ #include <config.h> #include "arg.h" +#include "gtype.h" #include "object.h" #include "foreign.h" #include "boxed.h" @@ -150,25 +151,6 @@ _gjs_enum_to_int (GIEnumInfo *enum_info, return (int)value; } -/* The typelib used to have machine-independent types like - * GI_TYPE_TAG_LONG that had to be converted; now we only - * handle GType specially here. - */ -static inline GITypeTag -replace_gtype(GITypeTag type) { - if (type == GI_TYPE_TAG_GTYPE) { - /* Constant folding should handle this hopefully */ - switch (sizeof(GType)) { - case 1: return GI_TYPE_TAG_UINT8; - case 2: return GI_TYPE_TAG_UINT16; - case 4: return GI_TYPE_TAG_UINT32; - case 8: return GI_TYPE_TAG_UINT64; - default: g_assert_not_reached (); - } - } - return type; -} - /* Check if an argument of the given needs to be released if we created it * from a JS value to pass it into a function and aren't transfering ownership. */ @@ -537,7 +519,6 @@ gjs_string_to_intarray(JSContext *context, guint16 *result16; element_type = g_type_info_get_tag(param_info); - element_type = replace_gtype(element_type); switch (element_type) { case GI_TYPE_TAG_INT8: @@ -624,6 +605,46 @@ gjs_array_to_intarray(JSContext *context, } static JSBool +gjs_gtypearray_to_array(JSContext *context, + jsval array_value, + unsigned int length, + void **arr_p) +{ + GType *result; + unsigned i; + + /* add one so we're always zero terminated */ + result = g_malloc0((length+1) * sizeof(GType)); + + for (i = 0; i < length; ++i) { + jsval elem; + GType gtype; + + elem = JSVAL_VOID; + if (!JS_GetElement(context, JSVAL_TO_OBJECT(array_value), + i, &elem)) { + g_free(result); + gjs_throw(context, "Missing array element %u", i); + return JS_FALSE; + } + + gtype = gjs_gtype_get_actual_gtype(context, JSVAL_TO_OBJECT(elem)); + + if (gtype == G_TYPE_INVALID) { + g_free(result); + gjs_throw(context, "Invalid element in GType array"); + return JS_FALSE; + } + + result[i] = gtype; + } + + *arr_p = result; + + return JS_TRUE; +} + +static JSBool gjs_array_to_floatarray(JSContext *context, jsval array_value, unsigned int length, @@ -854,7 +875,6 @@ gjs_array_to_array(JSContext *context, GITypeTag element_type; element_type = g_type_info_get_tag(param_info); - element_type = replace_gtype(element_type); /* Special case for GValue "flat arrays" */ if (is_gvalue_flat_array(param_info, element_type)) @@ -895,6 +915,9 @@ gjs_array_to_array(JSContext *context, case GI_TYPE_TAG_DOUBLE: return gjs_array_to_floatarray (context, array_value, length, arr_p, TRUE); + case GI_TYPE_TAG_GTYPE: + return gjs_gtypearray_to_array + (context, array_value, length, arr_p); /* Everything else is a pointer type */ case GI_TYPE_TAG_INTERFACE: @@ -924,7 +947,6 @@ gjs_g_array_new_for_type(JSContext *context, guint element_size; element_type = g_type_info_get_tag(param_info); - element_type = replace_gtype(element_type); if (element_type == GI_TYPE_TAG_INTERFACE) { GIInterfaceInfo *interface_info = g_type_info_get_interface(param_info); @@ -960,6 +982,9 @@ gjs_g_array_new_for_type(JSContext *context, case GI_TYPE_TAG_DOUBLE: element_size = sizeof(gdouble); break; + case GI_TYPE_TAG_GTYPE: + element_size = sizeof(GType); + break; case GI_TYPE_TAG_INTERFACE: case GI_TYPE_TAG_UTF8: case GI_TYPE_TAG_FILENAME: @@ -1085,7 +1110,6 @@ gjs_value_to_g_argument(JSContext *context, gboolean nullable_type; type_tag = g_type_info_get_tag( (GITypeInfo*) type_info); - type_tag = replace_gtype(type_tag); gjs_debug_marshal(GJS_DEBUG_GFUNCTION, "Converting jsval to GArgument %s", @@ -1206,6 +1230,19 @@ gjs_value_to_g_argument(JSContext *context, } break; + case GI_TYPE_TAG_GTYPE: + if (JSVAL_IS_OBJECT(value)) { + GType gtype; + gtype = gjs_gtype_get_actual_gtype(context, JSVAL_TO_OBJECT(value)); + if (gtype == G_TYPE_INVALID) + wrong = TRUE; + arg->v_ssize = gtype; + } else { + wrong = TRUE; + report_type_mismatch = TRUE; + } + break; + case GI_TYPE_TAG_FILENAME: nullable_type = TRUE; if (JSVAL_IS_NULL(value)) { @@ -1643,7 +1680,6 @@ gjs_g_argument_init_default(JSContext *context, GITypeTag type_tag; type_tag = g_type_info_get_tag( (GITypeInfo*) type_info); - type_tag = replace_gtype(type_tag); switch (type_tag) { case GI_TYPE_TAG_VOID: @@ -1694,6 +1730,10 @@ gjs_g_argument_init_default(JSContext *context, arg->v_double = 0.0; break; + case GI_TYPE_TAG_GTYPE: + arg->v_ssize = 0; + break; + case GI_TYPE_TAG_FILENAME: case GI_TYPE_TAG_UTF8: case GI_TYPE_TAG_GLIST: @@ -1869,7 +1909,6 @@ gjs_array_from_carray_internal (JSContext *context, guint i; element_type = g_type_info_get_tag(param_info); - element_type = replace_gtype(element_type); if (is_gvalue_flat_array(param_info, element_type)) return gjs_array_from_flat_gvalue_array(context, array, length, value_p); @@ -1938,6 +1977,7 @@ gjs_array_from_carray_internal (JSContext *context, case GI_TYPE_TAG_DOUBLE: ITERATE(double); break; + case GI_TYPE_TAG_GTYPE: case GI_TYPE_TAG_UTF8: case GI_TYPE_TAG_FILENAME: case GI_TYPE_TAG_ARRAY: @@ -2050,7 +2090,6 @@ gjs_array_from_zero_terminated_c_array (JSContext *context, guint i; element_type = g_type_info_get_tag(param_info); - element_type = replace_gtype(element_type); /* Special case array(guint8) */ if (element_type == GI_TYPE_TAG_UINT8) { @@ -2119,6 +2158,7 @@ gjs_array_from_zero_terminated_c_array (JSContext *context, case GI_TYPE_TAG_DOUBLE: ITERATE(double); break; + case GI_TYPE_TAG_GTYPE: case GI_TYPE_TAG_UTF8: case GI_TYPE_TAG_FILENAME: case GI_TYPE_TAG_ARRAY: @@ -2230,7 +2270,6 @@ gjs_value_from_g_argument (JSContext *context, GITypeTag type_tag; type_tag = g_type_info_get_tag( (GITypeInfo*) type_info); - type_tag = replace_gtype(type_tag); gjs_debug_marshal(GJS_DEBUG_GFUNCTION, "Converting GArgument %s to jsval", @@ -2277,6 +2316,14 @@ gjs_value_from_g_argument (JSContext *context, case GI_TYPE_TAG_DOUBLE: return JS_NewNumberValue(context, arg->v_double, value_p); + case GI_TYPE_TAG_GTYPE: + { + JSObject *obj; + obj = gjs_gtype_create_gtype_wrapper(context, arg->v_ssize); + *value_p = OBJECT_TO_JSVAL(obj); + } + break; + case GI_TYPE_TAG_UNICHAR: { char utf8[7]; @@ -2722,7 +2769,6 @@ gjs_g_arg_release_internal(JSContext *context, param_info = g_type_info_get_param_type(type_info, 0); element_type = g_type_info_get_tag(param_info); - element_type = replace_gtype(element_type); if (transfer != GI_TRANSFER_CONTAINER && is_gvalue_flat_array(param_info, element_type)) { g_free(arg->v_pointer); @@ -2744,6 +2790,7 @@ gjs_g_arg_release_internal(JSContext *context, case GI_TYPE_TAG_INT8: case GI_TYPE_TAG_INT16: case GI_TYPE_TAG_INT32: + case GI_TYPE_TAG_GTYPE: g_free (arg->v_pointer); break; @@ -2804,7 +2851,6 @@ gjs_g_arg_release_internal(JSContext *context, param_info = g_type_info_get_param_type(type_info, 0); element_type = g_type_info_get_tag(param_info); - element_type = replace_gtype(element_type); switch (element_type) { case GI_TYPE_TAG_UINT8: @@ -2815,6 +2861,7 @@ gjs_g_arg_release_internal(JSContext *context, case GI_TYPE_TAG_INT16: case GI_TYPE_TAG_INT32: case GI_TYPE_TAG_INT64: + case GI_TYPE_TAG_GTYPE: g_array_free((GArray*) arg->v_pointer, TRUE); break; diff --git a/gi/enumeration.c b/gi/enumeration.c index c7734b47..fac98547 100644 --- a/gi/enumeration.c +++ b/gi/enumeration.c @@ -28,6 +28,7 @@ #include <gjs/gjs-module.h> #include <gjs/compat.h> #include "repo.h" +#include "gtype.h" #include <util/log.h> @@ -167,7 +168,7 @@ gjs_define_enumeration(JSContext *context, } gtype = g_registered_type_info_get_g_type((GIRegisteredTypeInfo*)info); - value = INT_TO_JSVAL(gtype); + value = OBJECT_TO_JSVAL(gjs_gtype_create_gtype_wrapper(context, gtype)); JS_DefineProperty(context, enum_obj, "$gtype", value, NULL, NULL, JSPROP_PERMANENT); diff --git a/gi/gtype.c b/gi/gtype.c new file mode 100644 index 00000000..501903ae --- /dev/null +++ b/gi/gtype.c @@ -0,0 +1,171 @@ +/* -*- mode: C; c-basic-offset: 4; indent-tabs-mode: nil; -*- */ +/* + * Copyright (c) 2008 litl, LLC + * Copyright (c) 2012 Red Hat, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#include <config.h> + +#include "gtype.h" + +#include <gjs/gjs-module.h> +#include <gjs/compat.h> +#include <util/log.h> + +#include <jsapi.h> +#include <girepository.h> + +GJS_DEFINE_PROTO_ABSTRACT("GIRepositoryGType", gtype); + +/* priv_from_js adds a "*", so this returns "void *" */ +GJS_DEFINE_PRIV_FROM_JS(void, gjs_gtype_class); + +static GQuark +gjs_get_gtype_wrapper_quark(void) +{ + static gsize once_init = 0; + static GQuark value = 0; + if (g_once_init_enter(&once_init)) { + value = g_quark_from_string("gjs-gtype-wrapper"); + g_once_init_leave(&once_init, 1); + } + return value; +} + +static void +gjs_gtype_finalize(JSContext *context, + JSObject *obj) +{ + GType gtype = GPOINTER_TO_SIZE(priv_from_js(context, obj)); + + /* proto doesn't have a private set */ + if (G_UNLIKELY(gtype == 0)) + return; + + g_type_set_qdata(gtype, gjs_get_gtype_wrapper_quark(), NULL); +} + +static JSBool +to_string_func(JSContext *context, + uintN argc, + jsval *vp) +{ + JSObject *obj = JS_THIS_OBJECT(context, vp); + GType gtype; + gchar *strval; + JSBool ret; + jsval retval; + + gtype = GPOINTER_TO_SIZE(priv_from_js(context, obj)); + + strval = g_strdup_printf("[object GType for '%s']", + g_type_name(gtype)); + ret = gjs_string_from_utf8(context, strval, -1, &retval); + if (ret) + JS_SET_RVAL(context, vp, retval); + g_free(strval); + return ret; +} + +static JSBool +get_name_func (JSContext *context, + JSObject *obj, + jsid id, + jsval *vp) +{ + GType gtype; + JSBool ret; + jsval retval; + + gtype = GPOINTER_TO_SIZE(priv_from_js(context, obj)); + + ret = gjs_string_from_utf8(context, g_type_name(gtype), -1, &retval); + if (ret) + JS_SET_RVAL(context, vp, retval); + return ret; +} + +/* Properties */ +static JSPropertySpec gjs_gtype_proto_props[] = { + { "name", 0, JSPROP_READONLY | JSPROP_PERMANENT | JSPROP_SHARED, (JSPropertyOp)get_name_func, NULL } +}; + +/* Functions */ +static JSFunctionSpec gjs_gtype_proto_funcs[] = { + { "toString", (JSNative)to_string_func, 0, 0 } +}; + +JSObject * +gjs_gtype_create_gtype_wrapper (JSContext *context, + GType gtype) +{ + JSObject *object; + JSObject *global; + + JS_BeginRequest(context); + + /* put constructor for GIRepositoryGType() in the global namespace */ + global = gjs_get_import_global(context); + gjs_gtype_create_proto(context, global, "GIRepositoryGType", NULL); + + object = g_type_get_qdata(gtype, gjs_get_gtype_wrapper_quark()); + if (object != NULL) + goto out; + + object = JS_NewObject(context, &gjs_gtype_class, NULL, NULL); + if (object == NULL) + goto out; + + JS_SetPrivate(context, object, GSIZE_TO_POINTER(gtype)); + g_type_set_qdata(gtype, gjs_get_gtype_wrapper_quark(), object); + + out: + JS_EndRequest(context); + return object; +} + +GType +gjs_gtype_get_actual_gtype (JSContext *context, + JSObject *object) +{ + GType gtype = G_TYPE_INVALID; + jsval gtype_val; + + JS_BeginRequest(context); + if (JS_InstanceOf(context, object, &gjs_gtype_class, NULL)) { + gtype = GPOINTER_TO_SIZE(priv_from_js(context, object)); + goto out; + } + + /* OK, we don't have a GType wrapper object -- grab the "$gtype" + * property on that and hope it's a GType wrapper object */ + if (!JS_GetProperty(context, object, "$gtype", >ype_val)) + goto out; + + if (!JSVAL_IS_OBJECT(gtype_val)) + goto out; + + gtype = gjs_gtype_get_actual_gtype(context, JSVAL_TO_OBJECT(gtype_val)); + + out: + JS_EndRequest(context); + return gtype; +} diff --git a/gi/gtype.h b/gi/gtype.h new file mode 100644 index 00000000..645d6f54 --- /dev/null +++ b/gi/gtype.h @@ -0,0 +1,50 @@ +/* -*- mode: C; c-basic-offset: 4; indent-tabs-mode: nil; -*- */ +/* + * Copyright (c) 2008 litl, LLC + * Copyright (c) 2012 Red Hat, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#ifndef __GJS_GTYPE_H__ +#define __GJS_GTYPE_H__ + +#include <glib.h> + +#include <jsapi.h> + +#include <girepository.h> + +G_BEGIN_DECLS + +jsval gjs_gtype_create_proto (JSContext *context, + JSObject *module, + const char *proto_name, + JSObject *parent); + +JSObject * gjs_gtype_create_gtype_wrapper (JSContext *context, + GType gtype); + +GType gjs_gtype_get_actual_gtype (JSContext *context, + JSObject *object); + + +G_END_DECLS + +#endif /* __GJS_INTERFACE_H__ */ diff --git a/gi/object.c b/gi/object.c index adb11f84..effc6d52 100644 --- a/gi/object.c +++ b/gi/object.c @@ -26,6 +26,7 @@ #include <string.h> #include "object.h" +#include "gtype.h" #include "arg.h" #include "repo.h" #include "function.h" @@ -1395,7 +1396,7 @@ gjs_define_object_class(JSContext *context, gjs_define_static_methods(context, constructor, info); } - value = INT_TO_JSVAL(gtype); + value = OBJECT_TO_JSVAL(gjs_gtype_create_gtype_wrapper(context, gtype)); JS_DefineProperty(context, constructor, "$gtype", value, NULL, NULL, JSPROP_PERMANENT); @@ -1551,31 +1552,3 @@ gjs_g_object_from_object(JSContext *context, return priv->gobj; } - -GType -gjs_gtype_from_value(JSContext *context, - jsval val) -{ - GType gtype = G_TYPE_NONE; - - if (JSVAL_IS_INT(val)) - return JSVAL_TO_INT(val); - - if (JSVAL_IS_OBJECT(val)) { - JS_BeginRequest(context); - - JSObject *obj = JSVAL_TO_OBJECT(val); - jsval gtype_val; - if (!JS_GetProperty(context, obj, "$gtype", >ype_val)) - goto out; - - if (!JSVAL_IS_INT(gtype_val)) - goto out; - - gtype = JSVAL_TO_INT(gtype_val); - } - - out: - JS_EndRequest(context); - return gtype; -} diff --git a/gi/object.h b/gi/object.h index d6b93758..e0dc3a43 100644 --- a/gi/object.h +++ b/gi/object.h @@ -44,8 +44,6 @@ JSObject* gjs_object_from_g_object (JSContext *context, GObject *gobj); GObject* gjs_g_object_from_object (JSContext *context, JSObject *obj); -GType gjs_gtype_from_value (JSContext *context, - jsval value); G_END_DECLS @@ -29,6 +29,7 @@ #include "arg.h" #include "object.h" #include "repo.h" +#include "gtype.h" #include <gjs/gjs-module.h> #include <gjs/compat.h> @@ -189,14 +190,14 @@ param_new_internal(JSContext *cx, return JS_FALSE; if (!JSVAL_IS_STRING(argv[0]) || - !JSVAL_IS_INT(argv[1]) || + !JSVAL_IS_OBJECT(argv[1]) || !JSVAL_IS_STRING(argv[2]) || !JSVAL_IS_STRING(argv[3]) || !JSVAL_IS_INT(argv[4])) return JS_FALSE; prop_name = gjs_string_get_ascii(cx, argv[0]); - prop_gtype = JSVAL_TO_INT(argv[1]); + prop_gtype = gjs_gtype_get_actual_gtype(cx, JSVAL_TO_OBJECT(argv[1])); prop_type = G_TYPE_FUNDAMENTAL(prop_gtype); nick = gjs_string_get_ascii(cx, argv[2]); blurb = gjs_string_get_ascii(cx, argv[3]); @@ -298,7 +299,12 @@ param_new_internal(JSContext *cx, GIEnumInfo *info; gint64 default_value; - gtype = gjs_gtype_from_value(cx, argv[0]); + if (!JSVAL_IS_OBJECT(argv[0])) { + gjs_throw(cx, "Passed invalid GType to GParamSpecEnum constructor"); + goto out; + } + + gtype = gjs_gtype_get_actual_gtype(cx, JSVAL_TO_OBJECT(argv[0])); if (gtype == G_TYPE_NONE) { gjs_throw(cx, "Passed invalid GType to GParamSpecEnum constructor"); goto out; @@ -321,7 +327,12 @@ param_new_internal(JSContext *cx, GType gtype; gint64 default_value; - gtype = gjs_gtype_from_value(cx, argv[0]); + if (!JSVAL_IS_OBJECT(argv[0])) { + gjs_throw(cx, "Passed invalid GType to GParamSpecFlags constructor"); + goto out; + } + + gtype = gjs_gtype_get_actual_gtype(cx, JSVAL_TO_OBJECT(argv[0])); if (gtype == G_TYPE_NONE) { gjs_throw(cx, "Passed invalid GType to GParamSpecFlags constructor"); goto out; diff --git a/test/js/testGIMarshalling.js b/test/js/testGIMarshalling.js index 5b10c3c6..57dcbfcb 100644 --- a/test/js/testGIMarshalling.js +++ b/test/js/testGIMarshalling.js @@ -16,6 +16,7 @@ const GIMarshallingTests = imports.gi.GIMarshallingTests; // We use Gio to have some objects that we know exist const Gio = imports.gi.Gio; +const GObject = imports.gi.GObject; const Lang = imports.lang; function testCArray() { @@ -201,4 +202,32 @@ function testGValue() { assertArrayEquals([42, "42", true], thing); } +function testGType() { + assertEquals("void", GObject.TYPE_NONE.name); + assertEquals("gchararray", GObject.TYPE_STRING.name); + + // Make sure "name" is readonly + GObject.TYPE_STRING.name = "foo"; + assertEquals("gchararray", GObject.TYPE_STRING.name); + + // Make sure "name" is permanent + assertFalse((delete GObject.TYPE_STRING.name)); + + // Make sure "toString" works + assertEquals("[object GType for 'void']", GObject.TYPE_NONE.toString()); + assertEquals("[object GType for 'gchararray']", GObject.TYPE_STRING.toString()); + + // Marshalling tests + assertEquals(GObject.TYPE_NONE, GIMarshallingTests.gtype_return()); + assertEquals(GObject.TYPE_STRING, GIMarshallingTests.gtype_string_return()); + + GIMarshallingTests.gtype_in(GObject.TYPE_NONE); + GIMarshallingTests.gtype_string_in(GObject.TYPE_STRING); + + assertEquals(GObject.TYPE_NONE, GIMarshallingTests.gtype_out()); + assertEquals(GObject.TYPE_STRING, GIMarshallingTests.gtype_string_out()); + + assertEquals(GObject.TYPE_INT, GIMarshallingTests.gtype_inout(GObject.TYPE_NONE)); +} + gjstestRun(); |