| <refentry id="glib-mkenums" lang="en"> |
| |
| <refentryinfo> |
| <title>gdbus</title> |
| <productname>GObject</productname> |
| <authorgroup> |
| <author> |
| <contrib>Developer</contrib> |
| <firstname>Owen</firstname> |
| <surname>Taylor</surname> |
| </author> |
| </authorgroup> |
| </refentryinfo> |
| |
| <refmeta> |
| <refentrytitle>glib-mkenums</refentrytitle> |
| <manvolnum>1</manvolnum> |
| <refmiscinfo class="manual">User Commands</refmiscinfo> |
| </refmeta> |
| |
| <refnamediv> |
| <refname>glib-mkenums</refname> |
| <refpurpose>C language enum description generation utility</refpurpose> |
| </refnamediv> |
| |
| <refsynopsisdiv> |
| <cmdsynopsis> |
| <command>glib-mkenums</command> |
| <arg choice="opt" rep="repeat">OPTION</arg> |
| <arg choice="opt" rep="repeat">FILE</arg> |
| </cmdsynopsis> |
| </refsynopsisdiv> |
| |
| <refsect1><title>Description</title> |
| <para><command>glib-mkenums</command> is a small utility that parses C code to |
| extract enum definitions and produces enum descriptions based on text templates |
| specified by the user. Typically, you can use this tool to generate enumeration |
| types for the GType type system, for GObject properties and signal marshalling; |
| additionally, you can use it to generate enumeration values of GSettings schemas. |
| </para> |
| |
| <para><command>glib-mkenums</command> takes a list of valid C code files as |
| input. The options specified control the text that generated, substituting various |
| keywords enclosed in <literal>@</literal> characters in the templates. |
| </para> |
| |
| <refsect2><title>Production text substitutions</title> |
| <para> |
| Certain keywords enclosed in <literal>@</literal> characters will be substituted in the |
| emitted text. For the substitution examples of the keywords below, |
| the following example enum definition is assumed: |
| </para> |
| <informalexample><programlisting> |
| typedef enum |
| { |
| PREFIX_THE_XVALUE = 1 << 3, |
| PREFIX_ANOTHER_VALUE = 1 << 4 |
| } PrefixTheXEnum; |
| </programlisting></informalexample> |
| <variablelist> |
| <varlistentry> |
| <term><literal>@EnumName@</literal>></term> |
| <listitem><para> |
| The name of the enum currently being processed, enum names are assumed to be |
| properly namespaced and to use mixed capitalization to separate |
| words (e.g. <literal>PrefixTheXEnum</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@enum_name@</literal></term> |
| <listitem><para> |
| The enum name with words lowercase and word-separated by underscores |
| (e.g. <literal>prefix_the_xenum</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@ENUMNAME@</literal></term> |
| <listitem><para> |
| The enum name with words uppercase and word-separated by underscores |
| (e.g. <literal>PREFIX_THE_XENUM</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@ENUMSHORT@</literal></term> |
| <listitem><para> |
| The enum name with words uppercase and word-separated by underscores, |
| prefix stripped (e.g. <literal>THE_XENUM</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@ENUMPREFIX@</literal></term> |
| <listitem><para> |
| The prefix of the enum name (e.g. <literal>PREFIX</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@VALUENAME@</literal></term> |
| <listitem><para> |
| The enum value name currently being processed with words uppercase and |
| word-separated by underscores, |
| this is the assumed literal notation of enum values in the C sources |
| (e.g. <literal>PREFIX_THE_XVALUE</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@valuenick@</literal></term> |
| <listitem><para> |
| A nick name for the enum value currently being processed, this is usually |
| generated by stripping common prefix words of all the enum values of the |
| current enum, the words are lowercase and underscores are substituted by a |
| minus (e.g. <literal>the-xvalue</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@valuenum@</literal></term> |
| <listitem><para> |
| The integer value for the enum value currently being processed. If the |
| evaluation fails then <command>glib-mkenums</command> will exit with an |
| error status, but this only happens if <literal>@valuenum@</literal> |
| appears in your value production template. (Since: 2.26) |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@type@</literal></term> |
| <listitem><para> |
| This is substituted either by "enum" or "flags", depending on whether the |
| enum value definitions contained bit-shift operators or not (e.g. <literal>flags</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@Type@</literal></term> |
| <listitem><para> |
| The same as <literal>@type@</literal> with the first letter capitalized (e.g. <literal>Flags</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@TYPE@</literal></term> |
| <listitem><para> |
| The same as <literal>@type@</literal> with all letters uppercased (e.g. <literal>FLAGS</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@filename@</literal></term> |
| <listitem><para> |
| The full path of the input file currently being processed (e.g. <literal>/build/environment/project/src/foo.h</literal>). |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><literal>@basename@</literal></term> |
| <listitem><para> |
| The base name of the input file currently being processed (e.g. <literal>foo.h</literal>). |
| Typically you want to use <literal>@basename@</literal> in place of <literal>@filename@</literal> |
| in your templates, to improve the reproducibility of the build. (Since: 2.22) |
| </para></listitem> |
| </varlistentry> |
| </variablelist> |
| </refsect2> |
| <refsect2><title>Trigraph extensions</title> |
| <para> |
| Some C comments are treated specially in the parsed enum definitions, |
| such comments start out with the trigraph sequence <literal>/*<</literal> |
| and end with the trigraph sequence <literal>>*/</literal>. |
| </para> |
| |
| <para>The following options can be specified per enum definition:</para> |
| <variablelist> |
| <varlistentry> |
| <term><literal>skip</literal></term> |
| <listitem><para> |
| Indicates this enum definition should be skipped. |
| </para></listitem> |
| </varlistentry> |
| <varlistentry> |
| <term><literal>flags</literal></term> |
| <listitem><para> |
| Indicates this enum should be treated as a flags definition. |
| </para></listitem> |
| </varlistentry> |
| <varlistentry> |
| <term><literal>underscore_name</literal></term> |
| <listitem><para> |
| Specifies the word separation used in the <function>*_get_type()</function> |
| function. For instance, <literal>/*< underscore_name=gnome_vfs_uri_hide_options >*/</literal>. |
| </para></listitem> |
| </varlistentry> |
| <varlistentry> |
| <term><literal>since</literal></term> |
| <listitem><para> |
| Specifies the version tag that will be used to substitute the <literal>@enumsince@</literal> |
| keyword in the template, useful when documenting methods generated from the enums |
| (e.g. <literal>Since: @enumsince@</literal>). (Since: 2.66) |
| </para></listitem> |
| </varlistentry> |
| </variablelist> |
| |
| <para>The following options can be specified per value definition:</para> |
| <variablelist> |
| <varlistentry> |
| <term><literal>skip</literal></term> |
| <listitem><para> |
| Indicates the value should be skipped. |
| </para></listitem> |
| </varlistentry> |
| <varlistentry> |
| <term><literal>nick</literal></term> |
| <listitem><para> |
| Specifies the otherwise auto-generated nickname. |
| </para></listitem> |
| </varlistentry> |
| </variablelist> |
| |
| <para>Examples:</para> |
| <informalexample><programlisting> |
| typedef enum /*< skip >*/ |
| { |
| PREFIX_FOO |
| } PrefixThisEnumWillBeSkipped; |
| typedef enum /*< flags,prefix=PREFIX,since=1.0 >*/ |
| { |
| PREFIX_THE_ZEROTH_VALUE, /*< skip >*/ |
| PREFIX_THE_FIRST_VALUE, |
| PREFIX_THE_SECOND_VALUE, |
| PREFIX_THE_THIRD_VALUE, /*< nick=the-last-value >*/ |
| } PrefixTheFlagsEnum; |
| </programlisting></informalexample> |
| </refsect2> |
| </refsect1> |
| |
| <refsect1><title>Options</title> |
| <variablelist> |
| |
| <varlistentry> |
| <term><option>--fhead</option> <replaceable>TEXT</replaceable></term> |
| <listitem><para> |
| Emits <replaceable>TEXT</replaceable> prior to processing input files. |
| </para> |
| <para> |
| You can specify this option multiple times, and the <replaceable>TEXT</replaceable> |
| will be concatenated. |
| </para> |
| <para> |
| When used along with a template file, <replaceable>TEXT</replaceable> |
| will be prepended to the template's <literal>file-header</literal> section. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--fprod</option> <replaceable>TEXT</replaceable></term> |
| <listitem><para> |
| Emits <replaceable>TEXT</replaceable> every time a new input file |
| is being processed. |
| </para> |
| <para> |
| You can specify this option multiple times, and the <replaceable>TEXT</replaceable> |
| will be concatenated. |
| </para> |
| <para> |
| When used along with a template file, <replaceable>TEXT</replaceable> |
| will be appended to the template's <literal>file-production</literal> section. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--ftail</option> <replaceable>TEXT</replaceable></term> |
| <listitem><para> |
| Emits <replaceable>TEXT</replaceable> after all input files have been |
| processed. |
| </para> |
| <para> |
| You can specify this option multiple times, and the <replaceable>TEXT</replaceable> |
| will be concatenated. |
| </para> |
| <para> |
| When used along with a template file, <replaceable>TEXT</replaceable> |
| will be appended to the template's <literal>file-tail</literal> section. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--eprod</option> <replaceable>TEXT</replaceable></term> |
| <listitem><para> |
| Emits <replaceable>TEXT</replaceable> every time an enum is encountered |
| in the input files. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--vhead</option> <replaceable>TEXT</replaceable></term> |
| <listitem><para> |
| Emits <replaceable>TEXT</replaceable> before iterating over the set of |
| values of an enum. |
| </para> |
| <para> |
| You can specify this option multiple times, and the <replaceable>TEXT</replaceable> |
| will be concatenated. |
| </para> |
| <para> |
| When used along with a template file, <replaceable>TEXT</replaceable> |
| will be prepended to the template's <literal>value-header</literal> section. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--vprod</option> <replaceable>TEXT</replaceable></term> |
| <listitem><para> |
| Emits <replaceable>TEXT</replaceable> for every value of an enum. |
| </para> |
| <para> |
| You can specify this option multiple times, and the <replaceable>TEXT</replaceable> |
| will be concatenated. |
| </para> |
| <para> |
| When used along with a template file, <replaceable>TEXT</replaceable> |
| will be appended to the template's <literal>value-production</literal> section. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--vtail</option> <replaceable>TEXT</replaceable></term> |
| <listitem><para> |
| Emits <replaceable>TEXT</replaceable> after iterating over all values |
| of an enum. |
| </para> |
| <para> |
| You can specify this option multiple times, and the <replaceable>TEXT</replaceable> |
| will be concatenated. |
| </para> |
| <para> |
| When used along with a template file, <replaceable>TEXT</replaceable> |
| will be appended to the template's <literal>value-tail</literal> section. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--comments</option> <replaceable>TEXT</replaceable></term> |
| <listitem><para> |
| Template for auto-generated comments, the default (for C code generations) is |
| <literal>"/* @comment@ */"</literal>. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--template</option> <replaceable>FILE</replaceable></term> |
| <listitem><para> |
| Read templates from the given file. The templates are enclosed in |
| specially-formatted C comments: |
| </para> |
| <informalexample><programlisting> |
| /*** BEGIN section ***/ |
| /*** END section ***/ |
| </programlisting></informalexample> |
| <para> |
| <replaceable>section</replaceable> may be <literal>file-header</literal>, |
| <literal>file-production</literal>, <literal>file-tail</literal>, |
| <literal>enumeration-production</literal>, <literal>value-header</literal>, |
| <literal>value-production</literal>, <literal>value-tail</literal> or |
| <literal>comment</literal>. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--identifier-prefix</option> <replaceable>PREFIX</replaceable></term> |
| <listitem><para> |
| Indicates what portion of the enum name should be interpreted as the |
| prefix (eg, the "<literal>Gtk</literal>" in |
| "<literal>GtkDirectionType</literal>"). Normally this will be figured |
| out automatically, but you may need to override the default if your |
| namespace is capitalized oddly. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--symbol-prefix</option> <replaceable>PREFIX</replaceable></term> |
| <listitem><para> |
| Indicates what prefix should be used to correspond to the identifier |
| prefix in related C function names (eg, the "<literal>gtk</literal>" |
| in "<literal>gtk_direction_type_get_type</literal>". Equivalently, |
| this is the lowercase version of the prefix component of the enum |
| value names (eg, the "<literal>GTK</literal>" in |
| "<literal>GTK_DIR_UP</literal>". The default value is the identifier |
| prefix, converted to lowercase. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--help</option></term> |
| <listitem><para> |
| Print brief help and exit. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--version</option></term> |
| <listitem><para> |
| Print version and exit. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>--output=FILE</option></term> |
| <listitem><para> |
| Write output to FILE instead of stdout. |
| </para></listitem> |
| </varlistentry> |
| |
| <varlistentry> |
| <term><option>@RSPFILE</option></term> |
| <listitem><para> |
| When passed as the sole argument, read and parse the actual arguments from |
| <literal>RSPFILE</literal>. Useful on systems with a low command-line length |
| limit. For example, Windows has a limit of 8191 characters. |
| </para></listitem> |
| </varlistentry> |
| |
| </variablelist> |
| </refsect1> |
| |
| <refsect1><title>Using templates</title> |
| <para> |
| Instead of passing the various sections of the generated file to the command |
| line of <command>glib-mkenums</command>, it's strongly recommended to use a |
| template file, especially for generating C sources. |
| </para> |
| |
| <para> |
| A C header template file will typically look like this: |
| </para> |
| <informalexample><programlisting> |
| /*** BEGIN file-header ***/ |
| #pragma once |
| |
| /* Include the main project header */ |
| #include "project.h" |
| |
| G_BEGIN_DECLS |
| /*** END file-header ***/ |
| |
| /*** BEGIN file-production ***/ |
| |
| /* enumerations from "@basename@" */ |
| /*** END file-production ***/ |
| |
| /*** BEGIN value-header ***/ |
| GType @enum_name@_get_type (void) G_GNUC_CONST; |
| #define @ENUMPREFIX@_TYPE_@ENUMSHORT@ (@enum_name@_get_type ()) |
| /*** END value-header ***/ |
| |
| /*** BEGIN file-tail ***/ |
| G_END_DECLS |
| /*** END file-tail ***/ |
| </programlisting></informalexample> |
| |
| <para> |
| A C source template file will typically look like this: |
| </para> |
| <informalexample><programlisting> |
| /*** BEGIN file-header ***/ |
| #include "config.h" |
| #include "enum-types.h" |
| |
| /*** END file-header ***/ |
| |
| /*** BEGIN file-production ***/ |
| /* enumerations from "@basename@" */ |
| /*** END file-production ***/ |
| |
| /*** BEGIN value-header ***/ |
| GType |
| @enum_name@_get_type (void) |
| { |
| static gsize static_g_@type@_type_id; |
| |
| if (g_once_init_enter (&static_g_@type@_type_id)) |
| { |
| static const G@Type@Value values[] = { |
| /*** END value-header ***/ |
| |
| /*** BEGIN value-production ***/ |
| { @VALUENAME@, "@VALUENAME@", "@valuenick@" }, |
| /*** END value-production ***/ |
| |
| /*** BEGIN value-tail ***/ |
| { 0, NULL, NULL } |
| }; |
| |
| GType g_@type@_type_id = |
| g_@type@_register_static (g_intern_static_string ("@EnumName@"), values); |
| |
| g_once_init_leave (&static_g_@type@_type_id, g_@type@_type_id); |
| } |
| return static_g_@type@_type_id; |
| } |
| |
| /*** END value-tail ***/ |
| </programlisting></informalexample> |
| |
| <para> |
| Template files are easier to modify and update, and can be used |
| to generate various types of outputs using the same command line |
| or tools during the build. |
| </para> |
| </refsect1> |
| |
| <refsect1><title>Using glib-mkenums with Meson</title> |
| <para> |
| Meson supports generating enumeration types using <command>glib-mkenums</command> |
| out of the box in its "gnome" module. |
| </para> |
| |
| <para> |
| In your <filename>meson.build</filename> file you will typically call the |
| <literal>gnome.mkenums_simple()</literal> method to generate idiomatic enumeration |
| types from a list of headers to inspect: |
| </para> |
| <informalexample><programlisting> |
| project_headers = [ |
| 'project-foo.h', |
| 'project-bar.h', |
| 'project-baz.h', |
| ] |
| |
| gnome = import('gnome') |
| enum_files = gnome.mkenums_simple('enum-types', |
| sources: project_headers, |
| ) |
| </programlisting></informalexample> |
| |
| <para> |
| The <literal>enum_files</literal> variable will contain an array of two elements |
| in the following order: |
| </para> |
| <itemizedlist> |
| <listitem><para>a build target for the source file</para></listitem> |
| <listitem><para>a build target for the header file</para></listitem> |
| </itemizedlist> |
| <para> |
| You should use the returned objects to provide a dependency on every other |
| build target that references the source or header file; for instance, if you |
| are using the source to build a library: |
| </para> |
| <informalexample><programlisting> |
| mainlib = library('project', |
| sources: project_sources + enum_files, |
| ... |
| ) |
| </programlisting></informalexample> |
| <para> |
| Additionally, if you are including the generated header file inside a build |
| target that depends on the library you just built, you must ensure that the |
| internal dependency includes the generated header as a required source file: |
| </para> |
| <informalexample><programlisting> |
| mainlib_dep = declare_dependency(sources: enum_files[1], link_with: mainlib) |
| </programlisting></informalexample> |
| <para> |
| You should not include the generated source file as well, otherwise it will |
| be built separately for every target that depends on it, causing build |
| failures. To know more about why all this is required, please refer to the |
| <ulink url="https://mesonbuild.com/FAQ.html#how-do-i-tell-meson-that-my-sources-use-generated-headers"> |
| corresponding Meson FAQ entry</ulink>. |
| </para> |
| |
| <para> |
| If you are generating C header and source files that require special |
| templates, you can use <literal>gnome.mkenums()</literal> to provide those |
| headers, for instance: |
| </para> |
| <informalexample><programlisting> |
| enum_files = gnome.mkenums('enum-types', |
| sources: project_headers, |
| h_template: 'enum-types.h.in', |
| c_template: 'enum-types.c.in', |
| install_header: true, |
| ) |
| </programlisting></informalexample> |
| <para> |
| For more information, see the <ulink url="https://mesonbuild.com/Gnome-module.html#gnomegenmarshal">Meson |
| documentation for <literal>gnome.mkenums()</literal></ulink>. |
| </para> |
| </refsect1> |
| |
| <refsect1><title>Using glib-mkenums with Autotools</title> |
| <para> |
| In order to use <command>glib-mkenums</command> in your project when using |
| Autotools as the build system, you will first need to modify your |
| <filename>configure.ac</filename> file to ensure you find the appropriate |
| command using <command>pkg-config</command>, similarly as to how you discover |
| the compiler and linker flags for GLib. |
| </para> |
| <informalexample><programlisting> |
| PKG_PROG_PKG_CONFIG([0.28]) |
| |
| PKG_CHECK_VAR([GLIB_MKENUMS], [glib-2.0], [glib_mkenums]) |
| </programlisting></informalexample> |
| <para> |
| In your <filename>Makefile.am</filename> file you will typically use rules |
| like these: |
| </para> |
| <informalexample><programlisting> |
| # A list of headers to inspect |
| project_headers = \ |
| project-foo.h \ |
| project-bar.h \ |
| project-baz.h |
| |
| enum-types.h: $(project_headers) enum-types.h.in |
| $(AM_V_GEN)$(GLIB_MKENUMS) \ |
| --template=enum-types.h.in \ |
| --output=$@ \ |
| $(project_headers) |
| |
| enum-types.c: $(project_headers) enum-types.c.in enum-types.h |
| $(AM_V_GEN)$(GLIB_MKENUMS) \ |
| --template=enum-types.c.in \ |
| --output=$@ \ |
| $(project_headers) |
| |
| # Build the enum types files before every other target |
| BUILT_SOURCES += enum-types.h enum-types.c |
| CLEANFILES += enum-types.h enum-types.c |
| EXTRA_DIST += enum-types.h.in enum-types.c.in |
| </programlisting></informalexample> |
| <para> |
| In the example above, we have a variable called <literal>project_headers</literal> |
| where we reference all header files we want to inspect for generating enumeration |
| GTypes. In the <filename>enum-types.h</filename> rule we use <command>glib-mkenums</command> |
| with a template called <filename>enum-types.h.in</filename> in order to generate the |
| header file; similarly, in the <filename>enum-types.c</filename> rule we use a |
| template called <filename>enum-types.c.in</filename>. |
| </para> |
| </refsect1> |
| |
| <refsect1><title>See also</title> |
| <para> |
| <citerefentry> |
| <refentrytitle>glib-genmarshal</refentrytitle> |
| <manvolnum>1</manvolnum> |
| </citerefentry> |
| </para> |
| </refsect1> |
| </refentry> |