[glib/wip/otte/interface-types: 3/6] gtype: Add g_type_interface_instantiatable_prerequisite()
- From: Matthias Clasen <matthiasc src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [glib/wip/otte/interface-types: 3/6] gtype: Add g_type_interface_instantiatable_prerequisite()
- Date: Wed, 28 Oct 2020 15:03:06 +0000 (UTC)
commit 870461b7f121706468235bf46758debe1f03bef2
Author: Benjamin Otte <otte redhat com>
Date: Mon Nov 25 19:40:39 2019 +0100
gtype: Add g_type_interface_instantiatable_prerequisite()
This function returns the most specific instantiatable type
that is a prerequisite for a given interface.
This type is necessary in particular when dealing with GValues
because a GValue contains an instance of a type.
This commit includes tests for the new API.
docs/reference/gobject/gobject-sections.txt | 1 +
gobject/gtype.c | 45 +++++++++++++++++++++
gobject/gtype.h | 3 ++
gobject/tests/type.c | 63 +++++++++++++++++++++++++++++
4 files changed, 112 insertions(+)
---
diff --git a/docs/reference/gobject/gobject-sections.txt b/docs/reference/gobject/gobject-sections.txt
index f52d95379..36552b1b3 100644
--- a/docs/reference/gobject/gobject-sections.txt
+++ b/docs/reference/gobject/gobject-sections.txt
@@ -65,6 +65,7 @@ g_type_default_interface_unref
g_type_children
g_type_interfaces
g_type_interface_prerequisites
+g_type_interface_instantiatable_prerequisite
g_type_set_qdata
g_type_get_qdata
g_type_query
diff --git a/gobject/gtype.c b/gobject/gtype.c
index c25575800..ff5a8b01d 100644
--- a/gobject/gtype.c
+++ b/gobject/gtype.c
@@ -1689,6 +1689,51 @@ g_type_interface_prerequisites (GType interface_type,
}
}
+/**
+ * g_type_interface_instantiatable_prerequisite:
+ * @interface_type: an interface type
+ *
+ * Returns the most specific instantiatable prerequisite of an
+ * interface type. If the interface type has no instantiatable
+ * prerequisite, %G_TYPE_INVALID is returned.
+ *
+ * Returns: the instantiatable prerequisite type or %G_TYPE_INVALID if none
+ *
+ * Since: 2.68
+ **/
+GType
+g_type_interface_instantiatable_prerequisite (GType interface_type)
+{
+ TypeNode *inode = NULL;
+ TypeNode *iface;
+ guint i;
+
+ g_return_val_if_fail (G_TYPE_IS_INTERFACE (interface_type), G_TYPE_INVALID);
+
+ iface = lookup_type_node_I (interface_type);
+ if (iface == NULL)
+ return G_TYPE_INVALID;
+
+ G_READ_LOCK (&type_rw_lock);
+
+ for (i = 0; i < IFACE_NODE_N_PREREQUISITES (iface); i++)
+ {
+ GType prerequisite = IFACE_NODE_PREREQUISITES (iface)[i];
+ TypeNode *node = lookup_type_node_I (prerequisite);
+ if (node->is_instantiatable)
+ {
+ if (!inode || type_node_is_a_L (node, inode))
+ inode = node;
+ }
+ }
+
+ G_READ_UNLOCK (&type_rw_lock);
+
+ if (inode)
+ return NODE_TYPE (inode);
+ else
+ return G_TYPE_INVALID;
+}
static IFaceHolder*
type_iface_peek_holder_L (TypeNode *iface,
diff --git a/gobject/gtype.h b/gobject/gtype.h
index 89178411f..d839e4e3a 100644
--- a/gobject/gtype.h
+++ b/gobject/gtype.h
@@ -1300,6 +1300,9 @@ void g_type_interface_add_prerequisite (GType interface_type,
GLIB_AVAILABLE_IN_ALL
GType*g_type_interface_prerequisites (GType interface_type,
guint *n_prerequisites);
+GLIB_AVAILABLE_IN_2_68
+GType g_type_interface_instantiatable_prerequisite
+ (GType interface_type);
GLIB_DEPRECATED_IN_2_58
void g_type_class_add_private (gpointer g_class,
gsize private_size);
diff --git a/gobject/tests/type.c b/gobject/tests/type.c
index c5db7e992..30e138a77 100644
--- a/gobject/tests/type.c
+++ b/gobject/tests/type.c
@@ -40,6 +40,63 @@ foo_default_init (FooInterface *iface)
{
}
+typedef struct {
+ GTypeInterface g_iface;
+} BaaInterface;
+
+GType baa_get_type (void);
+
+G_DEFINE_INTERFACE (Baa, baa, G_TYPE_INVALID)
+
+static void
+baa_default_init (BaaInterface *iface)
+{
+}
+
+typedef struct {
+ GTypeInterface g_iface;
+} BooInterface;
+
+GType boo_get_type (void);
+
+G_DEFINE_INTERFACE_WITH_CODE (Boo, boo, G_TYPE_INVALID,
+ g_type_interface_add_prerequisite (g_define_type_id, baa_get_type ()))
+
+static void
+boo_default_init (BooInterface *iface)
+{
+}
+
+typedef struct {
+ GTypeInterface g_iface;
+} BibiInterface;
+
+GType bibi_get_type (void);
+
+G_DEFINE_INTERFACE (Bibi, bibi, G_TYPE_INITIALLY_UNOWNED)
+
+static void
+bibi_default_init (BibiInterface *iface)
+{
+}
+
+typedef struct {
+ GTypeInterface g_iface;
+} BozoInterface;
+
+GType bozo_get_type (void);
+
+G_DEFINE_INTERFACE_WITH_CODE (Bozo, bozo, G_TYPE_INVALID,
+ g_type_interface_add_prerequisite (g_define_type_id, foo_get_type ());
+ g_type_interface_add_prerequisite (g_define_type_id, bibi_get_type ()))
+
+static void
+bozo_default_init (BozoInterface *iface)
+{
+}
+
+
+
static void
test_interface_prerequisite (void)
{
@@ -52,6 +109,7 @@ test_interface_prerequisite (void)
g_assert_cmpint (n_prereqs, ==, 2);
g_assert (prereqs[0] == bar_get_type ());
g_assert (prereqs[1] == G_TYPE_OBJECT);
+ g_assert (g_type_interface_instantiatable_prerequisite (foo_get_type ()) == G_TYPE_OBJECT);
iface = g_type_default_interface_ref (foo_get_type ());
parent = g_type_interface_peek_parent (iface);
@@ -59,6 +117,11 @@ test_interface_prerequisite (void)
g_type_default_interface_unref (iface);
g_free (prereqs);
+
+ g_assert_cmpint (g_type_interface_instantiatable_prerequisite (baa_get_type ()), ==, G_TYPE_INVALID);
+ g_assert_cmpint (g_type_interface_instantiatable_prerequisite (boo_get_type ()), ==, G_TYPE_INVALID);
+
+ g_assert_cmpint (g_type_interface_instantiatable_prerequisite (bozo_get_type ()), ==,
G_TYPE_INITIALLY_UNOWNED);
}
typedef struct {
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]