summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--doc/gdbus-codegen.xml656
-rw-r--r--src/codegen.py4
-rw-r--r--src/codegen_main.py8
-rw-r--r--src/dbustypes.py2
-rw-r--r--src/org.project.xml32
5 files changed, 347 insertions, 355 deletions
diff --git a/doc/gdbus-codegen.xml b/doc/gdbus-codegen.xml
index f9a6435..6406665 100644
--- a/doc/gdbus-codegen.xml
+++ b/doc/gdbus-codegen.xml
@@ -14,13 +14,10 @@
<refsynopsisdiv>
<cmdsynopsis>
<command>gdbus-codegen</command>
- <arg><option>--namespace</option> <replaceable>YourProject</replaceable></arg>
- <arg><option>--output-prefix</option> <replaceable>prefix</replaceable></arg>
- <arg><option>--strip-prefix</option> <replaceable>org.project.Prefix</replaceable></arg>
- <arg><option>--include-dir</option> <replaceable>libsomething</replaceable></arg>
- <group choice="plain" rep="repeat">
- <arg><option>--add-include</option> <replaceable>path/to/file.h</replaceable></arg>
- </group>
+ <arg><option>--interface-prefix</option> <replaceable>org.project.Prefix</replaceable></arg>
+ <arg><option>--c-namespace</option> <replaceable>YourProject</replaceable></arg>
+ <arg><option>--generate-c-code</option> <replaceable>OUTFILES</replaceable></arg>
+ <arg><option>--generate-docbook</option> <replaceable>OUTFILES</replaceable></arg>
<group choice="plain" rep="repeat">
<arg>
<option>--annotate</option>
@@ -31,26 +28,258 @@
<replaceable>key</replaceable>
</arg>
</group>
- <arg choice="plain">file1</arg>
- <arg choice="plain" rep="repeat">file2</arg>
+ <arg choice="plain">FILE</arg>
+ <arg>
+ <arg choice="plain" rep="repeat">FILE</arg>
+ </arg>
</cmdsynopsis>
</refsynopsisdiv>
<refsect1>
<title>Description</title>
<para>
- <command>gdbus-codegen</command> is used to generate C code for
- interacting with and exporting objects using D-Bus. The tool reads
- D-Bus Introspection XML files and generates an abstract
- <type>GInterface</type>-derived type for each D-Bus interface
- encountered. Additionally, for every generated type,
+ <command>gdbus-codegen</command> is used to generate code and/or
+ documentation for one or more D-Bus interfaces. The tool reads
+ D-Bus Introspection XML files and generates output files. The tool
+ currently supports generating C code (via
+ <option>--generate-c-code</option>) and Docbook XML (via
+ <option>--generate-docbook</option>).
+ </para>
+ <para>
+ When generating C code, an abstract
+ <type>GInterface</type>-derived type is generated for each D-Bus
+ interface. Additionally, for every generated type,
<type>FooBar</type>, two concrete instantiable types,
<type>FooBarProxy</type> and <type>FooBarStub</type>, implementing
- the interface are also generated. The former is derived from
+ said interface are also generated. The former is derived from
<type>GDBusProxy</type> and intended for use on the client side
- while the latter implements the <type>GDBusInterface</type>
- interface making it easy to export on a
- <type>GDBusConnection</type>.
+ while the latter is derived from the
+ <type>GDBusInterfaceStub</type> type making it easy to export on a
+ <type>GDBusConnection</type> either directly or via a
+ <type>GDBusObjectManagerServer</type>.
+ </para>
+</refsect1>
+
+<refsect1>
+ <title>Options</title>
+ <para>
+ The following options are supported:
+ </para>
+ <variablelist>
+
+ <varlistentry>
+ <term><option>--interface-prefix</option> <replaceable>org.project.Prefix.</replaceable></term>
+ <listitem>
+ <para>
+ A prefix to strip from all D-Bus interface names when
+ calculating the typename for the C binding and the Docbook
+ <ulink
+ url="http://www.docbook.org/tdg/en/html/primary.html">sortas
+ attribute</ulink>.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><option>--generate-docbook</option> <replaceable>OUTFILES</replaceable></term>
+ <listitem>
+ <para>
+ Generate Docbook Documentation for each D-Bus interface and
+ put it in
+ <filename>OUTFILES-org.Project.IfaceName.xml</filename> (where
+ <literal>org.Project.IfaceName</literal> is a place-holder for
+ the interface name).
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><option>--generate-c-code</option> <replaceable>OUTFILES</replaceable></term>
+ <listitem>
+ <para>
+ Generate C code for all D-Bus interfaces and put it in
+ <filename>OUTFILES.c</filename> and
+ <filename>OUTFILES.h</filename>.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><option>--c-namespace</option> <replaceable>YourProject</replaceable></term>
+ <listitem>
+ <para>
+ The namespace to use for generated C code. This must be
+ provided in CamelCase format.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><option>--annotate</option></term>
+ <listitem>
+ <para>
+ Used together with <option>--key</option> and
+ <option>--value</option> to annotate the given XML files. It
+ can be used with interfaces, methods, signals, properties
+ and arguments in the following way:
+ </para>
+<informalexample><programlisting><![CDATA[
+gdbus-codegen --c-namespace MyApp \
+ --generate-c-code myapp-generated \
+ --annotate "org.project.InterfaceName" \
+ --key org.gtk.GDBus.Name --value MyFrobnicator \
+ --annotate "org.project.InterfaceName:Property" \
+ --key bar --value bat \
+ --annotate "org.project.InterfaceName.Method()" \
+ --key org.freedesktop.DBus.Deprecated --value true \
+ --annotate "org.project.InterfaceName.Method()[arg_name]" \
+ --key snake --value hiss \
+ --annotate "org.project.InterfaceName::Signal" \
+ --key cat --value meow \
+ --annotate "org.project.InterfaceName::Signal[arg_name]" \
+ --key dog --value wuff \
+ myapp-dbus-interfaces.xml
+]]></programlisting></informalexample>
+ </listitem>
+ </varlistentry>
+ </variablelist>
+</refsect1>
+
+<refsect1>
+ <title>Supported D-Bus Annotations</title>
+ <para>
+ The following D-Bus annotations are supported by
+ <command>gdbus-codegen</command>:
+ </para>
+
+ <variablelist>
+
+ <varlistentry>
+ <term><literal>org.gtk.GDBus.Name</literal></term>
+ <listitem>
+ <para>
+ Can be used on any <literal>&lt;interface&gt;</literal>,
+ <literal>&lt;method&gt;</literal>,
+ <literal>&lt;signal&gt;</literal> and
+ <literal>&lt;property&gt;</literal> element to specify the
+ name to use.
+ </para>
+ <para>
+ For interfaces where this annotation is not specified, the
+ name used is the D-Bus interface name stripped with the
+ prefix given with <option>--interface-prefix</option> and with
+ the dots removed and initial characters capitalized. For
+ example the D-Bus interface
+ <literal>com.acme.Coyote</literal> the name used is
+ <type>ComAcmeCoyote</type>. For the D-Bus interface
+ <literal>org.project.Bar.Frobnicator</literal> with
+ <option>--interface-prefix</option>
+ <literal>org.project.</literal>, the name used is
+ <type>BarFrobnicator</type>.
+ </para>
+ <para>
+ For methods, signals and properties the name used is
+ calculated by transforming
+ <literal>NameGivenThisWay</literal> into
+ <literal>name_given_this_way</literal>, e.g. roughly
+ converting from camel-case to lower-case with underscores
+ using certain heuristics.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><literal>org.gtk.GDBus.C.ForceGVariant</literal></term>
+ <listitem>
+ <para>
+ If set to a non-empty string, a <type>GVariant</type> will
+ be used instead of the natural C type. This annotation can
+ be used on any <literal>&lt;arg&gt;</literal> and
+ <literal>&lt;property&gt;</literal> element.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><literal>org.gtk.GDBus.DocString</literal></term>
+ <listitem>
+ <para>
+ A string with Docbook content for documentation. This annotation can
+ be used on <literal>&lt;interface&gt;</literal>,
+ <literal>&lt;method&gt;</literal>,
+ <literal>&lt;signal&gt;</literal>,
+ <literal>&lt;property&gt;</literal> and
+ <literal>&lt;arg&gt;</literal> elements.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><literal>org.gtk.GDBus.DocString.Short</literal></term>
+ <listitem>
+ <para>
+ A string with Docbook content for short/brief
+ documentation. This annotation can only be used on
+ <literal>&lt;interface&gt;</literal> elements.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ </variablelist>
+
+ <para>
+ As an easier alternative to using the
+ <literal>org.gtk.GDBus.DocString</literal> annotation, note that
+ XML parser used by <command>gdbus-codegen</command> parses XML
+ comments in a way similar to <ulink
+ url="http://www.gtk.org/gtk-doc/">gtk-doc</ulink>:
+<informalexample><programlisting><![CDATA[
+<!--
+ net.Corp.Bar:
+ @short_description: A short description
+
+ A <emphasis>longer</emphasis> description.
+
+ This is a new paragraph.
+-->
+<interface name="net.corp.Bar">
+ <!--
+ FooMethod:
+ @greeting: The docs for greeting parameter.
+ @response: The docs for response parameter.
+
+ The docs for the actual method.
+ -->
+ <method name="FooMethod">
+ <arg name="greeting" direction="in" type="s"/>
+ <arg name="response" direction="out" type="s"/>
+ </method>
+
+ <!--
+ BarSignal:
+ @blah: The docs for blah parameter.
+ @boo: The docs for boo parameter.
+
+ The docs for the actual signal.
+ -->
+ <signal name="BarSignal">
+ <arg name="blah" type="s"/>
+ <arg name="boo" type="s"/>
+ </signal>
+
+ <!-- BazProperty: The docs for the property. -->
+ <property name="BazProperty" type="s" access="read"/>
+</interface>
+]]></programlisting></informalexample>
+ </para>
+ <para>
+ For the <literal>org.gtk.GDBus.DocString</literal> annotation (and
+ inline comments), note that substrings of the form
+ <literal>#net.Corp.Bar</literal>,
+ <literal>net.Corp.Bar.FooMethod()</literal>,
+ <literal>#net.Corp.Bar::BarSignal</literal> and
+ <literal>#net.Corp.InlineDocs:BazProperty</literal> are all expanded
+ to links to the respective interface, method, signal and property.
</para>
</refsect1>
@@ -60,7 +289,7 @@
Consider the following D-Bus Introspection XML.
</para>
<informalexample><programlisting><![CDATA[
-<interface name="org.gtk.GDBus.Example">
+<interface name="net.Corp.MyApp.Frobber">
<method name="HelloWorld">
<arg name="greeting" direction="in" type="s"/>
<arg name="response" direction="out" type="s"/>
@@ -80,89 +309,95 @@
If <command>gdbus-codegen</command> is used on this file like this:
</para>
<informalexample><programlisting><![CDATA[
-gdbus-codegen --namespace=MyApp \
- --strip-prefix=org.gtk.GDBus. \
- org.gtk.GDBus.Example.xml
+gdbus-codegen --generate-c-code myapp-generated \
+ --c-namespace MyApp \
+ --interface-prefix net.corp.MyApp. \
+ net.Corp.MyApp.Frobber.xml
]]></programlisting></informalexample>
<para>
two files called
- <filename>generated-myappexample.[ch]</filename> are
+ <filename>myapp-generated.[ch]</filename> are
generated. The files provide an abstract
<type>GInterface</type>-derived type called
- <type>MyAppExample</type> as well as two instantiable types with
+ <type>MyAppFrobber</type> as well as two instantiable types with
the same name but suffixed with <type>Proxy</type> and
<type>Stub</type>. The generated file, roughly, contains the
following facilities:
</para>
<informalexample><programlisting><![CDATA[
/* GType macros for the three generated types */
-#define MY_APP_TYPE_EXAMPLE (my_app_example_get_type ())
-#define MY_APP_TYPE_EXAMPLE_STUB (my_app_example_stub_get_type ())
-#define MY_APP_TYPE_EXAMPLE_PROXY (my_app_example_proxy_get_type ())
+#define MY_APP_TYPE_FROBBER (my_app_frobber_get_type ())
+#define MY_APP_TYPE_FROBBER_STUB (my_app_frobber_stub_get_type ())
+#define MY_APP_TYPE_FROBBER_PROXY (my_app_frobber_proxy_get_type ())
-typedef struct _MyAppExample MyAppExample; /* Dummy typedef */
+typedef struct _MyAppFrobber MyAppFrobber; /* Dummy typedef */
typedef struct
{
GTypeInterface parent_iface;
/* Signal handler for the ::notification signal */
- void (*notification) (MyAppExample *proxy,
+ void (*notification) (MyAppFrobber *proxy,
GVariant *icon_blob,
gint height,
const gchar* const *messages);
/* Signal handler for the ::handle-hello-world signal */
- gboolean (*handle_hello_world) (MyAppExample *proxy,
+ gboolean (*handle_hello_world) (MyAppFrobber *proxy,
GDBusMethodInvocation *invocation,
const gchar *greeting);
-} MyAppExampleIface;
+} MyAppFrobberIface;
/* Asynchronously calls HelloWorld() */
-void my_app_example_call_hello_world (MyAppExample *proxy,
- const gchar *greeting,
- GCancellable *cancellable,
- GAsyncReadyCallback callback,
- gpointer user_data);
-void my_app_example_call_hello_world_finish (MyAppExample *proxy,
- gchar **out_response,
- GAsyncResult *res,
- GError **error);
+void
+my_app_frobber_call_hello_world (MyAppFrobber *proxy,
+ const gchar *greeting,
+ GCancellable *cancellable,
+ GAsyncReadyCallback callback,
+ gpointer user_data);
+gboolean
+my_app_frobber_call_hello_world_finish (MyAppFrobber *proxy,
+ gchar **out_response,
+ GAsyncResult *res,
+ GError **error);
/* Synchronously calls HelloWorld(). Blocks calling thread. */
-void my_app_example_call_hello_world_sync (MyAppExample *proxy,
- const gchar *greeting,
- gchar **out_response,
- GCancellable *cancellable,
- GError **error);
+gboolean
+my_app_frobber_call_hello_world_sync (MyAppFrobber *proxy,
+ const gchar *greeting,
+ gchar **out_response,
+ GCancellable *cancellable,
+ GError **error);
/* Completes handling the HelloWorld() method call */
-void my_app_example_complete_hello_world (MyAppExample *object,
- GDBusMethodInvocation *invocation,
- const gchar *response);
+void
+my_app_frobber_complete_hello_world (MyAppFrobber *object,
+ GDBusMethodInvocation *invocation,
+ const gchar *response);
/* Emits the ::notification signal / Notification() D-Bus signal */
-void my_app_example_emit_notification (MyAppExample *object,
- GVariant *icon_blob,
- gint height,
- const gchar* const *messages);
+void
+my_app_frobber_emit_notification (MyAppFrobber *object,
+ GVariant *icon_blob,
+ gint height,
+ const gchar* const *messages);
/* Gets the :verbose GObject property / Verbose D-Bus property.
* Does no blocking I/O.
*/
-gboolean my_app_example_get_verbose (MyAppExample *object);
+gboolean my_app_frobber_get_verbose (MyAppFrobber *object);
/* Sets the :verbose GObject property / Verbose D-Bus property.
* Does no blocking I/O.
*/
-void my_app_example_set_verbose (MyAppExample *object,
+void my_app_frobber_set_verbose (MyAppFrobber *object,
gboolean value);
/* Gets the interface info */
-const GDBusInterfaceInfo *my_app_example_interface_info (void);
+GDBusInterfaceInfo *my_app_frobber_interface_info (void);
/* Creates a new stub object, ready to be exported */
-MyAppExample *my_app_example_stub_new (void);
+MyAppFrobber *my_app_frobber_stub_new (void);
/* Client-side proxy constructors.
*
@@ -170,18 +405,18 @@ MyAppExample *my_app_example_stub_new (void);
* _new_for_bus_sync() proxy constructors are also generated.
*/
void
-my_app_example_proxy_new (GDBusConnection *connection,
+my_app_frobber_proxy_new (GDBusConnection *connection,
GDBusProxyFlags flags,
const gchar *name,
const gchar *object_path,
GCancellable *cancellable,
GAsyncReadyCallback callback,
gpointer user_data);
-MyAppExample *
-my_app_example_proxy_new_finish (GAsyncResult *res,
+MyAppFrobber *
+my_app_frobber_proxy_new_finish (GAsyncResult *res,
GError **error);
-MyAppExample *
-my_app_example_proxy_new_sync (GDBusConnection *connection,
+MyAppFrobber *
+my_app_frobber_proxy_new_sync (GDBusConnection *connection,
GDBusProxyFlags flags,
const gchar *name,
const gchar *object_path,
@@ -210,37 +445,32 @@ my_app_example_proxy_new_sync (GDBusConnection *connection,
<tbody>
<row>
<entry>Types</entry>
- <entry>Use <type>MyAppExampleProxy</type></entry>
- <entry>Any type implementing the <type>MyAppExample</type> interface</entry>
+ <entry>Use <type>MyAppFrobberProxy</type></entry>
+ <entry>Any type implementing the <type>MyAppFrobber</type> interface</entry>
</row>
<row>
<entry>Methods</entry>
- <entry>Use <function>m_a_e_hello_world()</function> to call.</entry>
- <entry>Receive via the <function>handle_hello_world()</function> signal handler. Complete the call with <function>m_a_e_complete_hello_world()</function></entry>
+ <entry>Use <function>m_a_f_hello_world()</function> to call.</entry>
+ <entry>Receive via the <function>handle_hello_world()</function> signal handler. Complete the call with <function>m_a_f_complete_hello_world()</function></entry>
</row>
<row>
<entry>Signals</entry>
<entry>Connect to the <function>::notification</function> GObject signal.</entry>
- <entry>Use <function>m_a_e_emit_notification()</function> to emit signal.</entry>
+ <entry>Use <function>m_a_f_emit_notification()</function> to emit signal.</entry>
</row>
<row>
<entry>Properties (Reading)</entry>
- <entry>Use <function>m_a_e_get_verbose()</function> or <parameter>:verbose</parameter>.</entry>
+ <entry>Use <function>m_a_f_get_verbose()</function> or <parameter>:verbose</parameter>.</entry>
<entry>Implement <type>GObject</type>'s <function>get_property()</function> vfunc.</entry>
</row>
<row>
<entry>Properties (writing)</entry>
- <entry>Use <function>m_a_e_set_verbose()</function> or <parameter>:verbose</parameter>.</entry>
+ <entry>Use <function>m_a_f_set_verbose()</function> or <parameter>:verbose</parameter>.</entry>
<entry>Implement <type>GObject</type>'s <function>set_property()</function> vfunc.</entry>
</row>
</tbody>
</tgroup>
</informaltable>
- <para>
- Note that the generated API has 100% <ulink
- url="http://www.gtk.org/gtk-doc/">GTK-Doc</ulink> coverage so if
- in doubt just look at the generated sources.
- </para>
<refsect2>
<title>Client-side usage</title>
@@ -249,16 +479,16 @@ my_app_example_proxy_new_sync (GDBusConnection *connection,
constructors:
</para>
<informalexample><programlisting><![CDATA[
- MyAppExample *proxy;
+ MyAppFrobber *proxy;
GError *error;
error = NULL;
- proxy = my_app_example_proxy_new_for_bus_sync (
+ proxy = my_app_frobber_proxy_new_for_bus_sync (
G_BUS_TYPE_SESSION,
G_DBUS_PROXY_FLAGS_NONE,
- "org.my.project.SomeService",
- "/org/my/project/SomeObject",
- NULL, /* GCancellable* */
+ "net.Corp.MyApp", /* bus name */
+ "/net/Corp/MyApp/SomeFrobber", /* object */
+ NULL, /* GCancellable* */
&error);
/* do stuff with proxy */
g_object_unref (proxy);
@@ -266,13 +496,13 @@ my_app_example_proxy_new_sync (GDBusConnection *connection,
<para>
Instead of using the generic <type>GDBusProxy</type> facilities,
one can use the generated methods such as
- <function>my_app_example_call_hello_world()</function> to invoke
- the <function>org.gtk.GDBus.Example.HelloWorld()</function>
+ <function>my_app_frobber_call_hello_world()</function> to invoke
+ the <function>net.Corp.MyApp.Frobber.HelloWorld()</function>
D-Bus method, connect to the the
<function>::notification</function> GObject signal to receive
- the <function>org.gtk.GDBus.Example::Notication</function> D-Bus
+ the <function>net.Corp.MyApp.Frobber::Notication</function> D-Bus
signal and get/set the
- <parameter>org.gtk.GDBus.Example:Verbose</parameter> D-Bus
+ <parameter>net.Corp.MyApp.Frobber:Verbose</parameter> D-Bus
Property using either the GObject property
<parameter>:verbose</parameter> or the
<function>my_app_get_verbose()</function> and
@@ -294,13 +524,13 @@ my_app_example_proxy_new_sync (GDBusConnection *connection,
<refsect2>
<title>Server-side usage</title>
<para>
- The generated <type>MyAppExample</type> interface is designed so
+ The generated <type>MyAppFrobber</type> interface is designed so
it is easy to implement it in a <type>GObject</type>
subclass. For example, to handle
<function>HelloWorld()</function> method invocations, set the
vfunc for <function>handle_hello_hello_world()</function> in the
- <type>MyAppExampleIface</type> structure. Similary, to handle
- the <parameter>org.gtk.GDBus.Example:Verbose</parameter>
+ <type>MyAppFrobberIface</type> structure. Similary, to handle
+ the <parameter>net.Corp.MyApp.Frobber:Verbose</parameter>
property override the <parameter>:verbose</parameter> GObject
property from the subclass. To emit a signal, use
e.g. <function>my_app_emit_signal()</function> or
@@ -308,7 +538,7 @@ my_app_example_proxy_new_sync (GDBusConnection *connection,
</para>
<para>
Instead of subclassing, it is often easier to use the generated
- <type>MyAppExampleStub</type> subclass. To handle incoming
+ <type>MyAppFrobberStub</type> subclass. To handle incoming
method calls, use <function>g_signal_connect()</function> with
the <function>::handle-*</function> signals and instead of
overriding <type>GObject</type>'s
@@ -321,7 +551,7 @@ my_app_example_proxy_new_sync (GDBusConnection *connection,
</para>
<informalexample><programlisting><![CDATA[
static gboolean
-on_handle_hello_world (MyAppExample *object,
+on_handle_hello_world (MyAppFrobber *object,
GDBusMethodInvocation *invocation,
const gchar *greeting,
gpointer user_data)
@@ -345,8 +575,8 @@ on_handle_hello_world (MyAppExample *object,
[...]
- object = my_app_example_stub_new ();
- my_app_example_set_verbose (object, TRUE);
+ object = my_app_frobber_stub_new ();
+ my_app_frobber_set_verbose (object, TRUE);
g_signal_connect (object,
"handle-hello-world",
@@ -368,14 +598,14 @@ on_handle_hello_world (MyAppExample *object,
and will cause emissions of the
<function>org.freedesktop.DBus.Properties::PropertiesChanged</function>
signal with all the properties that has changed. Use
- <function>g_dbus_interface_flush()</function> to empty the queue
- immediately.
+ <function>g_dbus_interface_stub_flush()</function> to empty the
+ queue immediately.
</para>
</refsect2>
</refsect1>
<refsect1>
- <title>Type mapping</title>
+ <title>C Type Mapping</title>
<para>
Scalar types, strings (including object paths (type-string
<literal>o</literal>), signatures (type-string
@@ -390,250 +620,12 @@ on_handle_hello_world (MyAppExample *object,
</para>
<para>
This automatic mapping can be turned off by using the annotation
- <literal>org.gtk.GDBus.UseGVariant</literal> - if used then a
+ <literal>org.gtk.GDBus.C.ForceGVariant</literal> - if used then a
<type>GVariant</type> is always exchanged instead of the
corresponding native C type. This annotation may be convenient to
use when using the type-string <literal>ay</literal> for data with
- embedded NULs.
- </para>
- <para>
- It is also possible to specify that a boxed or object type should
- be used instead of <type>GVariant</type>. It is best described by
- example. Consider the following D-Bus interface:
- </para>
- <informalexample><programlisting><![CDATA[
- <method name="SomeMethod">
- <arg name="clip_area" direction="in" type="(iiii)">
- <annotation name="org.gtk.GDBus.BoxedType" value="FOO_TYPE_RECT"/>
- </arg>
- </method>
-]]></programlisting>
- </informalexample>
- <para>
- The <literal>org.gtk.GDBus.BoxedType</literal> annotation specify
- that the type <type>FOO_TYPE_RECT</type> should be used for the
- <parameter>clip_area</parameter> parameter instead of a
- <type>GVariant</type>. It is not sufficient, however, to just
- specify the type, you normally have to also use the
- <option>--add-include</option> option to specify where to find the
- types and functions needed, e.g.:
- </para>
- <informalexample><programlisting><![CDATA[
-typedef struct _FooRect FooRect;
-
-struct _FooRect
-{
- gint x;
- gint y;
- gint width;
- gint height
-};
-
-#define FOO_TYPE_RECT (foo_type_get_type ())
-GType foo_type_get_type (void) G_GNUC_CONST;
-FooRect *foo_rect_from_gvariant (GVariant *value);
-GVariant *foo_rect_to_gvariant (FooRect *rect);
-]]></programlisting>
- </informalexample>
-</refsect1>
-
-<refsect1>
- <title>D-Bus Annotations</title>
- <para>
- The following annotations are supported by
- <command>gdbus-codegen</command>:
+ embedded NUL bytes.
</para>
-
- <variablelist>
-
- <varlistentry>
- <term><literal>org.gtk.GDBus.Name</literal></term>
- <listitem>
- <para>
- Can be used on any <literal>&lt;interface&gt;</literal>,
- <literal>&lt;method&gt;</literal>,
- <literal>&lt;signal&gt;</literal> and
- <literal>&lt;property&gt;</literal> element to specify the
- name to use.
- </para>
- <para>
- For interfaces where this annotation is not specified, the
- name used is the D-Bus interface name stripped with the
- prefix given with <option>--strip-prefix</option> and with
- the dots removed and initial characters capitalized. For
- example the D-Bus interface
- <literal>com.acme.Coyote</literal> the name used is
- <type>ComAcmeCoyote</type>. For the D-Bus interface
- <literal>org.project.Bar.Frobnicator</literal> with
- <option>--strip-prefix</option>
- <literal>org.project.</literal>, the name used is
- <type>BarFrobnicator</type>.
- </para>
- <para>
- For methods, signals and properties the name used is
- calculated by transforming
- <literal>NameGivenThisWay</literal> into
- <literal>name_given_this_way</literal>, e.g. roughly
- converting from camel-case to lower-case with underscores
- using certain heuristics.
- </para>
- </listitem>
- </varlistentry>
-
- <varlistentry>
- <term><literal>org.gtk.GDBus.UseGVariant</literal></term>
- <listitem>
- <para>
- If set to a non-empty string, a <type>GVariant</type> will
- be used instead of the natural C type. This annotation can
- be used on any <literal>&lt;arg&gt;</literal> and
- <literal>&lt;property&gt;</literal> element.
- </para>
- </listitem>
- </varlistentry>
-
- <varlistentry>
- <term><literal>org.gtk.GDBus.BoxedType</literal>, <literal>org.gtk.GDBus.ObjectType</literal></term>
- <listitem>
- <para>
- Can be used on any <literal>&lt;arg&gt;</literal> and
- <literal>&lt;property&gt;</literal> element to specify that
- the given boxed or <type>GObject</type>-derived type should
- be used instead of a <type>GVariant</type>. The type name
- should be given in form of an upper-case macro name,
- e.g. <literal>MY_TEST_TYPE_POINT</literal> that is used to
- resolve the <type>GType</type>.
- </para>
- <para>
- The C type to use in generated code is derived from this
- name by removing the word <literal>TYPE</literal>, stripping
- the underscores and then CamelCasing the result. For
- example, for <literal>MY_TEST_TYPE_POINT</literal> the
- resulting C type will be <literal>MyTestPoint</literal>.
- </para>
- <para>
- Similarly, the function names to transform type instances
- from/to <type>GVariant</type> instances are derived from the
- value of this annotation by removing the word
- <literal>TYPE</literal>, lower-casing and then adding the
- <literal>_to_gvariant()</literal> and
- <literal>_from_gvariant()</literal> suffixes. The expected
- function signature are as follows:
- </para>
-<informalexample><programlisting><![CDATA[
-GVariant *my_test_point_to_gvariant (MyTestPoint *instance);
-MyTestPoint *my_test_point_from_gvariant (GVariant *value);
-]]></programlisting></informalexample>
- <para>
- Note that you normally need to use the
- <option>--add-include</option> option to specify files to
- include so the necessary types and symbols are available
- while compiling the generated code.
- </para>
- </listitem>
- </varlistentry>
-
- </variablelist>
-
-</refsect1>
-
-<refsect1>
- <title>Options</title>
- <para>
- The following options are supported:
- </para>
- <variablelist>
-
- <varlistentry>
- <term><option>--namespace</option></term>
- <listitem>
- <para>
- The namespace to use for generated code. In CamelCase
- format.
- </para>
- </listitem>
- </varlistentry>
-
- <varlistentry>
- <term><option>--output-prefix</option></term>
- <listitem>
- <para>
- A prefix to use for all generated files. Defaults to
- <filename>generated</filename>.
- </para>
- </listitem>
- </varlistentry>
-
- <varlistentry>
- <term><option>--strip-prefix</option></term>
- <listitem>
- <para>
- A prefix to strip from all D-Bus interface names when
- calculating the typename. Example:
- <literal>org.freedesktop.UDisks.</literal>
- </para>
- </listitem>
- </varlistentry>
-
- <varlistentry>
- <term><option>--include-dir</option> <replaceable>libsomething</replaceable></term>
- <listitem>
- <para>
- If set, all <literal>#include</literal> directives will be
- prefixed with <replaceable>libsomething/</replaceable>. This is
- useful if you want to install the generated header files in
- e.g. <filename>/usr/include/myproject-1.0/libsomething</filename>
- and your
- <citerefentry><refentrytitle>pkg-config</refentrytitle><manvolnum>1</manvolnum></citerefentry>
- file has the include path
- <filename>/usr/include/myproject-1.0</filename>.
- </para>
- </listitem>
- </varlistentry>
-
- <varlistentry>
- <term><option>--add-include</option> <replaceable>path/to/file.h</replaceable></term>
- <listitem>
- <para>
- Includes <replaceable>path/to/file.h</replaceable> in all
- generated header and sources files. Note that the resulting
- <literal>#include</literal> directive is not affected by the
- <option>--include-dir</option> option. This option is
- typically used when using the
- <literal>org.gtk.GDBus.BoxedType</literal> and
- <literal>org.gtk.GDBus.ObjectType</literal> annotations.
- </para>
- </listitem>
- </varlistentry>
-
- <varlistentry>
- <term><option>--annotate</option></term>
- <listitem>
- <para>
- Used together with <option>--key</option> and
- <option>--value</option> to annotate the given XML files. It
- can be used with interfaces, methods, signals, properties
- and arguments in the following way:
- </para>
-<informalexample><programlisting><![CDATA[
-gdbus-codegen --namespace MyApp \
- --annotate "org.project.InterfaceName" \
- --key org.gtk.GDBus.Name --value MyFrobnicator \
- --annotate "org.project.InterfaceName:Property" \
- --key bar --value bat \
- --annotate "org.project.InterfaceName.Method()" \
- --key org.freedesktop.DBus.Deprecated --value true \
- --annotate "org.project.InterfaceName.Method()[arg_name]" \
- --key snake --value hiss \
- --annotate "org.project.InterfaceName::Signal" \
- --key cat --value meow \
- --annotate "org.project.InterfaceName::Signal[arg_name]" \
- --key dog --value wuff \
- myfile.xml
-]]></programlisting></informalexample>
- </listitem>
- </varlistentry>
- </variablelist>
</refsect1>
<refsect1>
diff --git a/src/codegen.py b/src/codegen.py
index 8b388b7..1a6273e 100644
--- a/src/codegen.py
+++ b/src/codegen.py
@@ -565,7 +565,7 @@ class CodeGenerator:
else:
self.c.write(' (GDBusAnnotationInfo **) &%s_arg_%s_annotation_info_pointers\n'%(prefix, a.name))
self.c.write(' },\n')
- if not utils.lookup_annotation(a.annotations, 'org.gtk.GDBus.UseGVariant'):
+ if not utils.lookup_annotation(a.annotations, 'org.gtk.GDBus.C.ForceGVariant'):
self.c.write(' FALSE\n')
else:
self.c.write(' TRUE\n')
@@ -684,7 +684,7 @@ class CodeGenerator:
self.c.write(' },\n'
' "%s",\n'
%(p.name_hyphen))
- if not utils.lookup_annotation(p.annotations, 'org.gtk.GDBus.UseGVariant'):
+ if not utils.lookup_annotation(p.annotations, 'org.gtk.GDBus.C.ForceGVariant'):
self.c.write(' FALSE\n')
else:
self.c.write(' TRUE\n')
diff --git a/src/codegen_main.py b/src/codegen_main.py
index 7e70e80..9ab2d1f 100644
--- a/src/codegen_main.py
+++ b/src/codegen_main.py
@@ -132,10 +132,10 @@ def codegen_main():
help='String to strip from D-Bus interface names for code and docs')
arg_parser.add_argument('--c-namespace', nargs='?', metavar='NAMESPACE', default='',
help='The namespace to use for generated C code')
- arg_parser.add_argument('--generate-c-code', nargs='?', metavar='OUTFILE',
- help='Generate C code in OUTFILE.[ch]')
- arg_parser.add_argument('--generate-docbook', nargs='?', metavar='OUTFILE',
- help='Generate Docbook in OUTFILE-org.Project.IFace.xml')
+ arg_parser.add_argument('--generate-c-code', nargs='?', metavar='OUTFILES',
+ help='Generate C code in OUTFILES.[ch]')
+ arg_parser.add_argument('--generate-docbook', nargs='?', metavar='OUTFILES',
+ help='Generate Docbook in OUTFILES-org.Project.IFace.xml')
arg_parser.add_argument('--annotate', nargs=3, action='append', metavar=('WHAT', 'KEY', 'VALUE'),
help='Add annotation (may be used several times)')
args = arg_parser.parse_args();
diff --git a/src/dbustypes.py b/src/dbustypes.py
index 01b2dda..a0cecbb 100644
--- a/src/dbustypes.py
+++ b/src/dbustypes.py
@@ -29,7 +29,7 @@ class Arg:
self.free_func = 'g_variant_unref'
self.format_in = '@' + self.signature
self.format_out = '@' + self.signature
- if not utils.lookup_annotation(self.annotations, 'org.gtk.GDBus.UseGVariant'):
+ if not utils.lookup_annotation(self.annotations, 'org.gtk.GDBus.C.ForceGVariant'):
if self.signature == 'b':
self.ctype_in_g = 'gboolean '
self.ctype_in = 'gboolean '
diff --git a/src/org.project.xml b/src/org.project.xml
index fdd5a1f..b987407 100644
--- a/src/org.project.xml
+++ b/src/org.project.xml
@@ -165,57 +165,57 @@
<!-- Forcing GVariant for types that would be mapped -->
<method name="ForceMethod">
<arg name="force_in_i" type="i" direction="in">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
<arg name="force_in_s" type="s" direction="in">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
<arg name="force_in_ay" type="ay" direction="in">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
<arg name="force_in_struct" type="(i)" direction="in">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
<arg name="force_out_i" type="i" direction="out">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
<arg name="force_out_s" type="s" direction="out">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
<arg name="force_out_ay" type="ay" direction="out">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
<arg name="force_out_struct" type="(i)" direction="out">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
</method>
<signal name="ForceSignal">
<arg name="force_i" type="i">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
<arg name="force_s" type="s">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
<arg name="force_ay" type="ay">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
<arg name="force_struct" type="(i)">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</arg>
</signal>
<property name="force_i" type="i" access="readwrite">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</property>
<property name="force_s" type="s" access="readwrite">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</property>
<property name="force_ay" type="ay" access="readwrite">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</property>
<property name="force_struct" type="(i)" access="readwrite">
- <annotation name="org.gtk.GDBus.UseGVariant" value="true"/>
+ <annotation name="org.gtk.GDBus.C.ForceGVariant" value="true"/>
</property>
</interface> <!-- End org.project.Bat -->