[glib/gvariant-varargs: 4/5] varargs docs
- From: Ryan Lortie <ryanl src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [glib/gvariant-varargs: 4/5] varargs docs
- Date: Mon, 8 Mar 2010 00:11:11 +0000 (UTC)
commit 3a5b25fa4963c24df6b3402c1a54cd8e5e7e3eca
Author: Ryan Lortie <desrt desrt ca>
Date: Sat Mar 6 18:14:27 2010 -0500
varargs docs
docs/reference/glib/glib-docs.sgml | 1 +
docs/reference/glib/gvariant-varargs.xml | 982 ++++++++++++++++++++++++++++++
2 files changed, 983 insertions(+), 0 deletions(-)
---
diff --git a/docs/reference/glib/glib-docs.sgml b/docs/reference/glib/glib-docs.sgml
index 47c9a9a..0ab911b 100644
--- a/docs/reference/glib/glib-docs.sgml
+++ b/docs/reference/glib/glib-docs.sgml
@@ -121,6 +121,7 @@ synchronize their operation.
<xi:include href="xml/allocators.xml" />
<xi:include href="xml/gvarianttype.xml"/>
<xi:include href="xml/gvariant.xml"/>
+ <xi:include href="gvariant-varargs.xml"/>
</chapter>
<chapter id="tools">
diff --git a/docs/reference/glib/gvariant-varargs.xml b/docs/reference/glib/gvariant-varargs.xml
new file mode 100644
index 0000000..6d58a5b
--- /dev/null
+++ b/docs/reference/glib/gvariant-varargs.xml
@@ -0,0 +1,982 @@
+<?xml version='1.0' encoding='utf-8'?>
+
+<refentry id='gvariant-varargs'>
+ <refentrytitle>GVariant Format Strings</refentrytitle>
+
+ <refsect1>
+ <title>Variable Argument Conversions</title>
+
+ <para>
+ This page attempts to document how to perform variable argument conversions with GVariant.
+ </para>
+ <para>
+ A conversion string is a two-way mapping between a single <link linkend='GVariant'>GVariant</link> value and one or
+ more C values.
+ </para>
+ <para>
+ A conversion from C values into a <link linkend='GVariant'>GVariant</link> value is made using the
+ <link linkend='g-variant-new'><function>g_variant_new()</function></link> function. A conversion from a
+ <link linkend='GVariant'>GVariant</link> into C values is made using the
+ <link linkend='g-variant-get'><function>g_variant_get()</function></link> function.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>Syntax</title>
+
+ <para>
+ This section exhaustively describes all possibilities for GVariant format strings. There are no valid forms of
+ format strings other than those described here. Please note that the format string syntax is likely to expand in the
+ future.
+ </para>
+ <para>
+ Valid format strings have one of the following forms:
+ </para>
+ <itemizedlist>
+ <listitem>
+ <para>any type string</para>
+ </listitem>
+ <listitem>
+ <para>
+ a type string prefixed with a '<literal>@</literal>'
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ a type string of a concrete, fixed-sized type, prefixed with a '<literal>&</literal>'
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ a type string of a concrete, fixed-sized type, prefixed with a '<literal>&a</literal>'
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ '<literal>&s</literal>' '<literal>&o</literal>', '<literal>&g</literal>', '<literal>^as</literal>',
+ '<literal>^ao</literal>', '<literal>^ag</literal>', '<literal>^a&s</literal>', '<literal>^a&o</literal>' or
+ '<literal>^a&g</literal>'
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ any conversion string, prefixed with an '<literal>m</literal>'
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ a sequence of zero or more format strings strings, concatenated and enclosed in parentheses
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ an opening brace, followed by two format strings, followed by a closing brace (subject to the constraint that the
+ first format string correspond to a type valid for use as the key type of a dictionary)
+ </para>
+ </listitem>
+ </itemizedlist>
+ </refsect1>
+ <refsect1>
+ <title>Symbols</title>
+
+ <para>
+ The following table describes the rough meaning of symbols that may appear inside a GVariant format string. Each
+ symbol is described in detail in its own section, including usage examples.
+ </para>
+
+ <informaltable>
+ <tgroup cols='2'>
+ <colspec colname='col_0'/>
+ <colspec colname='col_1'/>
+ <tbody>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>Symbol</emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>Meaning</emphasis>
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>b</literal>, <literal>y</literal>, <literal>n</literal>, <literal>q</literal>, <literal>i</literal>,
+ <literal>u</literal>, <literal>x</literal>, <literal>t</literal>, <literal>h</literal>, <literal>d</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Used for building or deconstructing boolean, byte and numeric types. See
+ <link linkend='gvariant-format-strings-numeric-types'>Numeric Types</link> below.
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>s</literal>, <literal>o</literal>, <literal>g</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Used for building or deconstructing string types. See
+ <link linkend='gvariant-format-strings-strings'>Strings</link> below.
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'><literal>v</literal></emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Used for building or deconstructing variant types. See
+ <link linkend='gvariant-format-strings-variant'>Variants</link> below.
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>a</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Used for building or deconstructing arrays. See
+ <link linkend='gvariant-format-strings-arrays'>Arrays</link> below.
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>m</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Used for building or deconstructing maybe types. See
+ <link linkend='gvariant-format-strings-maybe-types'>Maybe Types</link> below.
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>()</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Used for building or deconstructing tuples. See
+ <link linkend='gvariant-format-strings-tuples'>Tuples</link> below.
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>{}</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Used for building or deconstructing dictionary entries. See
+ <link linkend='gvariant-format-strings-dictionaries'>Dictionaries</link> below.
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>@</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Used as a prefix on a GVariant type string (not format string). Denotes that a pointer to a
+ <link linkend='GVariant'>GVariant</link> should be used in place of the normal C type or types. For
+ <link linkend='g-variant-new'><function>g_variant_new()</function></link> this means that you must pass a
+ non-<link linkend='NULL--CAPS'><literal>NULL</literal></link> <code>(<link linkend='GVariant'>GVariant</link>
+ *)</code>. For <link linkend='g-variant-get'><function>g_variant_get()</function></link> this means that you
+ must pass a pointer to a <code>(<link linkend='GVariant'>GVariant</link> *)</code> for the value to be returned
+ by reference or <link linkend='NULL--CAPS'><literal>NULL</literal></link> to ignore the value. See
+ <link linkend='gvariant-format-strings-gvariant'><code>GVariant *</code></link> below.
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>*</literal>, <literal>?</literal>, <literal>r</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Exactly equivalent to <literal>@*</literal>, <literal>@?</literal> and <literal>@r</literal>. Provided only for
+ completeness so that all GVariant type strings can be used also as format strings. See <link
+ linkend='gvariant-format-strings-gvariant'><code>GVariant *</code></link> below.
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'><literal>&</literal></emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Used as a prefix on a GVariant type string (not format string). Denotes that a C pointer to serialised data
+ should be used in place of the normal C type. See
+ <link linkend='gvariant-format-strings-pointers'>Pointers</link> below.
+ </para>
+ </entry>
+ </row>
+
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'><literal>^</literal></emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ Used as a prefix on some specific types of format strings. See
+ <link linkend='gvariant-format-strings-convenience'>Convenience Conversions</link> below.
+ </para>
+ </entry>
+ </row>
+ </tbody>
+ </tgroup>
+ </informaltable>
+
+
+ <refsect2 id='gvariant-format-strings-numeric-types'>
+ <title>Numeric Types</title>
+ <para>
+ <emphasis role='strong'>
+ Characters: <literal>b</literal>, <literal>y</literal>, <literal>n</literal>, <literal>q</literal>,
+ <literal>i</literal>, <literal>u</literal>, <literal>x</literal>, <literal>t</literal>, <literal>h</literal>,
+ <literal>d</literal>
+ </emphasis>
+ </para>
+
+ <para>
+ Variable argument conversions from numeric types work in the most obvious way possible. Upon encountering one of
+ these characters, <link linkend='g-variant-new'><function>g_variant_new()</function></link> takes the equivalent C
+ type as an argument. <link linkend='g-variant-get'><function>g_variant_get()</function></link> takes a pointer to
+ the equivalent C type (or <link linkend='NULL--CAPS'><literal>NULL</literal></link> to ignore the value).
+ </para>
+
+ <para>
+ The equivalent C types are as follows:
+ </para>
+
+ <informaltable>
+ <tgroup cols='2'>
+ <colspec colname='col_0'/><colspec colname='col_1'/>
+ <tbody>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>Character</emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>Equivalent C type</emphasis>
+ </para>
+ </entry>
+ </row>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>b</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <link linkend='gboolean'><type>gboolean</type></link>
+ </para>
+ </entry>
+ </row>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>y</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <link linkend='guchar'><type>guchar</type></link>
+ </para>
+ </entry>
+ </row>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>n</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <link linkend='gint16'><type>gint16</type></link>
+ </para>
+ </entry>
+ </row>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>q</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <link linkend='guint16'><type>guint16</type></link>
+ </para>
+ </entry>
+ </row>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>i</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <link linkend='gint32'><type>gint32</type></link>
+ </para>
+ </entry>
+ </row>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>u</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <link linkend='guint32'><type>guint32</type></link>
+ </para>
+ </entry>
+ </row>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>x</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <link linkend='gint64'><type>gint64</type></link>
+ </para>
+ </entry>
+ </row>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>t</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <link linkend='guint64'><type>guint64</type></link>
+ </para>
+ </entry>
+ </row>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>h</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <link linkend='gint32'><type>gint32</type></link>
+ </para>
+ </entry>
+ </row>
+ <row rowsep='1'>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <emphasis role='strong'>
+ <literal>d</literal>
+ </emphasis>
+ </para>
+ </entry>
+ <entry colsep='1' rowsep='1'>
+ <para>
+ <link linkend='gdouble'><type>gdouble</type></link>
+ </para>
+ </entry>
+ </row>
+ </tbody>
+ </tgroup>
+ </informaltable>
+
+ <para>
+ Note that in C, small integer types in variable argument lists are promoted up to <link
+ linkend='gint'><type>int</type></link> or <link linkend='guint'><type>unsigned int</type></link> as appropriate, and
+ read back accordingly. <link linkend='gint'><type>int</type></link> is 32 bits on every platform on which GLib is
+ currently suported. This means that you can use C expressions of type <link linkend='gint'><type>int</type></link>
+ with <link linkend='g-variant-new'><function>g_variant_new()</function></link> and format characters
+ '<literal>b</literal>', '<literal>y</literal>', '<literal>n</literal>', '<literal>q</literal>',
+ '<literal>i</literal>', '<literal>u</literal>' and '<literal>h</literal>'. Specifically, you can use integer
+ literals with these characters.
+ </para>
+
+ <para>
+ When using the '<literal>x</literal>' and '<literal>t</literal>' characters, you must ensure that the value that you
+ provide is 64 bit. This means that you should use a cast or make use of the
+ <link linkend='G-GINT64-CONSTANT--CAPS'><literal>G_GINT64_CONSTANT</literal></link> or
+ <link linkend='G-GUINT64-CONSTANT--CAPS'><literal>G_GUINT64_CONSTANT</literal></link> macros.
+ </para>
+
+ <para>
+ No type promotion occurs when using <link linkend='g-variant-get'><function>g_variant_get()</function></link> since
+ it operates with pointers. The pointers must always point to a memory region of exactly the correct size.
+ </para>
+
+ <refsect3>
+ <title>Examples</title>
+ <informalexample><programlisting>
+<![CDATA[GVariant *value1, *value2, *value3, *value4;
+
+value1 = g_variant_new ("y", 200);
+value2 = g_variant_new ("b", TRUE);
+value3 = g_variant_new ("d", 37.5):
+value4 = g_variant_new ("x", G_GINT64_CONSTANT (998877665544332211));
+
+{
+ gdouble floating;
+ gboolean truth;
+ gint64 bignum;
+
+
+ g_variant_get (value1, "y", NULL); /* ignore the value. */
+ g_variant_get (value2, "b", &truth);
+ g_variant_get (value3, "d", &floating);
+ g_variant_get (value4, "x", &bignum);
+}]]></programlisting></informalexample>
+ </refsect3>
+ </refsect2>
+
+ <refsect2 id='gvariant-format-strings-strings'>
+ <title>Strings</title>
+ <para>
+ <emphasis role='strong'>
+ Characters: <literal>s</literal>, <literal>o</literal>, <literal>g</literal>
+ </emphasis>
+ </para>
+
+ <para>
+ String conversions occur to and from standard nul-terminated C strings. Upon encountering an
+ '<literal>s</literal>', '<literal>o</literal>' or '<literal>g</literal>' in a format string,
+ <link linkend='g-variant-new'><function>g_variant_new()</function></link> takes a <code>(const
+ <link linkend='gchar'>gchar</link> *)</code> and makes a copy of it.
+ <link linkend='NULL--CAPS'><literal>NULL</literal></link> is not a valid string. If the '<literal>o</literal>' or
+ '<literal>g</literal>' characters are used, care must be taken to ensure that the passed string is a valid DBus
+ object path or DBus type signature, respectively.
+ </para>
+ <para>
+ Upon encounting '<literal>s</literal>', '<literal>o</literal>' or '<literal>g</literal>', <link
+ linkend='g-variant-get'><function>g_variant_get()</function></link> takes a pointer to a
+ <code>(<link linkend='gchar'>gchar</link> *)</code> (ie: <code>(<link linkend='gchar'>gchar</link> **)</code>) and
+ sets it to a newly-allocated copy of the string. It is appropriate to free this copy using
+ <link linkend='g-free'><function>g_free()</function></link>.
+ <link linkend='NULL--CAPS'><literal>NULL</literal></link> may also be passed to indicate that the value of the
+ string should be ignored (in which case no copy is made).
+ </para>
+
+ <refsect3>
+ <title>Examples</title>
+ <informalexample><programlisting>
+<![CDATA[GVariant *value1, *value2, *value3;
+
+value1 = g_variant_new ("s", "hello world!");
+value2 = g_variant_new ("o", "/must/be/a/valid/path");
+value3 = g_variant_new ("g", "iias");
+
+#if 0
+ g_variant_new ("s", NULL); /* not valid: NULL is not a string. */
+#endif
+
+{
+ gchar *result;
+
+ g_variant_get (value1, "s", &result);
+ g_print ("It was '%s'\n", result);
+ g_free (result);
+}]]></programlisting></informalexample>
+ </refsect3>
+ </refsect2>
+
+ <refsect2 id='gvariant-format-strings-variants'>
+ <title>Variants</title>
+ <para>
+ <emphasis role='strong'>
+ Characters: <literal>v</literal>
+ </emphasis>
+ </para>
+
+ <para>
+ Upon encountering a '<literal>v</literal>',
+ <link linkend='g-variant-new'><function>g_variant_new()</function></link> takes a <code>(<link
+ linkend='GVariant'>GVariant</link> *)</code>. The value of the
+ <link linkend='GVariant'><type>GVariant</type></link> is used as the contents of the variant value.
+ </para>
+ <para>
+ Upon encountering a '<literal>v</literal>', <link
+ linkend='g-variant-get'><function>g_variant_get()</function></link> takes a pointer to a
+ <code>(<link linkend='GVariant'>GVariant</link> *)</code> (ie: <code>(<link linkend='GVariant'>GVariant</link> **)
+ </code>). It is set to a new reference to a <link linkend='GVariant'><type>GVariant</type></link> instance
+ containing the contents of the variant value. It is appropriate to free this reference using
+ <link linkend='g-variant-unref'><function>g_variant_unref()</function></link>.
+ <link linkend='NULL--CAPS'><literal>NULL</literal></link> may also be passed to indicate that the value should be
+ ignored (in which case no new reference is created).
+ </para>
+
+ <refsect3>
+ <title>Examples</title>
+ <informalexample><programlisting>
+<![CDATA[GVariant *x, *y;
+
+/* the following two lines are equivalent: */
+x = g_variant_new ("v", y);
+x = g_variant_new_variant (y);
+
+/* as are these: */
+g_variant_get (x, "v", &y);
+y = g_variant_get_variant (x);]]></programlisting></informalexample>
+ </refsect3>
+ </refsect2>
+
+
+ <refsect2 id='gvariant-format-strings-arrays'>
+ <title>Arrays</title>
+ <para>
+ <emphasis role='strong'>
+ Characters: <literal>a</literal>
+ </emphasis>
+ </para>
+
+ <para>
+ Upon encountering an '<literal>a</literal>' character followed by a type string,
+ <link linkend='g-variant-new'><function>g_variant_new()</function></link> will take a
+ <code>(<link linkend='GVariantBuilder'>GVariantBuilder</link> *)</code> that has been created as an array builder
+ for an array of the type given in the type string. The builder will have
+ <link linkend='g-variant-builder-end'><function>g_variant_builder_end()</function></link> called on it and the
+ result will be used as the value. As a special exception, if the given type string is a definite type, then
+ <link linkend='NULL--CAPS'><literal>NULL</literal></link> may be given to mean an empty array of that type.
+ </para>
+
+ <para>
+ Upon encountering an '<literal>a</literal>' character followed by a type string,
+ <link linkend='g-variant-get'><function>g_variant_get()</function></link> will take a pointer to a
+ <link linkend='GVariantIter'><type>GVariantIter</type></link> (ie:
+ <code>(<link linkend='GVariantIter'>GVariantIter</link> *)</code>). The iter (which is assumed to be completely
+ uninitialised) is initialised for iterating over the elements of the array.
+ <link linkend='NULL--CAPS'><literal>NULL</literal></link> may also be given to indicate that the value of the array
+ should be ignored.
+ </para>
+
+ <refsect3>
+ <title>Examples</title>
+ <informalexample><programlisting>
+<![CDATA[GVariantBuilder *builder;
+GVariant *value;
+
+builder = g_variant_builder_new (G_VARIANT_TYPE_CLASS_ARRAY, NULL);
+g_variant_builder_add (builder, "s", "when");
+g_variant_builder_add (builder, "s", "in");
+g_variant_builder_add (builder, "s", "the");
+g_variant_builder_add (builder, "s", "course");
+value = g_variant_new ("as", builder);
+
+{
+ GVariantIter iter;
+ gchar *str;
+
+ g_variant_get (value, "as", &iter);
+ while (g_variant_iter_next (&iter, "s", &str))
+ g_print ("%s\n");
+}]]></programlisting></informalexample>
+ </refsect3>
+ </refsect2>
+
+ <refsect2 id='gvariant-format-strings-maybe-types'>
+ <title>Maybe Types</title>
+ <para>
+ <emphasis role='strong'>
+ Characters: <literal>m</literal>
+ </emphasis>
+ </para>
+ <para>
+ Maybe types are handled in two separate ways depending on the format string that follows the
+ '<literal>m</literal>'. The method that is used currently depends entirely on the character immediately following the
+ '<literal>m</literal>'.
+ </para>
+
+ <para>
+ The first way is used with format strings starting with '<literal>s</literal>', '<literal>o</literal>',
+ '<literal>g</literal>', '<literal>v</literal>', '<literal>@</literal>', '<literal>*</literal>',
+ '<literal>?</literal>', '<literal>r</literal>', '<literal>&</literal>', or '<literal>^</literal>'. In all of
+ these cases, for non-maybe types, <link linkend='g-variant-new'><function>g_variant_new()</function></link> takes
+ a pointer to a non-<link linkend='NULL--CAPS'><literal>NULL</literal></link> value and
+ <link linkend='g-variant-get'><function>g_variant_get()</function></link> returns (by reference) a
+ non-<link linkend='NULL--CAPS'><literal>NULL</literal></link> pointer. When any of these format strings are
+ prefixed with an '<literal>m</literal>', the type of arguments that are collected does not change in any way, but
+ <link linkend='NULL--CAPS'><literal>NULL</literal></link> becomes a permissable value, to indicate the Nothing case.
+ </para>
+ <para>
+ The second way is used with all other format strings. For
+ <link linkend='g-variant-new'><function>g_variant_new()</function></link> an additional
+ <link linkend='gboolean'><type>gboolean</type></link> argument is collected and for
+ <link linkend='g-variant-get'><function>g_variant_get()</function></link> an additional
+ <code>(<link linkend='gboolean'>gboolean</link> *)</code>. Following this argument, the arguments that are normally
+ collected for the equivalent non-maybe type will be collected.
+ </para>
+ <para>
+ If <link linkend='FALSE--CAPS'><literal>FALSE</literal></link> is given to
+ <link linkend='g-variant-new'><function>g_variant_new()</function></link> then the Nothing value is constructed and
+ the collected arguments are ignored. Otherwise (if <link linkend='TRUE--CAPS'><literal>TRUE</literal></link> was
+ given), the arguments are used in the normal way to create the Just value.
+ </para>
+ <para>
+ If <link linkend='NULL--CAPS'><literal>NULL</literal></link> is given to
+ <link linkend='g-variant-get'><function>g_variant_get()</function></link> then the value is ignored. If a
+ non-<link linkend='NULL--CAPS'><literal>NULL</literal></link> pointer is given then it is used to return by reference
+ whether the value was Just. In the case that the value was Just, the
+ <link linkend='gboolean'><type>gboolean</type></link> will be set to
+ <link linkend='TRUE--CAPS'><literal>TRUE</literal></link> and the value will be stored in the arguments in the usual
+ way. In the case that the value was Nothing, the <link linkend='gboolean'><type>gboolean</type></link> will be set to
+ <link linkend='FALSE--CAPS'><literal>FALSE</literal></link> and the arguments will be collected in the normal way
+ but have their values set to binary zero.
+ </para>
+
+ <refsect3>
+ <title>Examples</title>
+ <informalexample><programlisting>
+<![CDATA[GVariant *value1, *value2, *value3, *value4, *value5, *value6;
+value1 = g_variant_new ("ms", "Hello world");
+value2 = g_variant_new ("ms", NULL);
+value3 = g_variant_new ("(m(ii)s)", TRUE, 123, 456, "Done");
+value4 = g_variant_new ("(m(ii)s)", FALSE, -1, -1, "Done"); /* both '-1' are ignored. */
+value5 = g_variant_new ("(m@(ii)s)", NULL, "Done");
+
+{
+ GVariant *contents;
+ const gchar *cstr;
+ gboolean just;
+ gint32 x, y;
+ gchar *str;
+
+ g_variant_get (value1, "ms", &str);
+ if (str != NULL)
+ g_print ("str: %s\n", str);
+ else
+ g_print ("it was null\n");
+ g_free (str);
+
+
+ g_variant_get (value2, "m&s", &cstr);
+ if (cstr != NULL)
+ g_print ("str: %s\n", cstr);
+ else
+ g_print ("it was null\n");
+ /* don't free 'cstr' */
+
+
+ /* NULL passed for the gboolean *, but two 'gint32 *' still collected */
+ g_variant_get (value3, "(m(ii)s)", NULL, NULL, NULL, &str);
+ g_print ("string is %s\n", str);
+ g_free (str);
+
+ /* note: &s used, so g_free() not needed */
+ g_variant_get (value4, "(m(ii)&s)", &just, &x, &y, &cstr);
+ if (just)
+ g_print ("it was (%d, %d)\n", x, y);
+ else
+ g_print ("it was null\n");
+ g_print ("string is %s\n", cstr);
+ /* don't free 'cstr' */
+
+
+ g_variant_get (value5, "(m*s)", &contents, NULL); /* ignore the string. */
+ if (contents != NULL)
+ {
+ g_variant_get (contents, "(ii)", &x, &y);
+ g_print ("it was (%d, %d)\n", x, y);
+ g_variant_unref (contents);
+ }
+ else
+ g_print ("it was null\n");
+}]]></programlisting></informalexample>
+ </refsect3>
+ </refsect2>
+
+ <refsect2 id='gvariant-format-strings-tuples'>
+ <title>Tuples</title>
+ <para>
+ <emphasis role='strong'>
+ Characters: <code>()</code>
+ </emphasis>
+ </para>
+
+ <para>
+ Tuples are handled by handling each item in the tuple, in sequence. Each item is handled in the usual way.
+ </para>
+
+ <refsect3>
+ <title>Examples</title>
+ <informalexample><programlisting>
+<![CDATA[GVariant *value1, *value2;
+
+value1 = g_variant_new ("(s(ii))", "Hello", 55, 77);
+value2 = g_variant_new ("()");
+
+{
+ gchar *string;
+ gint x, y;
+
+ g_variant_get (value1, "(s(ii))", &string, &x, &y);
+ g_print ("%s, %d, %d\n", string, x, y);
+ g_free (string);
+
+ g_variant_get (value2, "()"); /* do nothing... */
+}]]></programlisting></informalexample>
+ </refsect3>
+ </refsect2>
+
+ <refsect2 id='gvariant-format-strings-dictionaries'>
+ <title>Dictionaries</title>
+ <para>
+ <emphasis role='strong'>
+ Characters: <code>{}</code>
+ </emphasis>
+ </para>
+
+ <para>
+ Dictionary entries are handled by handling first the key, then the value. Each is handled in the usual way.
+ </para>
+
+ <refsect3>
+ <title>Examples</title>
+ <informalexample><programlisting>
+<![CDATA[GVariantBuilder *b;
+GVariant *dict;
+
+b = g_variant_builder_new (G_VARIANT_TYPE_CLASS_ARRAY, G_VARIANT_TYPE ("a{sv}"));
+g_variant_builder_add (b, "{sv}", "name", g_variant_new_string ("foo"));
+g_variant_builder_add (b, "{sv}", "timeout", g_variant_new_int32 (10));
+dict = g_variant_builder_end (b);]]></programlisting></informalexample>
+ </refsect3>
+ </refsect2>
+
+ <refsect2 id='gvariant-format-strings-gvariant'>
+ <title>GVariant *</title>
+ <para>
+ <emphasis role='strong'>
+ Characters: <literal>@</literal>, <literal>*</literal>, <literal>?</literal>, <literal>r</literal>
+ </emphasis>
+
+ </para>
+ <para>
+ Upon encountering a '<literal>@</literal>' in front of a type string,
+ <link linkend='g-variant-new'><function>g_variant_new()</function></link> takes a
+ non-<link linkend='NULL--CAPS'><literal>NULL</literal></link> pointer to a
+ <link linkend='GVariant'><type>GVariant</type></link> and uses its value directly instead of collecting arguments to
+ create the value. The provided <link linkend='GVariant'><type>GVariant</type></link> must have a type that matches the
+ type string following the '<literal>@</literal>'. '<literal>*</literal>' is
+ the same as '<literal>@*</literal>' (ie: take a <link linkend='GVariant'><type>GVariant</type></link> of any type).
+ '<literal>?</literal>' is the same as '<literal>@?</literal>' (ie: take a
+ <link linkend='GVariant'><type>GVariant</type></link> of any basic type). '<literal>r</literal>' is the same as
+ '<literal>@r</literal>' (ie: take a <link linkend='GVariant'><type>GVariant</type></link> of any tuple type).
+ </para>
+ <para>
+ Upon encountering a '<literal>@</literal>' in front of a type string,
+ <link linkend='g-variant-get'><function>g_variant_get()</function></link>
+ takes a pointer to a <code>(<link linkend='GVariant'>GVariant</link> *)</code> (ie: a
+ <code>(<link linkend='GVariant'>GVariant</link> **)</code>) and sets it to a new reference to a
+ <link linkend='GVariant'><type>GVariant</type></link> containing the value (instead of deconstructing the value into
+ C types in the usual way). <link linkend='NULL--CAPS'><literal>NULL</literal></link> can be given to ignore the
+ value. '<literal>*</literal>', '<literal>?</literal>' and '<literal>r</literal>' are handled in a way analogous to
+ what is stated above.
+ </para>
+ <para>
+ You can always use '<literal>*</literal>' as an alternative to '<literal>?</literal>', '<literal>r</literal>' or any
+ use of '<literal>@</literal>'. Using the other characters where possible is recommended, however, due to the
+ improvements in type safety and code self-documentation.
+ </para>
+
+ <refsect3>
+ <title>Examples</title>
+ <informalexample><programlisting>
+<![CDATA[GVariant *value1, *value2;
+
+value1 = g_variant_new ("(i ii)", 44, g_variant_new_int32 (55), 66);
+
+/* note: consumes floating reference count on 'value1' */
+value2 = g_variant_new ("(@(iii)*)", value1, g_variant_new_string ("foo"));
+
+{
+ const gchar *string;
+ GVariant *tmp;
+ gsize length;
+ gint x, y, z;
+
+ g_variant_get (value2, "((iii)*)", &x, &y, &z, &tmp);
+ string = g_variant_get_string (tmp, &length);
+ g_print ("it is %d %d %d %s (length=%d)\n", x, y, z, string, (int) length);
+ g_variant_unref (tmp);
+
+ /* quick way to skip all the values in a tuple */
+ g_variant_get (value2, "(rs)", NULL, &string); /* or "(@(iii)s)" */
+ g_print ("i only got the string: %s\n", string);
+ g_free (string);
+}]]></programlisting></informalexample>
+ </refsect3>
+ </refsect2>
+
+ <refsect2 id='gvariant-format-strings-pointers'>
+ <title>Pointers</title>
+ <para>
+ <emphasis role='strong'>
+ Characters: <code>&</code>
+ </emphasis>
+ </para>
+
+ <para>
+ The '<code>&</code>' character is used to indicate that serialised data should be directly exchanged via a
+ pointer.
+ </para>
+ <para>
+ Currently there is only one use for this character -- to avoid making a copy of a string when using
+ <link linkend='g-variant-get'><function>g_variant_get()</function></link>.
+ </para>
+ <para>
+ The three cases are as follows:
+ </para>
+ <para>
+ Currently, the only use for this character is when it is applied to a string (ie: '<literal>&s</literal>',
+ '<literal>&o</literal>' or '<code>&g</code>'). For
+ <link linkend='g-variant-new'><function>g_variant_new()</function></link> this has absolutely no effect. The string
+ is collected and duplicated normally. For <link linkend='g-variant-get'><function>g_variant_get()</function></link>
+ it means that instead of creating a newly allocated copy of the string, a pointer to the serialised data is
+ returned. This pointer should not be freed. Validity checks are performed to ensure that the string data will
+ always be properly nul-terminated.
+ </para>
+
+ <refsect3>
+ <title>Examples</title>
+ <informalexample><programlisting>
+<![CDATA[{
+ const gchar *str;
+ GVariant *value;
+
+ value = g_variant_new ("&s", "hello world");
+ str = g_variant_get ("&s", &str);
+ g_print ("string is: %s\n", str);
+ /* no need to free str */
+}]]></programlisting></informalexample>
+ </refsect3>
+ </refsect2>
+
+ <refsect2 id='gvariant-format-strings-convenience'>
+ <title>Convenience Conversions</title>
+ <para>
+ <emphasis role='strong'>
+ Characters: <literal>^</literal>
+ </emphasis>
+ </para>
+
+ <para>
+ The '<literal>^</literal>' character currently only has one purpose: to convert to and from
+ <link linkend='G-TYPE-STRV'><literal>G_TYPE_STRV</literal></link> type arrays of strings. It is always used with
+ arrays of strings (or other string types). It has two forms.
+ </para>
+ <itemizedlist>
+ <listitem>
+ <para>
+ '<literal>^as</literal>' (or <literal>o</literal> or <literal>g</literal>)
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ '<literal>^a&s</literal>' (or <literal>o</literal> or <literal>g</literal>)
+ </para>
+ </listitem>
+ </itemizedlist>
+ <para>
+ When used with <link linkend='g-variant-new'><function>g_variant_new()</function></link> both forms are equivalent.
+ A <code>(const <link linkend='gchar'>gchar</link> * const *)</code> is collected. This must be a pointer to the
+ array of <link linkend='NULL--CAPS'><literal>NULL</literal></link>-terminated pointers to strings. This array is
+ converted to a <link linkend='GVariant'><type>GVariant</type></link> instance. Copies are made, so the original
+ array may be freed immediately.
+ </para>
+ <para>
+ When used with <link linkend='g-variant-get'><function>g_variant_get()</function></link> the two forms have
+ different meaning. Both return a freshly allocated
+ <link linkend='NULL--CAPS'><literal>NULL</literal></link>-terminated array of pointers to strings. In the case of
+ '<literal>^as</literal>', the strings are owned by the caller -- it is appropriate to free the array with
+ <link linkend='g-strfreev'><function>g_strfreev()</function></link>. In the case of '<literal>^a&s</literal>',
+ a shallow copy is made; the strings themselves are embedded in the serialised data and owned by the original
+ <link linkend='GVariant'><type>GVariant</type></link> instance -- it is only appropriate to free the outer array
+ with <link linkend='g-free'><function>g_free()</function></link>.
+ </para>
+ </refsect2>
+ </refsect1>
+</refentry>
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]