/* GDBus - GLib D-Bus Library
 *
 * Copyright (C) 2008-2010 Red Hat, Inc.
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General
 * Public License along with this library; if not, write to the
 * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
 * Boston, MA 02111-1307, USA.
 *
 * Author: David Zeuthen <davidz@redhat.com>
 */

#include "config.h"

#include <stdlib.h>
#include <string.h>

#include "gdbusintrospection.h"

#include "glibintl.h"

/**
 * SECTION:gdbusintrospection
 * @title: D-Bus Introspection Data
 * @short_description: Node and interface description data structures
 * @include: gio/gio.h
 *
 * Various data structures and convenience routines to parse and
 * generate D-Bus introspection XML. Introspection information is
 * used when registering objects with g_dbus_connection_register_object().
 *
 * The format of D-Bus introspection XML is specified in the
 * <link linkend="http://dbus.freedesktop.org/doc/dbus-specification.html&num;introspection-format">D-Bus specification</link>.
 */

/* ---------------------------------------------------------------------------------------------------- */

#define _MY_DEFINE_BOXED_TYPE(TypeName, type_name) \
  G_DEFINE_BOXED_TYPE (TypeName, type_name, type_name##_ref, type_name##_unref)

_MY_DEFINE_BOXED_TYPE (GDBusNodeInfo,       g_dbus_node_info);
_MY_DEFINE_BOXED_TYPE (GDBusInterfaceInfo,  g_dbus_interface_info);
_MY_DEFINE_BOXED_TYPE (GDBusMethodInfo,     g_dbus_method_info);
_MY_DEFINE_BOXED_TYPE (GDBusSignalInfo,     g_dbus_signal_info);
_MY_DEFINE_BOXED_TYPE (GDBusPropertyInfo,   g_dbus_property_info);
_MY_DEFINE_BOXED_TYPE (GDBusArgInfo,        g_dbus_arg_info);
_MY_DEFINE_BOXED_TYPE (GDBusAnnotationInfo, g_dbus_annotation_info);

/* ---------------------------------------------------------------------------------------------------- */

typedef struct
{
  /* stuff we are currently collecting */
  GPtrArray *args;
  GPtrArray *out_args;
  GPtrArray *methods;
  GPtrArray *signals;
  GPtrArray *properties;
  GPtrArray *interfaces;
  GPtrArray *nodes;
  GPtrArray *annotations;

  /* A list of GPtrArray's containing annotations */
  GSList *annotations_stack;

  /* A list of GPtrArray's containing interfaces */
  GSList *interfaces_stack;

  /* A list of GPtrArray's containing nodes */
  GSList *nodes_stack;

  /* Whether the direction was "in" for last parsed arg */
  gboolean last_arg_was_in;

  /* Number of args currently being collected; used for assigning
   * names to args without a "name" attribute
   */
  guint num_args;

} ParseData;

/* ---------------------------------------------------------------------------------------------------- */

/**
 * g_dbus_node_info_ref:
 * @info: A #GDBusNodeInfo
 *
 * If @info is statically allocated does nothing. Otherwise increases
 * the reference count.
 *
 * Returns: The same @info.
 *
 * Since: 2.26
 */
GDBusNodeInfo *
g_dbus_node_info_ref (GDBusNodeInfo *info)
{
  if (info->ref_count == -1)
    return info;
  g_atomic_int_inc (&info->ref_count);
  return info;
}

/**
 * g_dbus_interface_info_ref:
 * @info: A #GDBusInterfaceInfo
 *
 * If @info is statically allocated does nothing. Otherwise increases
 * the reference count.
 *
 * Returns: The same @info.
 *
 * Since: 2.26
 */
GDBusInterfaceInfo *
g_dbus_interface_info_ref (GDBusInterfaceInfo *info)
{
  if (info->ref_count == -1)
    return info;
  g_atomic_int_inc (&info->ref_count);
  return info;
}

/**
 * g_dbus_method_info_ref:
 * @info: A #GDBusMethodInfo
 *
 * If @info is statically allocated does nothing. Otherwise increases
 * the reference count.
 *
 * Returns: The same @info.
 *
 * Since: 2.26
 */
GDBusMethodInfo *
g_dbus_method_info_ref (GDBusMethodInfo *info)
{
  if (info->ref_count == -1)
    return info;
  g_atomic_int_inc (&info->ref_count);
  return info;
}

/**
 * g_dbus_signal_info_ref:
 * @info: A #GDBusSignalInfo
 *
 * If @info is statically allocated does nothing. Otherwise increases
 * the reference count.
 *
 * Returns: The same @info.
 *
 * Since: 2.26
 */
GDBusSignalInfo *
g_dbus_signal_info_ref (GDBusSignalInfo *info)
{
  if (info->ref_count == -1)
    return info;
  g_atomic_int_inc (&info->ref_count);
  return info;
}

/**
 * g_dbus_property_info_ref:
 * @info: A #GDBusPropertyInfo
 *
 * If @info is statically allocated does nothing. Otherwise increases
 * the reference count.
 *
 * Returns: The same @info.
 *
 * Since: 2.26
 */
GDBusPropertyInfo *
g_dbus_property_info_ref (GDBusPropertyInfo *info)
{
  if (info->ref_count == -1)
    return info;
  g_atomic_int_inc (&info->ref_count);
  return info;
}

/**
 * g_dbus_arg_info_ref:
 * @info: A #GDBusArgInfo
 *
 * If @info is statically allocated does nothing. Otherwise increases
 * the reference count.
 *
 * Returns: The same @info.
 *
 * Since: 2.26
 */
GDBusArgInfo *
g_dbus_arg_info_ref (GDBusArgInfo *info)
{
  if (info->ref_count == -1)
    return info;
  g_atomic_int_inc (&info->ref_count);
  return info;
}

/**
 * g_dbus_annotation_info_ref:
 * @info: A #GDBusNodeInfo
 *
 * If @info is statically allocated does nothing. Otherwise increases
 * the reference count.
 *
 * Returns: The same @info.
 *
 * Since: 2.26
 */
GDBusAnnotationInfo *
g_dbus_annotation_info_ref (GDBusAnnotationInfo *info)
{
  if (info->ref_count == -1)
    return info;
  g_atomic_int_inc (&info->ref_count);
  return info;
}

/* ---------------------------------------------------------------------------------------------------- */

static void
free_null_terminated_array (gpointer array, GDestroyNotify unref_func)
{
  guint n;
  gpointer *p = array;
  if (p == NULL)
    return;
  for (n = 0; p[n] != NULL; n++)
    unref_func (p[n]);
  g_free (p);
}

/**
 * g_dbus_annotation_info_unref:
 * @info: A #GDBusAnnotationInfo.
 *
 * If @info is statically allocated, does nothing. Otherwise decreases
 * the reference count of @info. When its reference count drops to 0,
 * the memory used is freed.
 *
 * Since: 2.26
 */
void
g_dbus_annotation_info_unref (GDBusAnnotationInfo *info)
{
  if (info->ref_count == -1)
    return;
  if (g_atomic_int_dec_and_test (&info->ref_count))
    {
      g_free (info->key);
      g_free (info->value);
      free_null_terminated_array (info->annotations, (GDestroyNotify) g_dbus_annotation_info_unref);
      g_free (info);
    }
}

/**
 * g_dbus_arg_info_unref:
 * @info: A #GDBusArgInfo.
 *
 * If @info is statically allocated, does nothing. Otherwise decreases
 * the reference count of @info. When its reference count drops to 0,
 * the memory used is freed.
 *
 * Since: 2.26
 */
void
g_dbus_arg_info_unref (GDBusArgInfo *info)
{
  if (info->ref_count == -1)
    return;
  if (g_atomic_int_dec_and_test (&info->ref_count))
    {
      g_free (info->name);
      g_free (info->signature);
      free_null_terminated_array (info->annotations, (GDestroyNotify) g_dbus_annotation_info_unref);
      g_free (info);
    }
}

/**
 * g_dbus_method_info_unref:
 * @info: A #GDBusMethodInfo.
 *
 * If @info is statically allocated, does nothing. Otherwise decreases
 * the reference count of @info. When its reference count drops to 0,
 * the memory used is freed.
 *
 * Since: 2.26
 */
void
g_dbus_method_info_unref (GDBusMethodInfo *info)
{
  if (info->ref_count == -1)
    return;
  if (g_atomic_int_dec_and_test (&info->ref_count))
    {
      g_free (info->name);
      free_null_terminated_array (info->in_args, (GDestroyNotify) g_dbus_arg_info_unref);
      free_null_terminated_array (info->out_args, (GDestroyNotify) g_dbus_arg_info_unref);
      free_null_terminated_array (info->annotations, (GDestroyNotify) g_dbus_annotation_info_unref);
      g_free (info);
    }
}

/**
 * g_dbus_signal_info_unref:
 * @info: A #GDBusSignalInfo.
 *
 * If @info is statically allocated, does nothing. Otherwise decreases
 * the reference count of @info. When its reference count drops to 0,
 * the memory used is freed.
 *
 * Since: 2.26
 */
void
g_dbus_signal_info_unref (GDBusSignalInfo *info)
{
  if (info->ref_count == -1)
    return;
  if (g_atomic_int_dec_and_test (&info->ref_count))
    {
      g_free (info->name);
      free_null_terminated_array (info->args, (GDestroyNotify) g_dbus_arg_info_unref);
      free_null_terminated_array (info->annotations, (GDestroyNotify) g_dbus_annotation_info_unref);
      g_free (info);
    }
}

/**
 * g_dbus_property_info_unref:
 * @info: A #GDBusPropertyInfo.
 *
 * If @info is statically allocated, does nothing. Otherwise decreases
 * the reference count of @info. When its reference count drops to 0,
 * the memory used is freed.
 *
 * Since: 2.26
 */
void
g_dbus_property_info_unref (GDBusPropertyInfo *info)
{
  if (info->ref_count == -1)
    return;
  if (g_atomic_int_dec_and_test (&info->ref_count))
    {
      g_free (info->name);
      g_free (info->signature);
      free_null_terminated_array (info->annotations, (GDestroyNotify) g_dbus_annotation_info_unref);
      g_free (info);
    }
}

/**
 * g_dbus_interface_info_unref:
 * @info: A #GDBusInterfaceInfo.
 *
 * If @info is statically allocated, does nothing. Otherwise decreases
 * the reference count of @info. When its reference count drops to 0,
 * the memory used is freed.
 *
 * Since: 2.26
 */
void
g_dbus_interface_info_unref (GDBusInterfaceInfo *info)
{
  if (info->ref_count == -1)
    return;
  if (g_atomic_int_dec_and_test (&info->ref_count))
    {
      g_free (info->name);
      free_null_terminated_array (info->methods, (GDestroyNotify) g_dbus_method_info_unref);
      free_null_terminated_array (info->signals, (GDestroyNotify) g_dbus_signal_info_unref);
      free_null_terminated_array (info->properties, (GDestroyNotify) g_dbus_property_info_unref);
      free_null_terminated_array (info->annotations, (GDestroyNotify) g_dbus_annotation_info_unref);
      g_free (info);
    }
}

/**
 * g_dbus_node_info_unref:
 * @info: A #GDBusNodeInfo.
 *
 * If @info is statically allocated, does nothing. Otherwise decreases
 * the reference count of @info. When its reference count drops to 0,
 * the memory used is freed.
 *
 * Since: 2.26
 */
void
g_dbus_node_info_unref (GDBusNodeInfo *info)
{
  if (info->ref_count == -1)
    return;
  if (g_atomic_int_dec_and_test (&info->ref_count))
    {
      g_free (info->path);
      free_null_terminated_array (info->interfaces, (GDestroyNotify) g_dbus_interface_info_unref);
      free_null_terminated_array (info->nodes, (GDestroyNotify) g_dbus_node_info_unref);
      free_null_terminated_array (info->annotations, (GDestroyNotify) g_dbus_annotation_info_unref);
      g_free (info);
    }
}

/* ---------------------------------------------------------------------------------------------------- */

static void
g_dbus_annotation_info_set (ParseData                      *data,
                            GDBusAnnotationInfo            *info,
                            const gchar                    *key,
                            const gchar                    *value,
                            GDBusAnnotationInfo **embedded_annotations)
{
  info->ref_count = 1;

  if (key != NULL)
    info->key = g_strdup (key);

  if (value != NULL)
    info->value = g_strdup (value);

  if (embedded_annotations != NULL)
    info->annotations = embedded_annotations;
}

static void
g_dbus_arg_info_set (ParseData            *data,
                     GDBusArgInfo         *info,
                     const gchar          *name,
                     const gchar          *signature,
                     GDBusAnnotationInfo **annotations)
{
  info->ref_count = 1;

  /* name may be NULL - TODO: compute name? */
  if (name != NULL)
    info->name = g_strdup (name);

  if (signature != NULL)
    info->signature = g_strdup (signature);

  if (annotations != NULL)
    info->annotations = annotations;
}

static void
g_dbus_method_info_set (ParseData            *data,
                        GDBusMethodInfo      *info,
                        const gchar          *name,
                        guint                 in_num_args,
                        GDBusArgInfo        **in_args,
                        guint                 out_num_args,
                        GDBusArgInfo        **out_args,
                        GDBusAnnotationInfo **annotations)
{
  info->ref_count = 1;

  if (name != NULL)
    info->name = g_strdup (name);

  if (in_num_args != 0)
    {
      //info->in_num_args = in_num_args;
      info->in_args = in_args;
    }

  if (out_num_args != 0)
    {
      //info->out_num_args = out_num_args;
      info->out_args = out_args;
    }

  if (annotations != NULL)
    info->annotations = annotations;
}

static void
g_dbus_signal_info_set (ParseData            *data,
                        GDBusSignalInfo      *info,
                        const gchar          *name,
                        guint                 num_args,
                        GDBusArgInfo        **args,
                        GDBusAnnotationInfo **annotations)
{
  info->ref_count = 1;

  if (name != NULL)
    info->name = g_strdup (name);

  if (num_args != 0)
    {
      //info->num_args = num_args;
      info->args = args;
    }

  if (annotations != NULL)
    {
      info->annotations = annotations;
    }
}

static void
g_dbus_property_info_set (ParseData               *data,
                          GDBusPropertyInfo       *info,
                          const gchar             *name,
                          const gchar             *signature,
                          GDBusPropertyInfoFlags   flags,
                          GDBusAnnotationInfo    **annotations)
{
  info->ref_count = 1;

  if (name != NULL)
    info->name = g_strdup (name);

  if (flags != G_DBUS_PROPERTY_INFO_FLAGS_NONE)
    info->flags = flags;

  if (signature != NULL)
    {
      info->signature = g_strdup (signature);
    }

  if (annotations != NULL)
    {
      info->annotations = annotations;
    }
}

static void
g_dbus_interface_info_set (ParseData            *data,
                           GDBusInterfaceInfo   *info,
                           const gchar          *name,
                           guint                 num_methods,
                           GDBusMethodInfo     **methods,
                           guint                 num_signals,
                           GDBusSignalInfo     **signals,
                           guint                 num_properties,
                           GDBusPropertyInfo   **properties,
                           GDBusAnnotationInfo **annotations)
{
  info->ref_count = 1;

  if (name != NULL)
    {
      info->name = g_strdup (name);
    }

  if (num_methods != 0)
    {
      //info->num_methods    = num_methods;
      info->methods        = methods;
    }

  if (num_signals != 0)
    {
      //info->num_signals    = num_signals;
      info->signals        = signals;
    }

  if (num_properties != 0)
    {
      //info->num_properties = num_properties;
      info->properties     = properties;
    }

  if (annotations != NULL)
    {
      info->annotations = annotations;
    }
}

static void
g_dbus_node_info_set (ParseData            *data,
                      GDBusNodeInfo        *info,
                      const gchar          *path,
                      guint                 num_interfaces,
                      GDBusInterfaceInfo  **interfaces,
                      guint                 num_nodes,
                      GDBusNodeInfo       **nodes,
                      GDBusAnnotationInfo **annotations)
{
  info->ref_count = 1;

  if (path != NULL)
    {
      info->path = g_strdup (path);
      /* TODO: relative / absolute path snafu */
    }

  if (num_interfaces != 0)
    {
      //info->num_interfaces = num_interfaces;
      info->interfaces     = interfaces;
    }

  if (num_nodes != 0)
    {
      //info->num_nodes      = num_nodes;
      info->nodes          = nodes;
    }

  if (annotations != NULL)
    {
      info->annotations = annotations;
    }

}

/* ---------------------------------------------------------------------------------------------------- */

static void
g_dbus_annotation_info_generate_xml (GDBusAnnotationInfo        *info,
                                     guint                       indent,
                                     GString                    *string_builder)
{
  guint n;

  g_string_append_printf (string_builder, "%*s<annotation name=\"%s\" value=\"%s\"",
                          indent, "",
                          info->key,
                          info->value);

  if (info->annotations == NULL)
    {
      g_string_append (string_builder, "/>\n");
    }
  else
    {
      g_string_append (string_builder, ">\n");

      for (n = 0; info->annotations != NULL && info->annotations[n] != NULL; n++)
        g_dbus_annotation_info_generate_xml (info->annotations[n],
                                             indent + 2,
                                             string_builder);

      g_string_append_printf (string_builder, "%*s</annotation>\n",
                              indent, "");
    }

}

static void
g_dbus_arg_info_generate_xml (GDBusArgInfo        *info,
                              guint                indent,
                              const gchar         *extra_attributes,
                              GString             *string_builder)
{
  guint n;

  g_string_append_printf (string_builder, "%*s<arg type=\"%s\"",
                          indent, "",
                          info->signature);

  if (info->name != NULL)
    g_string_append_printf (string_builder, " name=\"%s\"", info->name);

  if (extra_attributes != NULL)
    g_string_append_printf (string_builder, " %s", extra_attributes);

  if (info->annotations == NULL)
    {
      g_string_append (string_builder, "/>\n");
    }
  else
    {
      g_string_append (string_builder, ">\n");

      for (n = 0; info->annotations != NULL && info->annotations[n] != NULL; n++)
        g_dbus_annotation_info_generate_xml (info->annotations[n],
                                             indent + 2,
                                             string_builder);

      g_string_append_printf (string_builder, "%*s</arg>\n", indent, "");
    }

}

static void
g_dbus_method_info_generate_xml (GDBusMethodInfo        *info,
                                 guint                   indent,
                                 GString                *string_builder)
{
  guint n;

  g_string_append_printf (string_builder, "%*s<method name=\"%s\"",
                          indent, "",
                          info->name);

  if (info->annotations == NULL && info->in_args == NULL && info->out_args == NULL)
    {
      g_string_append (string_builder, "/>\n");
    }
  else
    {
      g_string_append (string_builder, ">\n");

      for (n = 0; info->annotations != NULL && info->annotations[n] != NULL; n++)
        g_dbus_annotation_info_generate_xml (info->annotations[n],
                                             indent + 2,
                                             string_builder);

      for (n = 0; info->in_args != NULL && info->in_args[n] != NULL; n++)
        g_dbus_arg_info_generate_xml (info->in_args[n],
                                      indent + 2,
                                      "direction=\"in\"",
                                      string_builder);

      for (n = 0; info->out_args != NULL && info->out_args[n] != NULL; n++)
        g_dbus_arg_info_generate_xml (info->out_args[n],
                                      indent + 2,
                                      "direction=\"out\"",
                                      string_builder);

      g_string_append_printf (string_builder, "%*s</method>\n", indent, "");
    }
}

static void
g_dbus_signal_info_generate_xml (GDBusSignalInfo        *info,
                                 guint                   indent,
                                 GString                *string_builder)
{
  guint n;

  g_string_append_printf (string_builder, "%*s<signal name=\"%s\"",
                          indent, "",
                          info->name);

  if (info->annotations == NULL && info->args == NULL)
    {
      g_string_append (string_builder, "/>\n");
    }
  else
    {
      g_string_append (string_builder, ">\n");

      for (n = 0; info->annotations != NULL && info->annotations[n] != NULL; n++)
        g_dbus_annotation_info_generate_xml (info->annotations[n],
                                             indent + 2,
                                             string_builder);

      for (n = 0; info->args != NULL && info->args[n] != NULL; n++)
        g_dbus_arg_info_generate_xml (info->args[n],
                                      indent + 2,
                                      NULL,
                                      string_builder);

      g_string_append_printf (string_builder, "%*s</signal>\n", indent, "");
    }
}

static void
g_dbus_property_info_generate_xml (GDBusPropertyInfo        *info,
                                   guint                     indent,
                                   GString                  *string_builder)
{
  guint n;
  const gchar *access_string;

  if ((info->flags & G_DBUS_PROPERTY_INFO_FLAGS_READABLE) &&
      (info->flags & G_DBUS_PROPERTY_INFO_FLAGS_WRITABLE))
    {
      access_string = "readwrite";
    }
  else if (info->flags & G_DBUS_PROPERTY_INFO_FLAGS_READABLE)
    {
      access_string = "read";
    }
  else if (info->flags & G_DBUS_PROPERTY_INFO_FLAGS_WRITABLE)
    {
      access_string = "write";
    }
  else
    {
      g_assert_not_reached ();
    }

  g_string_append_printf (string_builder, "%*s<property type=\"%s\" name=\"%s\" access=\"%s\"",
                          indent, "",
                          info->signature,
                          info->name,
                          access_string);

  if (info->annotations == NULL)
    {
      g_string_append (string_builder, "/>\n");
    }
  else
    {
      g_string_append (string_builder, ">\n");

      for (n = 0; info->annotations != NULL && info->annotations[n] != NULL; n++)
        g_dbus_annotation_info_generate_xml (info->annotations[n],
                                               indent + 2,
                                               string_builder);

      g_string_append_printf (string_builder, "%*s</property>\n", indent, "");
    }

}

/**
 * g_dbus_interface_info_generate_xml:
 * @info: A #GDBusNodeInfo
 * @indent: Indentation level.
 * @string_builder: A #GString to to append XML data to.
 *
 * Appends an XML representation of @info (and its children) to @string_builder.
 *
 * This function is typically used for generating introspection XML
 * documents at run-time for handling the
 * <literal>org.freedesktop.DBus.Introspectable.Introspect</literal>
 * method.
 *
 * Since: 2.26
 */
void
g_dbus_interface_info_generate_xml (GDBusInterfaceInfo        *info,
                                    guint                      indent,
                                    GString                   *string_builder)
{
  guint n;

  g_string_append_printf (string_builder, "%*s<interface name=\"%s\">\n",
                          indent, "",
                          info->name);

  for (n = 0; info->annotations != NULL && info->annotations[n] != NULL; n++)
    g_dbus_annotation_info_generate_xml (info->annotations[n],
                                         indent + 2,
                                         string_builder);

  for (n = 0; info->methods != NULL && info->methods[n] != NULL; n++)
    g_dbus_method_info_generate_xml (info->methods[n],
                                     indent + 2,
                                     string_builder);

  for (n = 0; info->signals != NULL && info->signals[n] != NULL; n++)
    g_dbus_signal_info_generate_xml (info->signals[n],
                                     indent + 2,
                                     string_builder);

  for (n = 0; info->properties != NULL && info->properties[n] != NULL; n++)
    g_dbus_property_info_generate_xml (info->properties[n],
                                       indent + 2,
                                       string_builder);

  g_string_append_printf (string_builder, "%*s</interface>\n", indent, "");
}

/**
 * g_dbus_node_info_generate_xml:
 * @info: A #GDBusNodeInfo.
 * @indent: Indentation level.
 * @string_builder: A #GString to to append XML data to.
 *
 * Appends an XML representation of @info (and its children) to @string_builder.
 *
 * This function is typically used for generating introspection XML documents at run-time for
 * handling the <literal>org.freedesktop.DBus.Introspectable.Introspect</literal> method.
 *
 * Since: 2.26
 */
void
g_dbus_node_info_generate_xml (GDBusNodeInfo        *info,
                               guint                 indent,
                               GString              *string_builder)
{
  guint n;

  g_string_append_printf (string_builder, "%*s<node", indent, "");
  if (info->path != NULL)
    g_string_append_printf (string_builder, " name=\"%s\"", info->path);

  if (info->interfaces == NULL && info->nodes == NULL && info->annotations == NULL)
    {
      g_string_append (string_builder, "/>\n");
    }
  else
    {
      g_string_append (string_builder, ">\n");

      for (n = 0; info->annotations != NULL && info->annotations[n] != NULL; n++)
        g_dbus_annotation_info_generate_xml (info->annotations[n],
                                             indent + 2,
                                             string_builder);

      for (n = 0; info->interfaces != NULL && info->interfaces[n] != NULL; n++)
        g_dbus_interface_info_generate_xml (info->interfaces[n],
                                            indent + 2,
                                            string_builder);

      for (n = 0; info->nodes != NULL && info->nodes[n] != NULL; n++)
        g_dbus_node_info_generate_xml (info->nodes[n],
                                       indent + 2,
                                       string_builder);

      g_string_append_printf (string_builder, "%*s</node>\n", indent, "");
    }
}

/* ---------------------------------------------------------------------------------------------------- */

static GDBusAnnotationInfo **
parse_data_steal_annotations (ParseData *data,
                              guint     *out_num_elements)
{
  GDBusAnnotationInfo **ret;
  if (out_num_elements != NULL)
    *out_num_elements = data->annotations->len;
  if (data->annotations == NULL)
    ret = NULL;
  else
    {
      g_ptr_array_add (data->annotations, NULL);
      ret = (GDBusAnnotationInfo **) g_ptr_array_free (data->annotations, FALSE);
    }
  data->annotations = g_ptr_array_new ();
  return ret;
}

static GDBusArgInfo **
parse_data_steal_args (ParseData *data,
                       guint     *out_num_elements)
{
  GDBusArgInfo **ret;
  if (out_num_elements != NULL)
    *out_num_elements = data->args->len;
  if (data->args == NULL)
    ret = NULL;
  else
    {
      g_ptr_array_add (data->args, NULL);
      ret = (GDBusArgInfo **) g_ptr_array_free (data->args, FALSE);
    }
  data->args = g_ptr_array_new ();
  return ret;
}

static GDBusArgInfo **
parse_data_steal_out_args (ParseData *data,
                           guint     *out_num_elements)
{
  GDBusArgInfo **ret;
  if (out_num_elements != NULL)
    *out_num_elements = data->out_args->len;
  if (data->out_args == NULL)
    ret = NULL;
  else
    {
      g_ptr_array_add (data->out_args, NULL);
      ret = (GDBusArgInfo **) g_ptr_array_free (data->out_args, FALSE);
    }
  data->out_args = g_ptr_array_new ();
  return ret;
}

static GDBusMethodInfo **
parse_data_steal_methods (ParseData *data,
                          guint     *out_num_elements)
{
  GDBusMethodInfo **ret;
  if (out_num_elements != NULL)
    *out_num_elements = data->methods->len;
  if (data->methods == NULL)
    ret = NULL;
  else
    {
      g_ptr_array_add (data->methods, NULL);
      ret = (GDBusMethodInfo **) g_ptr_array_free (data->methods, FALSE);
    }
  data->methods = g_ptr_array_new ();
  return ret;
}

static GDBusSignalInfo **
parse_data_steal_signals (ParseData *data,
                          guint     *out_num_elements)
{
  GDBusSignalInfo **ret;
  if (out_num_elements != NULL)
    *out_num_elements = data->signals->len;
  if (data->signals == NULL)
    ret = NULL;
  else
    {
      g_ptr_array_add (data->signals, NULL);
      ret = (GDBusSignalInfo **) g_ptr_array_free (data->signals, FALSE);
    }
  data->signals = g_ptr_array_new ();
  return ret;
}

static GDBusPropertyInfo **
parse_data_steal_properties (ParseData *data,
                             guint     *out_num_elements)
{
  GDBusPropertyInfo **ret;
  if (out_num_elements != NULL)
    *out_num_elements = data->properties->len;
  if (data->properties == NULL)
    ret = NULL;
  else
    {
      g_ptr_array_add (data->properties, NULL);
      ret = (GDBusPropertyInfo **) g_ptr_array_free (data->properties, FALSE);
    }
  data->properties = g_ptr_array_new ();
  return ret;
}

static GDBusInterfaceInfo **
parse_data_steal_interfaces (ParseData *data,
                             guint     *out_num_elements)
{
  GDBusInterfaceInfo **ret;
  if (out_num_elements != NULL)
    *out_num_elements = data->interfaces->len;
  if (data->interfaces == NULL)
    ret = NULL;
  else
    {
      g_ptr_array_add (data->interfaces, NULL);
      ret = (GDBusInterfaceInfo **) g_ptr_array_free (data->interfaces, FALSE);
    }
  data->interfaces = g_ptr_array_new ();
  return ret;
}

static GDBusNodeInfo **
parse_data_steal_nodes (ParseData *data,
                        guint     *out_num_elements)
{
  GDBusNodeInfo **ret;
  if (out_num_elements != NULL)
    *out_num_elements = data->nodes->len;
  if (data->nodes == NULL)
    ret = NULL;
  else
    {
      g_ptr_array_add (data->nodes, NULL);
      ret = (GDBusNodeInfo **) g_ptr_array_free (data->nodes, FALSE);
    }
  data->nodes = g_ptr_array_new ();
  return ret;
}

/* ---------------------------------------------------------------------------------------------------- */

static void
parse_data_free_annotations (ParseData *data)
{
  if (data->annotations == NULL)
    return;
  g_ptr_array_foreach (data->annotations, (GFunc) g_dbus_annotation_info_unref, NULL);
  g_ptr_array_free (data->annotations, TRUE);
  data->annotations = NULL;
}

static void
parse_data_free_args (ParseData *data)
{
  if (data->args == NULL)
    return;
  g_ptr_array_foreach (data->args, (GFunc) g_dbus_arg_info_unref, NULL);
  g_ptr_array_free (data->args, TRUE);
  data->args = NULL;
}

static void
parse_data_free_out_args (ParseData *data)
{
  if (data->out_args == NULL)
    return;
  g_ptr_array_foreach (data->out_args, (GFunc) g_dbus_arg_info_unref, NULL);
  g_ptr_array_free (data->out_args, TRUE);
  data->out_args = NULL;
}

static void
parse_data_free_methods (ParseData *data)
{
  if (data->methods == NULL)
    return;
  g_ptr_array_foreach (data->methods, (GFunc) g_dbus_method_info_unref, NULL);
  g_ptr_array_free (data->methods, TRUE);
  data->methods = NULL;
}

static void
parse_data_free_signals (ParseData *data)
{
  if (data->signals == NULL)
    return;
  g_ptr_array_foreach (data->signals, (GFunc) g_dbus_signal_info_unref, NULL);
  g_ptr_array_free (data->signals, TRUE);
  data->signals = NULL;
}

static void
parse_data_free_properties (ParseData *data)
{
  if (data->properties == NULL)
    return;
  g_ptr_array_foreach (data->properties, (GFunc) g_dbus_property_info_unref, NULL);
  g_ptr_array_free (data->properties, TRUE);
  data->properties = NULL;
}

static void
parse_data_free_interfaces (ParseData *data)
{
  if (data->interfaces == NULL)
    return;
  g_ptr_array_foreach (data->interfaces, (GFunc) g_dbus_interface_info_unref, NULL);
  g_ptr_array_free (data->interfaces, TRUE);
  data->interfaces = NULL;
}

static void
parse_data_free_nodes (ParseData *data)
{
  if (data->nodes == NULL)
    return;
  g_ptr_array_foreach (data->nodes, (GFunc) g_dbus_node_info_unref, NULL);
  g_ptr_array_free (data->nodes, TRUE);
  data->nodes = NULL;
}

/* ---------------------------------------------------------------------------------------------------- */

static GDBusAnnotationInfo *
parse_data_get_annotation (ParseData *data,
                           gboolean   create_new)
{
  if (create_new)
    g_ptr_array_add (data->annotations, g_new0 (GDBusAnnotationInfo, 1));
  return data->annotations->pdata[data->annotations->len - 1];
}

static GDBusArgInfo *
parse_data_get_arg (ParseData *data,
                    gboolean   create_new)
{
  if (create_new)
    g_ptr_array_add (data->args, g_new0 (GDBusArgInfo, 1));
  return data->args->pdata[data->args->len - 1];
}

static GDBusArgInfo *
parse_data_get_out_arg (ParseData *data,
                        gboolean   create_new)
{
  if (create_new)
    g_ptr_array_add (data->out_args, g_new0 (GDBusArgInfo, 1));
  return data->out_args->pdata[data->out_args->len - 1];
}

static GDBusMethodInfo *
parse_data_get_method (ParseData *data,
                       gboolean   create_new)
{
  if (create_new)
    g_ptr_array_add (data->methods, g_new0 (GDBusMethodInfo, 1));
  return data->methods->pdata[data->methods->len - 1];
}

static GDBusSignalInfo *
parse_data_get_signal (ParseData *data,
                       gboolean   create_new)
{
  if (create_new)
    g_ptr_array_add (data->signals, g_new0 (GDBusSignalInfo, 1));
  return data->signals->pdata[data->signals->len - 1];
}

static GDBusPropertyInfo *
parse_data_get_property (ParseData *data,
                         gboolean   create_new)
{
  if (create_new)
    g_ptr_array_add (data->properties, g_new0 (GDBusPropertyInfo, 1));
  return data->properties->pdata[data->properties->len - 1];
}

static GDBusInterfaceInfo *
parse_data_get_interface (ParseData *data,
                          gboolean   create_new)
{
  if (create_new)
    g_ptr_array_add (data->interfaces, g_new0 (GDBusInterfaceInfo, 1));
  return data->interfaces->pdata[data->interfaces->len - 1];
}

static GDBusNodeInfo *
parse_data_get_node (ParseData *data,
                     gboolean   create_new)
{
  if (create_new)
    g_ptr_array_add (data->nodes, g_new0 (GDBusNodeInfo, 1));
  return data->nodes->pdata[data->nodes->len - 1];
}

/* ---------------------------------------------------------------------------------------------------- */

static ParseData *
parse_data_new (void)
{
  ParseData *data;

  data = g_new0 (ParseData, 1);

  /* initialize arrays */
  parse_data_steal_annotations (data, NULL);
  parse_data_steal_args (data, NULL);
  parse_data_steal_out_args (data, NULL);
  parse_data_steal_methods (data, NULL);
  parse_data_steal_signals (data, NULL);
  parse_data_steal_properties (data, NULL);
  parse_data_steal_interfaces (data, NULL);
  parse_data_steal_nodes (data, NULL);

  return data;
}

static void
parse_data_free (ParseData *data)
{
  GSList *l;

  /* free stack of annotation arrays */
  for (l = data->annotations_stack; l != NULL; l = l->next)
    {
      GPtrArray *annotations = l->data;
      g_ptr_array_foreach (annotations, (GFunc) g_dbus_annotation_info_unref, NULL);
      g_ptr_array_free (annotations, TRUE);
    }
  g_slist_free (data->annotations_stack);

  /* free stack of interface arrays */
  for (l = data->interfaces_stack; l != NULL; l = l->next)
    {
      GPtrArray *interfaces = l->data;
      g_ptr_array_foreach (interfaces, (GFunc) g_dbus_interface_info_unref, NULL);
      g_ptr_array_free (interfaces, TRUE);
    }
  g_slist_free (data->interfaces_stack);

  /* free stack of node arrays */
  for (l = data->nodes_stack; l != NULL; l = l->next)
    {
      GPtrArray *nodes = l->data;
      g_ptr_array_foreach (nodes, (GFunc) g_dbus_node_info_unref, NULL);
      g_ptr_array_free (nodes, TRUE);
    }
  g_slist_free (data->nodes_stack);

  /* free arrays (data->annotations, data->interfaces and data->nodes have been freed above) */
  parse_data_free_args (data);
  parse_data_free_out_args (data);
  parse_data_free_methods (data);
  parse_data_free_signals (data);
  parse_data_free_properties (data);

  g_free (data);
}

/* ---------------------------------------------------------------------------------------------------- */

static void
parser_start_element (GMarkupParseContext  *context,
                      const gchar          *element_name,
                      const gchar         **attribute_names,
                      const gchar         **attribute_values,
                      gpointer              user_data,
                      GError              **error)
{
  ParseData *data = user_data;
  GSList *stack;
  const gchar *name;
  const gchar *type;
  const gchar *access;
  const gchar *direction;
  const gchar *value;

  name = NULL;
  type = NULL;
  access = NULL;
  direction = NULL;
  value = NULL;

  stack = (GSList *) g_markup_parse_context_get_element_stack (context);

  /* ---------------------------------------------------------------------------------------------------- */
  if (strcmp (element_name, "node") == 0)
    {
      if (!(g_slist_length (stack) >= 1 || strcmp (stack->next->data, "node") != 0))
        {
          g_set_error_literal (error,
                               G_MARKUP_ERROR,
                               G_MARKUP_ERROR_INVALID_CONTENT,
                               "<node> elements can only be top-level or embedded in other <node> elements");
          goto out;
        }

      if (!g_markup_collect_attributes (element_name,
                                        attribute_names,
                                        attribute_values,
                                        error,
                                        G_MARKUP_COLLECT_STRING | G_MARKUP_COLLECT_OPTIONAL, "name", &name,
                                        /* some hand-written introspection XML documents use this */
                                        G_MARKUP_COLLECT_STRING | G_MARKUP_COLLECT_OPTIONAL, "xmlns:doc", NULL,
                                        G_MARKUP_COLLECT_INVALID))
        goto out;

      g_dbus_node_info_set (data,
                            parse_data_get_node (data, TRUE),
                            name,
                            0, NULL,
                            0, NULL,
                            NULL);

      /* push the currently retrieved interfaces and nodes on the stack and prepare new arrays */
      data->interfaces_stack = g_slist_prepend (data->interfaces_stack, data->interfaces);
      data->interfaces = NULL;
      parse_data_steal_interfaces (data, NULL);

      data->nodes_stack = g_slist_prepend (data->nodes_stack, data->nodes);
      data->nodes = NULL;
      parse_data_steal_nodes (data, NULL);

    }
  /* ---------------------------------------------------------------------------------------------------- */
  else if (strcmp (element_name, "interface") == 0)
    {
      if (g_slist_length (stack) < 2 || strcmp (stack->next->data, "node") != 0)
        {
          g_set_error_literal (error,
                               G_MARKUP_ERROR,
                               G_MARKUP_ERROR_INVALID_CONTENT,
                               "<interface> elements can only be embedded in <node> elements");
          goto out;
        }

      if (!g_markup_collect_attributes (element_name,
                                        attribute_names,
                                        attribute_values,
                                        error,
                                        G_MARKUP_COLLECT_STRING, "name", &name,
                                        G_MARKUP_COLLECT_INVALID))
        goto out;

      g_dbus_interface_info_set (data,
                                 parse_data_get_interface (data, TRUE),
                                 name,
                                 0, NULL,
                                 0, NULL,
                                 0, NULL,
                                 NULL);

    }
  /* ---------------------------------------------------------------------------------------------------- */
  else if (strcmp (element_name, "method") == 0)
    {
      if (g_slist_length (stack) < 2 || strcmp (stack->next->data, "interface") != 0)
        {
          g_set_error_literal (error,
                               G_MARKUP_ERROR,
                               G_MARKUP_ERROR_INVALID_CONTENT,
                               "<method> elements can only be embedded in <interface> elements");
          goto out;
        }

      if (!g_markup_collect_attributes (element_name,
                                        attribute_names,
                                        attribute_values,
                                        error,
                                        G_MARKUP_COLLECT_STRING, "name", &name,
                                        G_MARKUP_COLLECT_INVALID))
        goto out;

      g_dbus_method_info_set (data,
                              parse_data_get_method (data, TRUE),
                              name,
                              0, NULL,
                              0, NULL,
                              NULL);

      data->num_args = 0;

    }
  /* ---------------------------------------------------------------------------------------------------- */
  else if (strcmp (element_name, "signal") == 0)
    {
      if (g_slist_length (stack) < 2 || strcmp (stack->next->data, "interface") != 0)
        {
          g_set_error_literal (error,
                               G_MARKUP_ERROR,
                               G_MARKUP_ERROR_INVALID_CONTENT,
                               "<signal> elements can only be embedded in <interface> elements");
          goto out;
        }

      if (!g_markup_collect_attributes (element_name,
                                        attribute_names,
                                        attribute_values,
                                        error,
                                        G_MARKUP_COLLECT_STRING, "name", &name,
                                        G_MARKUP_COLLECT_INVALID))
        goto out;

      g_dbus_signal_info_set (data,
                              parse_data_get_signal (data, TRUE),
                              name,
                              0, NULL,
                              NULL);

      data->num_args = 0;

    }
  /* ---------------------------------------------------------------------------------------------------- */
  else if (strcmp (element_name, "property") == 0)
    {
      GDBusPropertyInfoFlags flags;

      if (g_slist_length (stack) < 2 || strcmp (stack->next->data, "interface") != 0)
        {
          g_set_error_literal (error,
                               G_MARKUP_ERROR,
                               G_MARKUP_ERROR_INVALID_CONTENT,
                               "<property> elements can only be embedded in <interface> elements");
          goto out;
        }

      if (!g_markup_collect_attributes (element_name,
                                        attribute_names,
                                        attribute_values,
                                        error,
                                        G_MARKUP_COLLECT_STRING, "name", &name,
                                        G_MARKUP_COLLECT_STRING, "type", &type,
                                        G_MARKUP_COLLECT_STRING, "access", &access,
                                        G_MARKUP_COLLECT_INVALID))
        goto out;

      if (strcmp (access, "read") == 0)
        flags = G_DBUS_PROPERTY_INFO_FLAGS_READABLE;
      else if (strcmp (access, "write") == 0)
        flags = G_DBUS_PROPERTY_INFO_FLAGS_WRITABLE;
      else if (strcmp (access, "readwrite") == 0)
        flags = G_DBUS_PROPERTY_INFO_FLAGS_READABLE | G_DBUS_PROPERTY_INFO_FLAGS_WRITABLE;
      else
        {
          g_set_error (error,
                       G_MARKUP_ERROR,
                       G_MARKUP_ERROR_INVALID_CONTENT,
                       "Unknown value '%s' of access attribute for element <property>",
                       access);
          goto out;
        }

      g_dbus_property_info_set (data,
                                parse_data_get_property (data, TRUE),
                                name,
                                type,
                                flags,
                                NULL);

    }
  /* ---------------------------------------------------------------------------------------------------- */
  else if (strcmp (element_name, "arg") == 0)
    {
      gboolean is_in;
      gchar *name_to_use;

      if (g_slist_length (stack) < 2 ||
          (strcmp (stack->next->data, "method") != 0 &&
           strcmp (stack->next->data, "signal") != 0))
        {
          g_set_error_literal (error,
                               G_MARKUP_ERROR,
                               G_MARKUP_ERROR_INVALID_CONTENT,
                               "<arg> elements can only be embedded in <method> or <signal> elements");
          goto out;
        }

      if (!g_markup_collect_attributes (element_name,
                                        attribute_names,
                                        attribute_values,
                                        error,
                                        G_MARKUP_COLLECT_STRING | G_MARKUP_COLLECT_OPTIONAL, "name", &name,
                                        G_MARKUP_COLLECT_STRING | G_MARKUP_COLLECT_OPTIONAL, "direction", &direction,
                                        G_MARKUP_COLLECT_STRING, "type", &type,
                                        G_MARKUP_COLLECT_INVALID))
        goto out;

      if (strcmp (stack->next->data, "method") == 0)
        is_in = TRUE;
      else
        is_in = FALSE;
      if (direction != NULL)
        {
          if (strcmp (direction, "in") == 0)
            is_in = TRUE;
          else if (strcmp (direction, "out") == 0)
            is_in = FALSE;
          else
            {
              g_set_error (error,
                           G_MARKUP_ERROR,
                           G_MARKUP_ERROR_INVALID_CONTENT,
                           "Unknown value '%s' of direction attribute",
                           direction);
              goto out;
            }
        }

      if (is_in && strcmp (stack->next->data, "signal") == 0)
        {
          g_set_error_literal (error,
                               G_MARKUP_ERROR,
                               G_MARKUP_ERROR_INVALID_CONTENT,
                               "Only direction 'out' is allowed for <arg> elements embedded in <signal>");
          goto out;
        }

      if (name == NULL)
        name_to_use = g_strdup_printf ("arg_%d", data->num_args);
      else
        name_to_use = g_strdup (name);
      data->num_args++;

      if (is_in)
        {
          g_dbus_arg_info_set (data,
                               parse_data_get_arg (data, TRUE),
                               name_to_use,
                               type,
                               NULL);
          data->last_arg_was_in = TRUE;
        }
      else
        {
          g_dbus_arg_info_set (data,
                               parse_data_get_out_arg (data, TRUE),
                               name_to_use,
                               type,
                               NULL);
          data->last_arg_was_in = FALSE;

        }

      g_free (name_to_use);
    }
  /* ---------------------------------------------------------------------------------------------------- */
  else if (strcmp (element_name, "annotation") == 0)
    {
      if (g_slist_length (stack) < 2 ||
          (strcmp (stack->next->data, "node") != 0 &&
           strcmp (stack->next->data, "interface") != 0 &&
           strcmp (stack->next->data, "signal") != 0 &&
           strcmp (stack->next->data, "method") != 0 &&
           strcmp (stack->next->data, "property") != 0 &&
           strcmp (stack->next->data, "arg") != 0 &&
           strcmp (stack->next->data, "annotation") != 0))
        {
          g_set_error_literal (error,
                               G_MARKUP_ERROR,
                               G_MARKUP_ERROR_INVALID_CONTENT,
                               "<annotation> elements can only be embedded in <node>, <interface>, <signal>, <method>, <property>, <arg> or <annotation> elements");
          goto out;
        }

      if (!g_markup_collect_attributes (element_name,
                                        attribute_names,
                                        attribute_values,
                                        error,
                                        G_MARKUP_COLLECT_STRING, "name", &name,
                                        G_MARKUP_COLLECT_STRING, "value", &value,
                                        G_MARKUP_COLLECT_INVALID))
        goto out;

      g_dbus_annotation_info_set (data,
                                  parse_data_get_annotation (data, TRUE),
                                  name,
                                  value,
                                  NULL);
    }
  /* ---------------------------------------------------------------------------------------------------- */
  else
    {
      /* don't bail on unknown elements; just ignore them */
    }
  /* ---------------------------------------------------------------------------------------------------- */

  /* push the currently retrieved annotations on the stack and prepare a new one */
  data->annotations_stack = g_slist_prepend (data->annotations_stack, data->annotations);
  data->annotations = NULL;
  parse_data_steal_annotations (data, NULL);

 out:
  ;
}

/* ---------------------------------------------------------------------------------------------------- */

static GDBusAnnotationInfo **
steal_annotations (ParseData *data)
{
  return parse_data_steal_annotations (data, NULL);
}


static void
parser_end_element (GMarkupParseContext  *context,
                    const gchar          *element_name,
                    gpointer              user_data,
                    GError              **error)
{
  ParseData *data = user_data;
  gboolean have_popped_annotations;

  have_popped_annotations = FALSE;

  if (strcmp (element_name, "node") == 0)
    {
      guint num_nodes;
      guint num_interfaces;
      GDBusNodeInfo **nodes;
      GDBusInterfaceInfo **interfaces;

      nodes = parse_data_steal_nodes (data, &num_nodes);
      interfaces = parse_data_steal_interfaces (data, &num_interfaces);

      /* destroy the nodes, interfaces for scope we're exiting and and pop the nodes, interfaces from the
       * scope we're reentering
       */
      parse_data_free_interfaces (data);
      data->interfaces = (GPtrArray *) data->interfaces_stack->data;
      data->interfaces_stack = g_slist_remove (data->interfaces_stack, data->interfaces_stack->data);

      parse_data_free_nodes (data);
      data->nodes = (GPtrArray *) data->nodes_stack->data;
      data->nodes_stack = g_slist_remove (data->nodes_stack, data->nodes_stack->data);

      g_dbus_node_info_set (data,
                            parse_data_get_node (data, FALSE),
                            NULL,
                            num_interfaces,
                            interfaces,
                            num_nodes,
                            nodes,
                            steal_annotations (data));

    }
  else if (strcmp (element_name, "interface") == 0)
    {
      guint num_methods;
      guint num_signals;
      guint num_properties;
      GDBusMethodInfo **methods;
      GDBusSignalInfo **signals;
      GDBusPropertyInfo **properties;

      methods    = parse_data_steal_methods    (data, &num_methods);
      signals    = parse_data_steal_signals    (data, &num_signals);
      properties = parse_data_steal_properties (data, &num_properties);

      g_dbus_interface_info_set (data,
                                 parse_data_get_interface (data, FALSE),
                                 NULL,
                                 num_methods,
                                 methods,
                                 num_signals,
                                 signals,
                                 num_properties,
                                 properties,
                                 steal_annotations (data));

    }
  else if (strcmp (element_name, "method") == 0)
    {
      guint in_num_args;
      guint out_num_args;
      GDBusArgInfo **in_args;
      GDBusArgInfo **out_args;

      in_args  = parse_data_steal_args     (data, &in_num_args);
      out_args = parse_data_steal_out_args (data, &out_num_args);

      g_dbus_method_info_set (data,
                              parse_data_get_method (data, FALSE),
                              NULL,
                              in_num_args,
                              in_args,
                              out_num_args,
                              out_args,
                              steal_annotations (data));
    }
  else if (strcmp (element_name, "signal") == 0)
    {
      guint num_args;
      GDBusArgInfo **args;

      args = parse_data_steal_out_args (data, &num_args);

      g_dbus_signal_info_set (data,
                              parse_data_get_signal (data, FALSE),
                              NULL,
                              num_args,
                              args,
                              steal_annotations (data));
    }
  else if (strcmp (element_name, "property") == 0)
    {
      g_dbus_property_info_set (data,
                                parse_data_get_property (data, FALSE),
                                NULL,
                                NULL,
                                G_DBUS_PROPERTY_INFO_FLAGS_NONE,
                                steal_annotations (data));
    }
  else if (strcmp (element_name, "arg") == 0)
    {
      g_dbus_arg_info_set (data,
                           data->last_arg_was_in ? parse_data_get_arg (data, FALSE) : parse_data_get_out_arg (data, FALSE),
                           NULL,
                           NULL,
                           steal_annotations (data));
    }
  else if (strcmp (element_name, "annotation") == 0)
    {
      GDBusAnnotationInfo **embedded_annotations;

      embedded_annotations = steal_annotations (data);

      /* destroy the annotations for scope we're exiting and and pop the annotations from the scope we're reentering */
      parse_data_free_annotations (data);
      data->annotations = (GPtrArray *) data->annotations_stack->data;
      data->annotations_stack = g_slist_remove (data->annotations_stack, data->annotations_stack->data);

      have_popped_annotations = TRUE;

      g_dbus_annotation_info_set (data,
                                  parse_data_get_annotation (data, FALSE),
                                  NULL,
                                  NULL,
                                  embedded_annotations);
    }
  else
    {
      /* don't bail on unknown elements; just ignore them */
    }

  if (!have_popped_annotations)
    {
      /* destroy the annotations for scope we're exiting and and pop the annotations from the scope we're reentering */
      parse_data_free_annotations (data);
      data->annotations = (GPtrArray *) data->annotations_stack->data;
      data->annotations_stack = g_slist_remove (data->annotations_stack, data->annotations_stack->data);
    }
}

/* ---------------------------------------------------------------------------------------------------- */

static void
parser_error (GMarkupParseContext *context,
              GError              *error,
              gpointer             user_data)
{
  gint line_number;
  gint char_number;

  g_markup_parse_context_get_position (context, &line_number, &char_number);

  g_prefix_error (&error, "%d:%d: ",
                  line_number,
                  char_number);
}

/* ---------------------------------------------------------------------------------------------------- */

/**
 * g_dbus_node_info_new_for_xml:
 * @xml_data: Valid D-Bus introspection XML.
 * @error: Return location for error.
 *
 * Parses @xml_data and returns a #GDBusNodeInfo representing the data.
 *
 * Returns: A #GDBusNodeInfo structure or %NULL if @error is set. Free
 * with g_dbus_node_info_unref().
 *
 * Since: 2.26
 */
GDBusNodeInfo *
g_dbus_node_info_new_for_xml (const gchar  *xml_data,
                              GError      **error)
{
  GDBusNodeInfo *ret;
  GMarkupParseContext *context;
  GMarkupParser *parser;
  guint num_nodes;
  ParseData *data;
  GDBusNodeInfo **ughret;

  ret = NULL;
  parser = NULL;
  context = NULL;

  parser = g_new0 (GMarkupParser, 1);
  parser->start_element = parser_start_element;
  parser->end_element   = parser_end_element;
  parser->error         = parser_error;

  data = parse_data_new ();
  context = g_markup_parse_context_new (parser,
                                        0,
                                        data,
                                        (GDestroyNotify) parse_data_free);

  if (!g_markup_parse_context_parse (context,
                                     xml_data,
                                     strlen (xml_data),
                                     error))
    goto out;

  ughret = parse_data_steal_nodes (data, &num_nodes);

  if (num_nodes != 1)
    {
      guint n;

      g_set_error (error,
                   G_MARKUP_ERROR,
                   G_MARKUP_ERROR_INVALID_CONTENT,
                   "Expected a single node in introspection XML, found %d",
                   num_nodes);

      /* clean up */
      for (n = 0; n < num_nodes; n++)
        {
          for (n = 0; n < num_nodes; n++)
            g_dbus_node_info_unref (&(ret[n]));
        }
      g_free (ret);
      ret = NULL;
    }

  ret = ughret[0];
  g_free (ughret);

 out:
  if (parser != NULL)
    g_free (parser);
  if (context != NULL)
    g_markup_parse_context_free (context);

  return ret;
}

/* ---------------------------------------------------------------------------------------------------- */

/**
 * g_dbus_annotation_info_lookup:
 * @annotations: A %NULL-terminated array of annotations or %NULL.
 * @name: The name of the annotation to look up.
 *
 * Looks up the value of an annotation.
 *
 * This cost of this function is O(n) in number of annotations.
 *
 * Returns: The value or %NULL if not found. Do not free, it is owned by @annotations.
 *
 * Since: 2.26
 */
const gchar *
g_dbus_annotation_info_lookup (GDBusAnnotationInfo **annotations,
                               const gchar          *name)
{
  guint n;
  const gchar *ret;

  ret = NULL;
  for (n = 0; annotations != NULL && annotations[n] != NULL; n++)
    {
      if (g_strcmp0 (annotations[n]->key, name) == 0)
        {
          ret = annotations[n]->value;
          goto out;
        }
    }

 out:
  return ret;
}

/* ---------------------------------------------------------------------------------------------------- */

/**
 * g_dbus_interface_info_lookup_method:
 * @info: A #GDBusInterfaceInfo.
 * @name: A D-Bus method name (typically in CamelCase)
 *
 * Looks up information about a method.
 *
 * This cost of this function is O(n) in number of methods.
 *
 * Returns: A #GDBusMethodInfo or %NULL if not found. Do not free, it is owned by @info.
 *
 * Since: 2.26
 */
GDBusMethodInfo *
g_dbus_interface_info_lookup_method (GDBusInterfaceInfo *info,
                                     const gchar        *name)
{
  guint n;
  GDBusMethodInfo *result;

  for (n = 0; info->methods != NULL && info->methods[n] != NULL; n++)
    {
      GDBusMethodInfo *i = info->methods[n];

      if (g_strcmp0 (i->name, name) == 0)
        {
          result = i;
          goto out;
        }
    }

  result = NULL;

 out:
  return result;
}

/* ---------------------------------------------------------------------------------------------------- */

/**
 * g_dbus_interface_info_lookup_signal:
 * @info: A #GDBusInterfaceInfo.
 * @name: A D-Bus signal name (typically in CamelCase)
 *
 * Looks up information about a signal.
 *
 * This cost of this function is O(n) in number of signals.
 *
 * Returns: A #GDBusSignalInfo or %NULL if not found. Do not free, it is owned by @info.
 *
 * Since: 2.26
 */
GDBusSignalInfo *
g_dbus_interface_info_lookup_signal (GDBusInterfaceInfo *info,
                                     const gchar        *name)
{
  guint n;
  GDBusSignalInfo *result;

  for (n = 0; info->signals != NULL && info->signals[n] != NULL; n++)
    {
      GDBusSignalInfo *i = info->signals[n];

      if (g_strcmp0 (i->name, name) == 0)
        {
          result = i;
          goto out;
        }
    }

  result = NULL;

 out:
  return result;
}

/* ---------------------------------------------------------------------------------------------------- */

/**
 * g_dbus_interface_info_lookup_property:
 * @info: A #GDBusInterfaceInfo.
 * @name: A D-Bus property name (typically in CamelCase).
 *
 * Looks up information about a property.
 *
 * This cost of this function is O(n) in number of properties.
 *
 * Returns: A #GDBusPropertyInfo or %NULL if not found. Do not free, it is owned by @info.
 *
 * Since: 2.26
 */
GDBusPropertyInfo *
g_dbus_interface_info_lookup_property (GDBusInterfaceInfo *info,
                                       const gchar        *name)
{
  guint n;
  GDBusPropertyInfo *result;

  for (n = 0; info->properties != NULL && info->properties[n] != NULL; n++)
    {
      GDBusPropertyInfo *i = info->properties[n];

      if (g_strcmp0 (i->name, name) == 0)
        {
          result = i;
          goto out;
        }
    }

  result = NULL;

 out:
  return result;
}

/* ---------------------------------------------------------------------------------------------------- */

/**
 * g_dbus_node_info_lookup_interface:
 * @info: A #GDBusNodeInfo.
 * @name: A D-Bus interface name.
 *
 * Looks up information about an interface.
 *
 * This cost of this function is O(n) in number of interfaces.
 *
 * Returns: A #GDBusInterfaceInfo or %NULL if not found. Do not free, it is owned by @info.
 *
 * Since: 2.26
 */
GDBusInterfaceInfo *
g_dbus_node_info_lookup_interface (GDBusNodeInfo *info,
                                   const gchar   *name)
{
  guint n;
  GDBusInterfaceInfo *result;

  for (n = 0; info->interfaces != NULL && info->interfaces[n] != NULL; n++)
    {
      GDBusInterfaceInfo *i = info->interfaces[n];

      if (g_strcmp0 (i->name, name) == 0)
        {
          result = i;
          goto out;
        }
    }

  result = NULL;

 out:
  return result;
}
