[gjs] gi: Add a nicer toString() for boxed objects too



commit 58cb9cd2db685f6d0dd095cfa5159dd0b9c0b147
Author: Colin Walters <walters verbum org>
Date:   Sat Dec 1 11:44:22 2012 -0500

    gi: Add a nicer toString() for boxed objects too
    
    Previously we just printed "GLib_Boxed"; but now you see the same
    thing we print for GObjects.  This is useful for all the same reasons,
    but the one I wanted in particular for debugging my app was to know
    the GIName/GType.
    
    https://bugzilla.gnome.org/show_bug.cgi?id=689434

 Makefile.am     |    2 +
 gi/boxed.c      |   24 +++++++++++++++++
 gi/object.c     |   39 ++++++++--------------------
 gi/proxyutils.c |   76 +++++++++++++++++++++++++++++++++++++++++++++++++++++++
 gi/proxyutils.h |   42 ++++++++++++++++++++++++++++++
 gi/union.c      |   25 ++++++++++++++++++
 6 files changed, 180 insertions(+), 28 deletions(-)
---
diff --git a/Makefile.am b/Makefile.am
index 336a4c1..3231754 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -61,6 +61,7 @@ nobase_gjs_module_include_HEADERS =	\
 noinst_HEADERS +=		\
 	gjs/jsapi-private.h	\
 	gjs/profiler.h		\
+	gi/proxyutils.h		\
 	gjs/unit-test-utils.h	\
 	util/crash.h		\
 	util/error.h		\
@@ -138,6 +139,7 @@ libgjs_la_SOURCES += \
 	gi/object.c	\
 	gi/foreign.c	\
 	gi/param.c	\
+	gi/proxyutils.c	\
         gi/repo.c	\
 	gi/union.c	\
         gi/value.c	\
diff --git a/gi/boxed.c b/gi/boxed.c
index c6e58e9..d7e0920 100644
--- a/gi/boxed.c
+++ b/gi/boxed.c
@@ -31,6 +31,7 @@
 #include <gjs/gjs-module.h>
 #include <gjs/compat.h>
 #include "repo.h"
+#include "proxyutils.h"
 #include "function.h"
 #include "gtype.h"
 
@@ -893,6 +894,28 @@ define_boxed_class_fields (JSContext *context,
     return JS_TRUE;
 }
 
+static JSBool
+to_string_func(JSContext *context,
+               uintN      argc,
+               jsval     *vp)
+{
+    JSObject *obj = JS_THIS_OBJECT(context, vp);
+    Boxed *priv;
+    JSBool ret = JS_FALSE;
+    jsval retval;
+
+    if (!priv_from_js_with_typecheck(context, obj, &priv))
+        goto out;
+    
+    if (!_gjs_proxy_to_string_func(context, obj, "boxed", (GIBaseInfo*)priv->info,
+                                   priv->gtype, priv->gboxed, &retval))
+        goto out;
+
+    ret = JS_TRUE;
+    JS_SET_RVAL(context, vp, retval);
+ out:
+    return ret;
+}
 
 /* The bizarre thing about this vtable is that it applies to both
  * instances of the object, and to the prototype that instances of the
@@ -928,6 +951,7 @@ static JSPropertySpec gjs_boxed_proto_props[] = {
 };
 
 static JSFunctionSpec gjs_boxed_proto_funcs[] = {
+    { "toString", (JSNative)to_string_func, 0, 0 },
     { NULL }
 };
 
diff --git a/gi/object.c b/gi/object.c
index 3cfac29..1b73435 100644
--- a/gi/object.c
+++ b/gi/object.c
@@ -31,6 +31,7 @@
 #include "arg.h"
 #include "repo.h"
 #include "function.h"
+#include "proxyutils.h"
 #include "param.h"
 #include "value.h"
 #include "keep-alive.h"
@@ -1441,10 +1442,6 @@ emit_func(JSContext *context,
     return ret;
 }
 
-/* Default spidermonkey toString is worthless.  Replace it
- * with something that gives us both the introspection name
- * and a memory address.
- */
 static JSBool
 to_string_func(JSContext *context,
                uintN      argc,
@@ -1452,40 +1449,26 @@ to_string_func(JSContext *context,
 {
     JSObject *obj = JS_THIS_OBJECT(context, vp);
     ObjectInstance *priv;
-    char *strval;
-    JSBool ret;
-    const char *namespace;
-    const char *name;
+    JSBool ret = JS_FALSE;
     jsval retval;
 
     if (!do_base_typecheck(context, obj, JS_TRUE))
-        return JS_FALSE;
+        goto out;
 
     priv = priv_from_js(context, obj);
 
     if (priv == NULL) {
         throw_priv_is_null_error(context);
-        return JS_FALSE; /* wrong class passed in */
-    }
-
-    if (priv->info) {
-        namespace = g_base_info_get_namespace( (GIBaseInfo*) priv->info);
-        name = g_base_info_get_name( (GIBaseInfo*) priv->info);
-    } else {
-        namespace = "";
-        name = g_type_name(priv->gtype);
-    }
-
-    if (priv->gobj == NULL) {
-        strval = g_strdup_printf ("[object prototype of GIName:%s.%s jsobj %p]", namespace, name, obj);
-    } else {
-        strval = g_strdup_printf ("[object instance proxy GIName:%s.%s jsobj %p native %p]", namespace, name, obj, priv->gobj);
+        goto out;  /* wrong class passed in */
     }
+    
+    if (!_gjs_proxy_to_string_func(context, obj, "object", (GIBaseInfo*)priv->info,
+                                   priv->gtype, priv->gobj, &retval))
+        goto out;
 
-    ret = gjs_string_from_utf8 (context, strval, -1, &retval);
-    if (ret)
-        JS_SET_RVAL(context, vp, retval);
-    g_free (strval);
+    ret = JS_TRUE;
+    JS_SET_RVAL(context, vp, retval);
+ out:
     return ret;
 }
 
diff --git a/gi/proxyutils.c b/gi/proxyutils.c
new file mode 100644
index 0000000..b15c4e5
--- /dev/null
+++ b/gi/proxyutils.c
@@ -0,0 +1,76 @@
+/* -*- mode: C; c-basic-offset: 4; indent-tabs-mode: nil; -*- */
+/*
+ * 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 <string.h>
+
+#include "proxyutils.h"
+
+/* Default spidermonkey toString is worthless.  Replace it
+ * with something that gives us both the introspection name
+ * and a memory address.
+ */
+JSBool
+_gjs_proxy_to_string_func(JSContext  *context,
+                          JSObject   *this_obj,
+                          const char *objtype,
+                          GIBaseInfo *info,
+                          GType       gtype,
+                          gpointer    native_address,
+                          jsval      *rval)
+{
+    GString *buf;
+    JSBool ret = JS_FALSE;
+
+    buf = g_string_new("");
+    g_string_append_c(buf, '[');
+    g_string_append(buf, objtype);
+    if (native_address == NULL)
+        g_string_append(buf, " prototype of");
+    else
+        g_string_append(buf, " instance proxy");
+
+    if (info != NULL) {
+        g_string_append_printf(buf, " GIName:%s.%s",
+                               g_base_info_get_namespace(info),
+                               g_base_info_get_name(info));
+    } else {
+        g_string_append(buf, " GType:");
+        g_string_append(buf, g_type_name(gtype));
+    }
+
+    g_string_append_printf(buf, " jsobj %p", this_obj);
+    if (native_address != NULL)
+        g_string_append_printf(buf, " native %p", native_address);
+    
+    g_string_append_c(buf, ']');
+
+    if (!gjs_string_from_utf8 (context, buf->str, -1, rval))
+        goto out;
+
+    ret = JS_TRUE;
+ out:
+    g_string_free (buf, TRUE);
+    return ret;
+}
diff --git a/gi/proxyutils.h b/gi/proxyutils.h
new file mode 100644
index 0000000..8ca7643
--- /dev/null
+++ b/gi/proxyutils.h
@@ -0,0 +1,42 @@
+/* -*- mode: C; c-basic-offset: 4; indent-tabs-mode: nil; -*- */
+/*
+ * Copyright (c) 2008  litl, LLC
+ *
+ * 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_PROXYUTILS_H__
+#define __GJS_PROXYUTILS_H__
+
+#include "gjs/jsapi-util.h"
+#include <gjs/gi.h>
+
+G_BEGIN_DECLS
+
+JSBool _gjs_proxy_to_string_func(JSContext  *context,
+                                 JSObject   *this_obj,
+                                 const char *objtype,
+                                 GIBaseInfo *info,
+                                 GType       gtype,
+                                 gpointer    native_address,
+                                 jsval      *ret);
+
+G_END_DECLS
+
+#endif  /* __GJS_OBJECT_H__ */
diff --git a/gi/union.c b/gi/union.c
index 999e2cb..e68605b 100644
--- a/gi/union.c
+++ b/gi/union.c
@@ -34,6 +34,7 @@
 #include <gjs/gjs-module.h>
 #include <gjs/compat.h>
 #include "repo.h"
+#include "proxyutils.h"
 #include "function.h"
 #include "gtype.h"
 #include <girepository.h>
@@ -278,6 +279,29 @@ union_finalize(JSContext *context,
     g_slice_free(Union, priv);
 }
 
+static JSBool
+to_string_func(JSContext *context,
+               uintN      argc,
+               jsval     *vp)
+{
+    JSObject *obj = JS_THIS_OBJECT(context, vp);
+    Union *priv;
+    JSBool ret = JS_FALSE;
+    jsval retval;
+
+    if (!priv_from_js_with_typecheck(context, obj, &priv))
+        goto out;
+    
+    if (!_gjs_proxy_to_string_func(context, obj, "union", (GIBaseInfo*)priv->info,
+                                   priv->gtype, priv->gboxed, &retval))
+        goto out;
+
+    ret = JS_TRUE;
+    JS_SET_RVAL(context, vp, retval);
+ out:
+    return ret;
+}
+
 /* The bizarre thing about this vtable is that it applies to both
  * instances of the object, and to the prototype that instances of the
  * class have.
@@ -306,6 +330,7 @@ static JSPropertySpec gjs_union_proto_props[] = {
 };
 
 static JSFunctionSpec gjs_union_proto_funcs[] = {
+    { "toString", (JSNative)to_string_func, 0, 0 },
     { NULL }
 };
 



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]