After an evaluation, GNOME has moved from Bugzilla to GitLab. Learn more about GitLab.
No new issues can be reported in GNOME Bugzilla anymore.
To report an issue in a GNOME project, go to GNOME GitLab.
Do not go to GNOME Gitlab for: Bluefish, Doxygen, GnuCash, GStreamer, java-gnome, LDTP, NetworkManager, Tomboy.
Bug 581686 - Support "extra types" in typelib, for parameterized containers
Support "extra types" in typelib, for parameterized containers
Status: RESOLVED WONTFIX
Product: gobject-introspection
Classification: Platform
Component: general
unspecified
Other Linux
: Normal enhancement
: ---
Assigned To: gobject-introspection Maintainer(s)
gobject-introspection Maintainer(s)
Depends on:
Blocks: 581695
 
 
Reported: 2009-05-07 03:58 UTC by C. Scott Ananian
Modified: 2017-04-02 20:52 UTC
See Also:
GNOME target: ---
GNOME version: ---


Attachments
Support-extra-types-in-typelib-used-for-parameterized-cont.patch (10.23 KB, patch)
2009-05-07 03:59 UTC, C. Scott Ananian
none Details | Review
Parse-extra-elements-in-.gir-XML-and-write-v2.1-typelib.patch (12.37 KB, patch)
2009-05-07 03:59 UTC, C. Scott Ananian
none Details | Review

Description C. Scott Ananian 2009-05-07 03:58:50 UTC
Infrastructures like dbus-gtype-specialized (in dbus-glib) register additional GTypes to record precise information about parameterized types such as GI_TYPE_TAG_ARRAY, GI_TYPE_TAG_GLIST, GI_TYPE_TAG_GSLIST, and GI_TYPE_TAG_GHASH.
Knowing the element type is necessary to properly marshall objects of these types to/from bindings, and having a GType to represent the full parameterized type is necessary to use GValue and other genericity mechanisms.

The attached patches add support for encoding such "extra" GTypes in a typelib in a backwards-compatible way that won't break existing typelibs.  We simply add some structures describing the GType->GI_INFO_TYPE_TYPE mapping to the end of the type lib, and add them to the set of places where g_irepository_find_by_gtype() looks for type information.  The minor version of the typelib is incremented by one to signal the presence of this information.  Extra types are defined by an <extra> element in the GIR XML, for example:
  <extra glib:type-name="GHashTable_gchararray+gchararray_"
         glib:get-type="nm_string_map_get_type">
    <type name="GLib.HashTable" c:type="GHashTable">
      <type name="utf8" />
      <type name="utf8" />
    </type>
  </extra>
with the patch for bug 581685, this could also be written as:
  <extra glib:type-name="GHashTable_gchararray+gchararray_"
         glib:get-type="nm_string_map_get_type">
    <type name="GLib.HashTable<utf8,utf8>" c:type="GHashTable"/>
  </extra>
Comment 1 C. Scott Ananian 2009-05-07 03:59:29 UTC
Created attachment 134155 [details] [review]
Support-extra-types-in-typelib-used-for-parameterized-cont.patch
Comment 2 C. Scott Ananian 2009-05-07 03:59:55 UTC
Created attachment 134156 [details] [review]
Parse-extra-elements-in-.gir-XML-and-write-v2.1-typelib.patch
Comment 3 Colin Walters 2009-05-07 21:04:28 UTC
Hmm.  I'm a little unsure how this is actually used.  How do we detect the dbus-glib type specialization stuff?  

In an ideal world dbus-glib could pick this stuff up from introspection, it was kind of the original goal. 
Comment 4 C. Scott Ananian 2009-05-11 15:33:33 UTC
At the moment, this is used by manually injecting <extra> clauses into your .gir file, in the form above.  libnm, for example, specifies appropriate <extra> clauses for the specialized types it uses, and other dbus-glib libraries would do the same; it's not a problem if an "extra type" is specified by more than one library.  The goal was to avoid a dependence on any particular scheme for associating GValues with parameterized types; you can use this mechanism to specify alternative schemes if you like.  It involves a little extra manual intervention at the moment; one could imagine extending g-ir-scanner to find the specialized types automagically, but it would introduce a dependency on dbus-glib.

Getting dbus-glib to pick types up from introspection is not straightforward.  The issue is that dbus-glib is dealing with *runtime* types, as expressed as GValue objects.  You still need a mechanism to map GTypes (as stored in a GValue object) to some parameterized GIR type.  Unless GValue is converted to use GIBaseInfo to represent its types, you will always need some mechanism to convert between GType and GIBaseInfo.

I did consider allowing libraries to specify a *function* for mapping between GType and GIR type, but the implementation of this gets complicated quick.  The extra type mechanism may not be the "long term" solution to the parameterized type problem, but it will always be useful as a way to patch any holes in the GType->GIR mappings.
Comment 5 C. Scott Ananian 2009-05-11 16:50:34 UTC
Incidentally, it's not just parameterized types that can use <extra> clauses; I was just looking through the big code and found a place where we wanted to map the GType 'BigGError' to 'GError' and were hacking around it by defining a trivial subclass.  We could use <extra> to do this mapping more cleanly.
Comment 6 Havoc Pennington 2009-05-13 20:12:55 UTC
Some irc discussion with dcbw, owen, david z, seemed to conclude that APIs meant to be bindable should simply never be returning GHashTable. Or that the parameterization should not be reflected in the GType (only in the introspection annotations), at least. dcbw says we should not use the settings objects, they are a "C binding" and we're meant to reimplement.
Comment 7 C. Scott Ananian 2009-05-18 17:27:59 UTC
I'm not convinced.  Like I said, it's really an issue of mapping GValue to GIR type, it's not just libnm where this arises.  This mechanism just introduces a method to make the GValue<->GIR mapping complete.

And GHashTable isn't the only user, either: arrays are another big user of "extra" types.   We're really talking about how GValue interacts with GIR here, not about libnm.
Comment 8 C. Scott Ananian 2009-05-18 17:30:23 UTC
See also bug 581687, which describes how this patch allows support for GArray and the new G_TYPE_BYTE_ARRAY
Comment 9 Colin Walters 2009-06-04 21:31:35 UTC
See the bug 581106  for an attempt at having some mapping data accessible from GHashTable etc.  It doesn't support full recursion.

As for Comment #7, I totally see your argument, being the person who inflicted the specialized stuff in dbus-glib on the world =)  But...I guess I'd like to see more examples and use cases.

We know we would need it to bind "nm_string_map".  Anything else?

So if this went in, would there also be a patch for gjs to handle the extra types?

Also if we do put this in, let's just break the typelib format, we haven't done a stable release, so it's not a problem.  Is there a reason we can't retrieve the nested types using g_type_info_get_param_type ?
Comment 10 C. Scott Ananian 2009-06-04 23:40:58 UTC
Well, the <extra> types I currently have for libnm are:

<inject path="namespace/">
  <extra glib:type-name="GHashTable_gchararray+gchararray_"
         glib:get-type="nm_string_map_get_type">
    <type name="GLib.HashTable" c:type="GHashTable">
      <type name="utf8"/>
      <type name="utf8"/>
    </type>
  </extra>
  <extra glib:type-name="GSList_gchararray_">
    <type name="GLib.SList" c:type="GSList">
      <type name="utf8"/>
    </type>
  </extra>
  <extra glib:type-name="GArray_guint_">
    <type name="GLib.Array" c:type="GArray">
      <type name="uint"/>
    </type>
  </extra>
  <extra glib:type-name="GArray_guchar_">
    <type name="GLib.Array" c:type="GArray">
      <type name="uint8"/>
    </type>
  </extra>
  <extra glib:type-name="GPtrArray_GArray_guint__">
    <type name="GLib.PtrArray" c:type="GPtrArray">
      <type name="GLib.Array" c:type="GArray">
        <type name="uint"/>
      </type>
    </type>
  </extra>
</inject>

These are dbus-glib specialized types, of course, but anyone who wants to put a container type in a GValue is going to have to do something similar -- unless and until GType is unified with GIRegisteredTypeInfo.

It's actually no harder to add the extra type stuff "backwards compatibly" than it is to do so otherwise.  The extra type table has to go somewhere; it might as well go at the end where older girepository code will ignore it.

It's been a while since I wrote this now, but I think we can't use g_type_info_get_param_type because (a) the "extra" type isn't necessarily parameterized; in litl's code we wanted to define a BigGError alias to GError using the extra type mechanism, and (b) parameterized types don't have the fields from RegisteredTypeBlob (gtype_name/gtype_init) that we need.  What is wanted is a RegisteredTypeBlob that was just an alias for another type.
Comment 11 C. Scott Ananian 2009-06-10 18:46:19 UTC
(In reply to comment #9)
> So if this went in, would there also be a patch for gjs to handle the extra
> types?

Yes, those patches are in bug 581695, and the extra types support (better conversions of GValue) can be used by the patch attached to bug 581696 for GArray support, allowing GArrays to be wrapped as GValues using extra types.
Comment 12 André Klapper 2015-02-07 17:15:46 UTC
[Mass-moving gobject-introspection tickets to its own Bugzilla product - see bug 708029. Mass-filter your bugmail for this message: introspection20150207 ]
Comment 13 Philip Chimento 2017-04-02 20:52:53 UTC
It seems that in the intervening time, the GIR format has crystallized around not having "extra types". Closing this, in the absence of a compelling use case.