/*
 * Generated by gdbus-codegen 2.40.2. DO NOT EDIT.
 *
 * The license of this code is the same as for the source it was derived from.
 */

#ifdef HAVE_CONFIG_H
#  include "config.h"
#endif

#include "interfaces/led.h"

#include <string.h>
#ifdef G_OS_UNIX
#  include <gio/gunixfdlist.h>
#endif

typedef struct
{
  GDBusArgInfo parent_struct;
  gboolean use_gvariant;
} _ExtendedGDBusArgInfo;

typedef struct
{
  GDBusMethodInfo parent_struct;
  const gchar *signal_name;
  gboolean pass_fdlist;
} _ExtendedGDBusMethodInfo;

typedef struct
{
  GDBusSignalInfo parent_struct;
  const gchar *signal_name;
} _ExtendedGDBusSignalInfo;

typedef struct
{
  GDBusPropertyInfo parent_struct;
  const gchar *hyphen_name;
  gboolean use_gvariant;
} _ExtendedGDBusPropertyInfo;

typedef struct
{
  GDBusInterfaceInfo parent_struct;
  const gchar *hyphen_name;
} _ExtendedGDBusInterfaceInfo;

typedef struct
{
  const _ExtendedGDBusPropertyInfo *info;
  guint prop_id;
  GValue orig_value; /* the value before the change */
} ChangedProperty;

static void
_changed_property_free (ChangedProperty *data)
{
  g_value_unset (&data->orig_value);
  g_free (data);
}

static gboolean
_g_strv_equal0 (gchar **a, gchar **b)
{
  gboolean ret = FALSE;
  guint n;
  if (a == NULL && b == NULL)
    {
      ret = TRUE;
      goto out;
    }
  if (a == NULL || b == NULL)
    goto out;
  if (g_strv_length (a) != g_strv_length (b))
    goto out;
  for (n = 0; a[n] != NULL; n++)
    if (g_strcmp0 (a[n], b[n]) != 0)
      goto out;
  ret = TRUE;
out:
  return ret;
}

static gboolean
_g_variant_equal0 (GVariant *a, GVariant *b)
{
  gboolean ret = FALSE;
  if (a == NULL && b == NULL)
    {
      ret = TRUE;
      goto out;
    }
  if (a == NULL || b == NULL)
    goto out;
  ret = g_variant_equal (a, b);
out:
  return ret;
}

G_GNUC_UNUSED static gboolean
_g_value_equal (const GValue *a, const GValue *b)
{
  gboolean ret = FALSE;
  g_assert (G_VALUE_TYPE (a) == G_VALUE_TYPE (b));
  switch (G_VALUE_TYPE (a))
    {
      case G_TYPE_BOOLEAN:
        ret = (g_value_get_boolean (a) == g_value_get_boolean (b));
        break;
      case G_TYPE_UCHAR:
        ret = (g_value_get_uchar (a) == g_value_get_uchar (b));
        break;
      case G_TYPE_INT:
        ret = (g_value_get_int (a) == g_value_get_int (b));
        break;
      case G_TYPE_UINT:
        ret = (g_value_get_uint (a) == g_value_get_uint (b));
        break;
      case G_TYPE_INT64:
        ret = (g_value_get_int64 (a) == g_value_get_int64 (b));
        break;
      case G_TYPE_UINT64:
        ret = (g_value_get_uint64 (a) == g_value_get_uint64 (b));
        break;
      case G_TYPE_DOUBLE:
        {
          /* Avoid -Wfloat-equal warnings by doing a direct bit compare */
          gdouble da = g_value_get_double (a);
          gdouble db = g_value_get_double (b);
          ret = memcmp (&da, &db, sizeof (gdouble)) == 0;
        }
        break;
      case G_TYPE_STRING:
        ret = (g_strcmp0 (g_value_get_string (a), g_value_get_string (b)) == 0);
        break;
      case G_TYPE_VARIANT:
        ret = _g_variant_equal0 (g_value_get_variant (a), g_value_get_variant (b));
        break;
      default:
        if (G_VALUE_TYPE (a) == G_TYPE_STRV)
          ret = _g_strv_equal0 (g_value_get_boxed (a), g_value_get_boxed (b));
        else
          g_critical ("_g_value_equal() does not handle type %s", g_type_name (G_VALUE_TYPE (a)));
        break;
    }
  return ret;
}

/* ------------------------------------------------------------------------
 * Code for interface org.openbmc.Led
 * ------------------------------------------------------------------------
 */

/**
 * SECTION:Led
 * @title: Led
 * @short_description: Generated C code for the org.openbmc.Led D-Bus interface
 *
 * This section contains code for working with the <link linkend="gdbus-interface-org-openbmc-Led.top_of_page">org.openbmc.Led</link> D-Bus interface in C.
 */

/* ---- Introspection data for org.openbmc.Led ---- */

static const _ExtendedGDBusMethodInfo _led_method_info_set_on =
{
  {
    -1,
    (gchar *) "setOn",
    NULL,
    NULL,
    NULL
  },
  "handle-set-on",
  FALSE
};

static const _ExtendedGDBusMethodInfo _led_method_info_set_off =
{
  {
    -1,
    (gchar *) "setOff",
    NULL,
    NULL,
    NULL
  },
  "handle-set-off",
  FALSE
};

static const _ExtendedGDBusMethodInfo _led_method_info_set_blink_slow =
{
  {
    -1,
    (gchar *) "setBlinkSlow",
    NULL,
    NULL,
    NULL
  },
  "handle-set-blink-slow",
  FALSE
};

static const _ExtendedGDBusMethodInfo _led_method_info_set_blink_fast =
{
  {
    -1,
    (gchar *) "setBlinkFast",
    NULL,
    NULL,
    NULL
  },
  "handle-set-blink-fast",
  FALSE
};

static const _ExtendedGDBusMethodInfo * const _led_method_info_pointers[] =
{
  &_led_method_info_set_on,
  &_led_method_info_set_off,
  &_led_method_info_set_blink_slow,
  &_led_method_info_set_blink_fast,
  NULL
};

static const _ExtendedGDBusPropertyInfo _led_property_info_color =
{
  {
    -1,
    (gchar *) "color",
    (gchar *) "i",
    G_DBUS_PROPERTY_INFO_FLAGS_READABLE,
    NULL
  },
  "color",
  FALSE
};

static const _ExtendedGDBusPropertyInfo _led_property_info_function =
{
  {
    -1,
    (gchar *) "function",
    (gchar *) "s",
    G_DBUS_PROPERTY_INFO_FLAGS_READABLE,
    NULL
  },
  "function",
  FALSE
};

static const _ExtendedGDBusPropertyInfo * const _led_property_info_pointers[] =
{
  &_led_property_info_color,
  &_led_property_info_function,
  NULL
};

static const _ExtendedGDBusInterfaceInfo _led_interface_info =
{
  {
    -1,
    (gchar *) "org.openbmc.Led",
    (GDBusMethodInfo **) &_led_method_info_pointers,
    NULL,
    (GDBusPropertyInfo **) &_led_property_info_pointers,
    NULL
  },
  "led",
};


/**
 * led_interface_info:
 *
 * Gets a machine-readable description of the <link linkend="gdbus-interface-org-openbmc-Led.top_of_page">org.openbmc.Led</link> D-Bus interface.
 *
 * Returns: (transfer none): A #GDBusInterfaceInfo. Do not free.
 */
GDBusInterfaceInfo *
led_interface_info (void)
{
  return (GDBusInterfaceInfo *) &_led_interface_info.parent_struct;
}

/**
 * led_override_properties:
 * @klass: The class structure for a #GObject<!-- -->-derived class.
 * @property_id_begin: The property id to assign to the first overridden property.
 *
 * Overrides all #GObject properties in the #Led interface for a concrete class.
 * The properties are overridden in the order they are defined.
 *
 * Returns: The last property id.
 */
guint
led_override_properties (GObjectClass *klass, guint property_id_begin)
{
  g_object_class_override_property (klass, property_id_begin++, "color");
  g_object_class_override_property (klass, property_id_begin++, "function");
  return property_id_begin - 1;
}



/**
 * Led:
 *
 * Abstract interface type for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-Led.top_of_page">org.openbmc.Led</link>.
 */

/**
 * LedIface:
 * @parent_iface: The parent interface.
 * @handle_set_blink_fast: Handler for the #Led::handle-set-blink-fast signal.
 * @handle_set_blink_slow: Handler for the #Led::handle-set-blink-slow signal.
 * @handle_set_off: Handler for the #Led::handle-set-off signal.
 * @handle_set_on: Handler for the #Led::handle-set-on signal.
 * @get_color: Getter for the #Led:color property.
 * @get_function: Getter for the #Led:function property.
 *
 * Virtual table for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-Led.top_of_page">org.openbmc.Led</link>.
 */

typedef LedIface LedInterface;
G_DEFINE_INTERFACE (Led, led, G_TYPE_OBJECT);

static void
led_default_init (LedIface *iface)
{
  /* GObject signals for incoming D-Bus method calls: */
  /**
   * Led::handle-set-on:
   * @object: A #Led.
   * @invocation: A #GDBusMethodInvocation.
   *
   * Signal emitted when a remote caller is invoking the <link linkend="gdbus-method-org-openbmc-Led.setOn">setOn()</link> D-Bus method.
   *
   * If a signal handler returns %TRUE, it means the signal handler will handle the invocation (e.g. take a reference to @invocation and eventually call led_complete_set_on() or e.g. g_dbus_method_invocation_return_error() on it) and no order signal handlers will run. If no signal handler handles the invocation, the %G_DBUS_ERROR_UNKNOWN_METHOD error is returned.
   *
   * Returns: %TRUE if the invocation was handled, %FALSE to let other signal handlers run.
   */
  g_signal_new ("handle-set-on",
    G_TYPE_FROM_INTERFACE (iface),
    G_SIGNAL_RUN_LAST,
    G_STRUCT_OFFSET (LedIface, handle_set_on),
    g_signal_accumulator_true_handled,
    NULL,
    g_cclosure_marshal_generic,
    G_TYPE_BOOLEAN,
    1,
    G_TYPE_DBUS_METHOD_INVOCATION);

  /**
   * Led::handle-set-off:
   * @object: A #Led.
   * @invocation: A #GDBusMethodInvocation.
   *
   * Signal emitted when a remote caller is invoking the <link linkend="gdbus-method-org-openbmc-Led.setOff">setOff()</link> D-Bus method.
   *
   * If a signal handler returns %TRUE, it means the signal handler will handle the invocation (e.g. take a reference to @invocation and eventually call led_complete_set_off() or e.g. g_dbus_method_invocation_return_error() on it) and no order signal handlers will run. If no signal handler handles the invocation, the %G_DBUS_ERROR_UNKNOWN_METHOD error is returned.
   *
   * Returns: %TRUE if the invocation was handled, %FALSE to let other signal handlers run.
   */
  g_signal_new ("handle-set-off",
    G_TYPE_FROM_INTERFACE (iface),
    G_SIGNAL_RUN_LAST,
    G_STRUCT_OFFSET (LedIface, handle_set_off),
    g_signal_accumulator_true_handled,
    NULL,
    g_cclosure_marshal_generic,
    G_TYPE_BOOLEAN,
    1,
    G_TYPE_DBUS_METHOD_INVOCATION);

  /**
   * Led::handle-set-blink-slow:
   * @object: A #Led.
   * @invocation: A #GDBusMethodInvocation.
   *
   * Signal emitted when a remote caller is invoking the <link linkend="gdbus-method-org-openbmc-Led.setBlinkSlow">setBlinkSlow()</link> D-Bus method.
   *
   * If a signal handler returns %TRUE, it means the signal handler will handle the invocation (e.g. take a reference to @invocation and eventually call led_complete_set_blink_slow() or e.g. g_dbus_method_invocation_return_error() on it) and no order signal handlers will run. If no signal handler handles the invocation, the %G_DBUS_ERROR_UNKNOWN_METHOD error is returned.
   *
   * Returns: %TRUE if the invocation was handled, %FALSE to let other signal handlers run.
   */
  g_signal_new ("handle-set-blink-slow",
    G_TYPE_FROM_INTERFACE (iface),
    G_SIGNAL_RUN_LAST,
    G_STRUCT_OFFSET (LedIface, handle_set_blink_slow),
    g_signal_accumulator_true_handled,
    NULL,
    g_cclosure_marshal_generic,
    G_TYPE_BOOLEAN,
    1,
    G_TYPE_DBUS_METHOD_INVOCATION);

  /**
   * Led::handle-set-blink-fast:
   * @object: A #Led.
   * @invocation: A #GDBusMethodInvocation.
   *
   * Signal emitted when a remote caller is invoking the <link linkend="gdbus-method-org-openbmc-Led.setBlinkFast">setBlinkFast()</link> D-Bus method.
   *
   * If a signal handler returns %TRUE, it means the signal handler will handle the invocation (e.g. take a reference to @invocation and eventually call led_complete_set_blink_fast() or e.g. g_dbus_method_invocation_return_error() on it) and no order signal handlers will run. If no signal handler handles the invocation, the %G_DBUS_ERROR_UNKNOWN_METHOD error is returned.
   *
   * Returns: %TRUE if the invocation was handled, %FALSE to let other signal handlers run.
   */
  g_signal_new ("handle-set-blink-fast",
    G_TYPE_FROM_INTERFACE (iface),
    G_SIGNAL_RUN_LAST,
    G_STRUCT_OFFSET (LedIface, handle_set_blink_fast),
    g_signal_accumulator_true_handled,
    NULL,
    g_cclosure_marshal_generic,
    G_TYPE_BOOLEAN,
    1,
    G_TYPE_DBUS_METHOD_INVOCATION);

  /* GObject properties for D-Bus properties: */
  /**
   * Led:color:
   *
   * Represents the D-Bus property <link linkend="gdbus-property-org-openbmc-Led.color">"color"</link>.
   *
   * Since the D-Bus property for this #GObject property is readable but not writable, it is meaningful to read from it on both the client- and service-side. It is only meaningful, however, to write to it on the service-side.
   */
  g_object_interface_install_property (iface,
    g_param_spec_int ("color", "color", "color", G_MININT32, G_MAXINT32, 0, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  /**
   * Led:function:
   *
   * Represents the D-Bus property <link linkend="gdbus-property-org-openbmc-Led.function">"function"</link>.
   *
   * Since the D-Bus property for this #GObject property is readable but not writable, it is meaningful to read from it on both the client- and service-side. It is only meaningful, however, to write to it on the service-side.
   */
  g_object_interface_install_property (iface,
    g_param_spec_string ("function", "function", "function", NULL, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
}

/**
 * led_get_color: (skip)
 * @object: A #Led.
 *
 * Gets the value of the <link linkend="gdbus-property-org-openbmc-Led.color">"color"</link> D-Bus property.
 *
 * Since this D-Bus property is readable, it is meaningful to use this function on both the client- and service-side.
 *
 * Returns: The property value.
 */
gint 
led_get_color (Led *object)
{
  return LED_GET_IFACE (object)->get_color (object);
}

/**
 * led_set_color: (skip)
 * @object: A #Led.
 * @value: The value to set.
 *
 * Sets the <link linkend="gdbus-property-org-openbmc-Led.color">"color"</link> D-Bus property to @value.
 *
 * Since this D-Bus property is not writable, it is only meaningful to use this function on the service-side.
 */
void
led_set_color (Led *object, gint value)
{
  g_object_set (G_OBJECT (object), "color", value, NULL);
}

/**
 * led_get_function: (skip)
 * @object: A #Led.
 *
 * Gets the value of the <link linkend="gdbus-property-org-openbmc-Led.function">"function"</link> D-Bus property.
 *
 * Since this D-Bus property is readable, it is meaningful to use this function on both the client- and service-side.
 *
 * <warning>The returned value is only valid until the property changes so on the client-side it is only safe to use this function on the thread where @object was constructed. Use led_dup_function() if on another thread.</warning>
 *
 * Returns: (transfer none): The property value or %NULL if the property is not set. Do not free the returned value, it belongs to @object.
 */
const gchar *
led_get_function (Led *object)
{
  return LED_GET_IFACE (object)->get_function (object);
}

/**
 * led_dup_function: (skip)
 * @object: A #Led.
 *
 * Gets a copy of the <link linkend="gdbus-property-org-openbmc-Led.function">"function"</link> D-Bus property.
 *
 * Since this D-Bus property is readable, it is meaningful to use this function on both the client- and service-side.
 *
 * Returns: (transfer full): The property value or %NULL if the property is not set. The returned value should be freed with g_free().
 */
gchar *
led_dup_function (Led *object)
{
  gchar *value;
  g_object_get (G_OBJECT (object), "function", &value, NULL);
  return value;
}

/**
 * led_set_function: (skip)
 * @object: A #Led.
 * @value: The value to set.
 *
 * Sets the <link linkend="gdbus-property-org-openbmc-Led.function">"function"</link> D-Bus property to @value.
 *
 * Since this D-Bus property is not writable, it is only meaningful to use this function on the service-side.
 */
void
led_set_function (Led *object, const gchar *value)
{
  g_object_set (G_OBJECT (object), "function", value, NULL);
}

/**
 * led_call_set_on:
 * @proxy: A #LedProxy.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @callback: A #GAsyncReadyCallback to call when the request is satisfied or %NULL.
 * @user_data: User data to pass to @callback.
 *
 * Asynchronously invokes the <link linkend="gdbus-method-org-openbmc-Led.setOn">setOn()</link> D-Bus method on @proxy.
 * When the operation is finished, @callback will be invoked in the <link linkend="g-main-context-push-thread-default">thread-default main loop</link> of the thread you are calling this method from.
 * You can then call led_call_set_on_finish() to get the result of the operation.
 *
 * See led_call_set_on_sync() for the synchronous, blocking version of this method.
 */
void
led_call_set_on (
    Led *proxy,
    GCancellable *cancellable,
    GAsyncReadyCallback callback,
    gpointer user_data)
{
  g_dbus_proxy_call (G_DBUS_PROXY (proxy),
    "setOn",
    g_variant_new ("()"),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    callback,
    user_data);
}

/**
 * led_call_set_on_finish:
 * @proxy: A #LedProxy.
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to led_call_set_on().
 * @error: Return location for error or %NULL.
 *
 * Finishes an operation started with led_call_set_on().
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
led_call_set_on_finish (
    Led *proxy,
    GAsyncResult *res,
    GError **error)
{
  GVariant *_ret;
  _ret = g_dbus_proxy_call_finish (G_DBUS_PROXY (proxy), res, error);
  if (_ret == NULL)
    goto _out;
  g_variant_get (_ret,
                 "()");
  g_variant_unref (_ret);
_out:
  return _ret != NULL;
}

/**
 * led_call_set_on_sync:
 * @proxy: A #LedProxy.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @error: Return location for error or %NULL.
 *
 * Synchronously invokes the <link linkend="gdbus-method-org-openbmc-Led.setOn">setOn()</link> D-Bus method on @proxy. The calling thread is blocked until a reply is received.
 *
 * See led_call_set_on() for the asynchronous version of this method.
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
led_call_set_on_sync (
    Led *proxy,
    GCancellable *cancellable,
    GError **error)
{
  GVariant *_ret;
  _ret = g_dbus_proxy_call_sync (G_DBUS_PROXY (proxy),
    "setOn",
    g_variant_new ("()"),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    error);
  if (_ret == NULL)
    goto _out;
  g_variant_get (_ret,
                 "()");
  g_variant_unref (_ret);
_out:
  return _ret != NULL;
}

/**
 * led_call_set_off:
 * @proxy: A #LedProxy.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @callback: A #GAsyncReadyCallback to call when the request is satisfied or %NULL.
 * @user_data: User data to pass to @callback.
 *
 * Asynchronously invokes the <link linkend="gdbus-method-org-openbmc-Led.setOff">setOff()</link> D-Bus method on @proxy.
 * When the operation is finished, @callback will be invoked in the <link linkend="g-main-context-push-thread-default">thread-default main loop</link> of the thread you are calling this method from.
 * You can then call led_call_set_off_finish() to get the result of the operation.
 *
 * See led_call_set_off_sync() for the synchronous, blocking version of this method.
 */
void
led_call_set_off (
    Led *proxy,
    GCancellable *cancellable,
    GAsyncReadyCallback callback,
    gpointer user_data)
{
  g_dbus_proxy_call (G_DBUS_PROXY (proxy),
    "setOff",
    g_variant_new ("()"),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    callback,
    user_data);
}

/**
 * led_call_set_off_finish:
 * @proxy: A #LedProxy.
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to led_call_set_off().
 * @error: Return location for error or %NULL.
 *
 * Finishes an operation started with led_call_set_off().
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
led_call_set_off_finish (
    Led *proxy,
    GAsyncResult *res,
    GError **error)
{
  GVariant *_ret;
  _ret = g_dbus_proxy_call_finish (G_DBUS_PROXY (proxy), res, error);
  if (_ret == NULL)
    goto _out;
  g_variant_get (_ret,
                 "()");
  g_variant_unref (_ret);
_out:
  return _ret != NULL;
}

/**
 * led_call_set_off_sync:
 * @proxy: A #LedProxy.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @error: Return location for error or %NULL.
 *
 * Synchronously invokes the <link linkend="gdbus-method-org-openbmc-Led.setOff">setOff()</link> D-Bus method on @proxy. The calling thread is blocked until a reply is received.
 *
 * See led_call_set_off() for the asynchronous version of this method.
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
led_call_set_off_sync (
    Led *proxy,
    GCancellable *cancellable,
    GError **error)
{
  GVariant *_ret;
  _ret = g_dbus_proxy_call_sync (G_DBUS_PROXY (proxy),
    "setOff",
    g_variant_new ("()"),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    error);
  if (_ret == NULL)
    goto _out;
  g_variant_get (_ret,
                 "()");
  g_variant_unref (_ret);
_out:
  return _ret != NULL;
}

/**
 * led_call_set_blink_slow:
 * @proxy: A #LedProxy.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @callback: A #GAsyncReadyCallback to call when the request is satisfied or %NULL.
 * @user_data: User data to pass to @callback.
 *
 * Asynchronously invokes the <link linkend="gdbus-method-org-openbmc-Led.setBlinkSlow">setBlinkSlow()</link> D-Bus method on @proxy.
 * When the operation is finished, @callback will be invoked in the <link linkend="g-main-context-push-thread-default">thread-default main loop</link> of the thread you are calling this method from.
 * You can then call led_call_set_blink_slow_finish() to get the result of the operation.
 *
 * See led_call_set_blink_slow_sync() for the synchronous, blocking version of this method.
 */
void
led_call_set_blink_slow (
    Led *proxy,
    GCancellable *cancellable,
    GAsyncReadyCallback callback,
    gpointer user_data)
{
  g_dbus_proxy_call (G_DBUS_PROXY (proxy),
    "setBlinkSlow",
    g_variant_new ("()"),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    callback,
    user_data);
}

/**
 * led_call_set_blink_slow_finish:
 * @proxy: A #LedProxy.
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to led_call_set_blink_slow().
 * @error: Return location for error or %NULL.
 *
 * Finishes an operation started with led_call_set_blink_slow().
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
led_call_set_blink_slow_finish (
    Led *proxy,
    GAsyncResult *res,
    GError **error)
{
  GVariant *_ret;
  _ret = g_dbus_proxy_call_finish (G_DBUS_PROXY (proxy), res, error);
  if (_ret == NULL)
    goto _out;
  g_variant_get (_ret,
                 "()");
  g_variant_unref (_ret);
_out:
  return _ret != NULL;
}

/**
 * led_call_set_blink_slow_sync:
 * @proxy: A #LedProxy.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @error: Return location for error or %NULL.
 *
 * Synchronously invokes the <link linkend="gdbus-method-org-openbmc-Led.setBlinkSlow">setBlinkSlow()</link> D-Bus method on @proxy. The calling thread is blocked until a reply is received.
 *
 * See led_call_set_blink_slow() for the asynchronous version of this method.
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
led_call_set_blink_slow_sync (
    Led *proxy,
    GCancellable *cancellable,
    GError **error)
{
  GVariant *_ret;
  _ret = g_dbus_proxy_call_sync (G_DBUS_PROXY (proxy),
    "setBlinkSlow",
    g_variant_new ("()"),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    error);
  if (_ret == NULL)
    goto _out;
  g_variant_get (_ret,
                 "()");
  g_variant_unref (_ret);
_out:
  return _ret != NULL;
}

/**
 * led_call_set_blink_fast:
 * @proxy: A #LedProxy.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @callback: A #GAsyncReadyCallback to call when the request is satisfied or %NULL.
 * @user_data: User data to pass to @callback.
 *
 * Asynchronously invokes the <link linkend="gdbus-method-org-openbmc-Led.setBlinkFast">setBlinkFast()</link> D-Bus method on @proxy.
 * When the operation is finished, @callback will be invoked in the <link linkend="g-main-context-push-thread-default">thread-default main loop</link> of the thread you are calling this method from.
 * You can then call led_call_set_blink_fast_finish() to get the result of the operation.
 *
 * See led_call_set_blink_fast_sync() for the synchronous, blocking version of this method.
 */
void
led_call_set_blink_fast (
    Led *proxy,
    GCancellable *cancellable,
    GAsyncReadyCallback callback,
    gpointer user_data)
{
  g_dbus_proxy_call (G_DBUS_PROXY (proxy),
    "setBlinkFast",
    g_variant_new ("()"),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    callback,
    user_data);
}

/**
 * led_call_set_blink_fast_finish:
 * @proxy: A #LedProxy.
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to led_call_set_blink_fast().
 * @error: Return location for error or %NULL.
 *
 * Finishes an operation started with led_call_set_blink_fast().
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
led_call_set_blink_fast_finish (
    Led *proxy,
    GAsyncResult *res,
    GError **error)
{
  GVariant *_ret;
  _ret = g_dbus_proxy_call_finish (G_DBUS_PROXY (proxy), res, error);
  if (_ret == NULL)
    goto _out;
  g_variant_get (_ret,
                 "()");
  g_variant_unref (_ret);
_out:
  return _ret != NULL;
}

/**
 * led_call_set_blink_fast_sync:
 * @proxy: A #LedProxy.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @error: Return location for error or %NULL.
 *
 * Synchronously invokes the <link linkend="gdbus-method-org-openbmc-Led.setBlinkFast">setBlinkFast()</link> D-Bus method on @proxy. The calling thread is blocked until a reply is received.
 *
 * See led_call_set_blink_fast() for the asynchronous version of this method.
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
led_call_set_blink_fast_sync (
    Led *proxy,
    GCancellable *cancellable,
    GError **error)
{
  GVariant *_ret;
  _ret = g_dbus_proxy_call_sync (G_DBUS_PROXY (proxy),
    "setBlinkFast",
    g_variant_new ("()"),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    error);
  if (_ret == NULL)
    goto _out;
  g_variant_get (_ret,
                 "()");
  g_variant_unref (_ret);
_out:
  return _ret != NULL;
}

/**
 * led_complete_set_on:
 * @object: A #Led.
 * @invocation: (transfer full): A #GDBusMethodInvocation.
 *
 * Helper function used in service implementations to finish handling invocations of the <link linkend="gdbus-method-org-openbmc-Led.setOn">setOn()</link> D-Bus method. If you instead want to finish handling an invocation by returning an error, use g_dbus_method_invocation_return_error() or similar.
 *
 * This method will free @invocation, you cannot use it afterwards.
 */
void
led_complete_set_on (
    Led *object,
    GDBusMethodInvocation *invocation)
{
  g_dbus_method_invocation_return_value (invocation,
    g_variant_new ("()"));
}

/**
 * led_complete_set_off:
 * @object: A #Led.
 * @invocation: (transfer full): A #GDBusMethodInvocation.
 *
 * Helper function used in service implementations to finish handling invocations of the <link linkend="gdbus-method-org-openbmc-Led.setOff">setOff()</link> D-Bus method. If you instead want to finish handling an invocation by returning an error, use g_dbus_method_invocation_return_error() or similar.
 *
 * This method will free @invocation, you cannot use it afterwards.
 */
void
led_complete_set_off (
    Led *object,
    GDBusMethodInvocation *invocation)
{
  g_dbus_method_invocation_return_value (invocation,
    g_variant_new ("()"));
}

/**
 * led_complete_set_blink_slow:
 * @object: A #Led.
 * @invocation: (transfer full): A #GDBusMethodInvocation.
 *
 * Helper function used in service implementations to finish handling invocations of the <link linkend="gdbus-method-org-openbmc-Led.setBlinkSlow">setBlinkSlow()</link> D-Bus method. If you instead want to finish handling an invocation by returning an error, use g_dbus_method_invocation_return_error() or similar.
 *
 * This method will free @invocation, you cannot use it afterwards.
 */
void
led_complete_set_blink_slow (
    Led *object,
    GDBusMethodInvocation *invocation)
{
  g_dbus_method_invocation_return_value (invocation,
    g_variant_new ("()"));
}

/**
 * led_complete_set_blink_fast:
 * @object: A #Led.
 * @invocation: (transfer full): A #GDBusMethodInvocation.
 *
 * Helper function used in service implementations to finish handling invocations of the <link linkend="gdbus-method-org-openbmc-Led.setBlinkFast">setBlinkFast()</link> D-Bus method. If you instead want to finish handling an invocation by returning an error, use g_dbus_method_invocation_return_error() or similar.
 *
 * This method will free @invocation, you cannot use it afterwards.
 */
void
led_complete_set_blink_fast (
    Led *object,
    GDBusMethodInvocation *invocation)
{
  g_dbus_method_invocation_return_value (invocation,
    g_variant_new ("()"));
}

/* ------------------------------------------------------------------------ */

/**
 * LedProxy:
 *
 * The #LedProxy structure contains only private data and should only be accessed using the provided API.
 */

/**
 * LedProxyClass:
 * @parent_class: The parent class.
 *
 * Class structure for #LedProxy.
 */

struct _LedProxyPrivate
{
  GData *qdata;
};

static void led_proxy_iface_init (LedIface *iface);

#if GLIB_VERSION_MAX_ALLOWED >= GLIB_VERSION_2_38
G_DEFINE_TYPE_WITH_CODE (LedProxy, led_proxy, G_TYPE_DBUS_PROXY,
                         G_ADD_PRIVATE (LedProxy)
                         G_IMPLEMENT_INTERFACE (TYPE_LED, led_proxy_iface_init));

#else
G_DEFINE_TYPE_WITH_CODE (LedProxy, led_proxy, G_TYPE_DBUS_PROXY,
                         G_IMPLEMENT_INTERFACE (TYPE_LED, led_proxy_iface_init));

#endif
static void
led_proxy_finalize (GObject *object)
{
  LedProxy *proxy = LED_PROXY (object);
  g_datalist_clear (&proxy->priv->qdata);
  G_OBJECT_CLASS (led_proxy_parent_class)->finalize (object);
}

static void
led_proxy_get_property (GObject      *object,
  guint         prop_id,
  GValue       *value,
  GParamSpec   *pspec G_GNUC_UNUSED)
{
  const _ExtendedGDBusPropertyInfo *info;
  GVariant *variant;
  g_assert (prop_id != 0 && prop_id - 1 < 2);
  info = _led_property_info_pointers[prop_id - 1];
  variant = g_dbus_proxy_get_cached_property (G_DBUS_PROXY (object), info->parent_struct.name);
  if (info->use_gvariant)
    {
      g_value_set_variant (value, variant);
    }
  else
    {
      if (variant != NULL)
        g_dbus_gvariant_to_gvalue (variant, value);
    }
  if (variant != NULL)
    g_variant_unref (variant);
}

static void
led_proxy_set_property_cb (GDBusProxy *proxy,
  GAsyncResult *res,
  gpointer      user_data)
{
  const _ExtendedGDBusPropertyInfo *info = user_data;
  GError *error;
  GVariant *_ret;
  error = NULL;
  _ret = g_dbus_proxy_call_finish (proxy, res, &error);
  if (!_ret)
    {
      g_warning ("Error setting property '%s' on interface org.openbmc.Led: %s (%s, %d)",
                 info->parent_struct.name, 
                 error->message, g_quark_to_string (error->domain), error->code);
      g_error_free (error);
    }
  else
    {
      g_variant_unref (_ret);
    }
}

static void
led_proxy_set_property (GObject      *object,
  guint         prop_id,
  const GValue *value,
  GParamSpec   *pspec G_GNUC_UNUSED)
{
  const _ExtendedGDBusPropertyInfo *info;
  GVariant *variant;
  g_assert (prop_id != 0 && prop_id - 1 < 2);
  info = _led_property_info_pointers[prop_id - 1];
  variant = g_dbus_gvalue_to_gvariant (value, G_VARIANT_TYPE (info->parent_struct.signature));
  g_dbus_proxy_call (G_DBUS_PROXY (object),
    "org.freedesktop.DBus.Properties.Set",
    g_variant_new ("(ssv)", "org.openbmc.Led", info->parent_struct.name, variant),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    NULL, (GAsyncReadyCallback) led_proxy_set_property_cb, (GDBusPropertyInfo *) &info->parent_struct);
  g_variant_unref (variant);
}

static void
led_proxy_g_signal (GDBusProxy *proxy,
  const gchar *sender_name G_GNUC_UNUSED,
  const gchar *signal_name,
  GVariant *parameters)
{
  _ExtendedGDBusSignalInfo *info;
  GVariantIter iter;
  GVariant *child;
  GValue *paramv;
  guint num_params;
  guint n;
  guint signal_id;
  info = (_ExtendedGDBusSignalInfo *) g_dbus_interface_info_lookup_signal ((GDBusInterfaceInfo *) &_led_interface_info.parent_struct, signal_name);
  if (info == NULL)
    return;
  num_params = g_variant_n_children (parameters);
  paramv = g_new0 (GValue, num_params + 1);
  g_value_init (&paramv[0], TYPE_LED);
  g_value_set_object (&paramv[0], proxy);
  g_variant_iter_init (&iter, parameters);
  n = 1;
  while ((child = g_variant_iter_next_value (&iter)) != NULL)
    {
      _ExtendedGDBusArgInfo *arg_info = (_ExtendedGDBusArgInfo *) info->parent_struct.args[n - 1];
      if (arg_info->use_gvariant)
        {
          g_value_init (&paramv[n], G_TYPE_VARIANT);
          g_value_set_variant (&paramv[n], child);
          n++;
        }
      else
        g_dbus_gvariant_to_gvalue (child, &paramv[n++]);
      g_variant_unref (child);
    }
  signal_id = g_signal_lookup (info->signal_name, TYPE_LED);
  g_signal_emitv (paramv, signal_id, 0, NULL);
  for (n = 0; n < num_params + 1; n++)
    g_value_unset (&paramv[n]);
  g_free (paramv);
}

static void
led_proxy_g_properties_changed (GDBusProxy *_proxy,
  GVariant *changed_properties,
  const gchar *const *invalidated_properties)
{
  LedProxy *proxy = LED_PROXY (_proxy);
  guint n;
  const gchar *key;
  GVariantIter *iter;
  _ExtendedGDBusPropertyInfo *info;
  g_variant_get (changed_properties, "a{sv}", &iter);
  while (g_variant_iter_next (iter, "{&sv}", &key, NULL))
    {
      info = (_ExtendedGDBusPropertyInfo *) g_dbus_interface_info_lookup_property ((GDBusInterfaceInfo *) &_led_interface_info.parent_struct, key);
      g_datalist_remove_data (&proxy->priv->qdata, key);
      if (info != NULL)
        g_object_notify (G_OBJECT (proxy), info->hyphen_name);
    }
  g_variant_iter_free (iter);
  for (n = 0; invalidated_properties[n] != NULL; n++)
    {
      info = (_ExtendedGDBusPropertyInfo *) g_dbus_interface_info_lookup_property ((GDBusInterfaceInfo *) &_led_interface_info.parent_struct, invalidated_properties[n]);
      g_datalist_remove_data (&proxy->priv->qdata, invalidated_properties[n]);
      if (info != NULL)
        g_object_notify (G_OBJECT (proxy), info->hyphen_name);
    }
}

static gint 
led_proxy_get_color (Led *object)
{
  LedProxy *proxy = LED_PROXY (object);
  GVariant *variant;
  gint value = 0;
  variant = g_dbus_proxy_get_cached_property (G_DBUS_PROXY (proxy), "color");
  if (variant != NULL)
    {
      value = g_variant_get_int32 (variant);
      g_variant_unref (variant);
    }
  return value;
}

static const gchar *
led_proxy_get_function (Led *object)
{
  LedProxy *proxy = LED_PROXY (object);
  GVariant *variant;
  const gchar *value = NULL;
  variant = g_dbus_proxy_get_cached_property (G_DBUS_PROXY (proxy), "function");
  if (variant != NULL)
    {
      value = g_variant_get_string (variant, NULL);
      g_variant_unref (variant);
    }
  return value;
}

static void
led_proxy_init (LedProxy *proxy)
{
#if GLIB_VERSION_MAX_ALLOWED >= GLIB_VERSION_2_38
  proxy->priv = led_proxy_get_instance_private (proxy);
#else
  proxy->priv = G_TYPE_INSTANCE_GET_PRIVATE (proxy, TYPE_LED_PROXY, LedProxyPrivate);
#endif

  g_dbus_proxy_set_interface_info (G_DBUS_PROXY (proxy), led_interface_info ());
}

static void
led_proxy_class_init (LedProxyClass *klass)
{
  GObjectClass *gobject_class;
  GDBusProxyClass *proxy_class;

  gobject_class = G_OBJECT_CLASS (klass);
  gobject_class->finalize     = led_proxy_finalize;
  gobject_class->get_property = led_proxy_get_property;
  gobject_class->set_property = led_proxy_set_property;

  proxy_class = G_DBUS_PROXY_CLASS (klass);
  proxy_class->g_signal = led_proxy_g_signal;
  proxy_class->g_properties_changed = led_proxy_g_properties_changed;

  led_override_properties (gobject_class, 1);

#if GLIB_VERSION_MAX_ALLOWED < GLIB_VERSION_2_38
  g_type_class_add_private (klass, sizeof (LedProxyPrivate));
#endif
}

static void
led_proxy_iface_init (LedIface *iface)
{
  iface->get_color = led_proxy_get_color;
  iface->get_function = led_proxy_get_function;
}

/**
 * led_proxy_new:
 * @connection: A #GDBusConnection.
 * @flags: Flags from the #GDBusProxyFlags enumeration.
 * @name: (allow-none): A bus name (well-known or unique) or %NULL if @connection is not a message bus connection.
 * @object_path: An object path.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @callback: A #GAsyncReadyCallback to call when the request is satisfied.
 * @user_data: User data to pass to @callback.
 *
 * Asynchronously creates a proxy for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-Led.top_of_page">org.openbmc.Led</link>. See g_dbus_proxy_new() for more details.
 *
 * When the operation is finished, @callback will be invoked in the <link linkend="g-main-context-push-thread-default">thread-default main loop</link> of the thread you are calling this method from.
 * You can then call led_proxy_new_finish() to get the result of the operation.
 *
 * See led_proxy_new_sync() for the synchronous, blocking version of this constructor.
 */
void
led_proxy_new (
    GDBusConnection     *connection,
    GDBusProxyFlags      flags,
    const gchar         *name,
    const gchar         *object_path,
    GCancellable        *cancellable,
    GAsyncReadyCallback  callback,
    gpointer             user_data)
{
  g_async_initable_new_async (TYPE_LED_PROXY, G_PRIORITY_DEFAULT, cancellable, callback, user_data, "g-flags", flags, "g-name", name, "g-connection", connection, "g-object-path", object_path, "g-interface-name", "org.openbmc.Led", NULL);
}

/**
 * led_proxy_new_finish:
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to led_proxy_new().
 * @error: Return location for error or %NULL
 *
 * Finishes an operation started with led_proxy_new().
 *
 * Returns: (transfer full) (type LedProxy): The constructed proxy object or %NULL if @error is set.
 */
Led *
led_proxy_new_finish (
    GAsyncResult        *res,
    GError             **error)
{
  GObject *ret;
  GObject *source_object;
  source_object = g_async_result_get_source_object (res);
  ret = g_async_initable_new_finish (G_ASYNC_INITABLE (source_object), res, error);
  g_object_unref (source_object);
  if (ret != NULL)
    return LED (ret);
  else
    return NULL;
}

/**
 * led_proxy_new_sync:
 * @connection: A #GDBusConnection.
 * @flags: Flags from the #GDBusProxyFlags enumeration.
 * @name: (allow-none): A bus name (well-known or unique) or %NULL if @connection is not a message bus connection.
 * @object_path: An object path.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @error: Return location for error or %NULL
 *
 * Synchronously creates a proxy for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-Led.top_of_page">org.openbmc.Led</link>. See g_dbus_proxy_new_sync() for more details.
 *
 * The calling thread is blocked until a reply is received.
 *
 * See led_proxy_new() for the asynchronous version of this constructor.
 *
 * Returns: (transfer full) (type LedProxy): The constructed proxy object or %NULL if @error is set.
 */
Led *
led_proxy_new_sync (
    GDBusConnection     *connection,
    GDBusProxyFlags      flags,
    const gchar         *name,
    const gchar         *object_path,
    GCancellable        *cancellable,
    GError             **error)
{
  GInitable *ret;
  ret = g_initable_new (TYPE_LED_PROXY, cancellable, error, "g-flags", flags, "g-name", name, "g-connection", connection, "g-object-path", object_path, "g-interface-name", "org.openbmc.Led", NULL);
  if (ret != NULL)
    return LED (ret);
  else
    return NULL;
}


/**
 * led_proxy_new_for_bus:
 * @bus_type: A #GBusType.
 * @flags: Flags from the #GDBusProxyFlags enumeration.
 * @name: A bus name (well-known or unique).
 * @object_path: An object path.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @callback: A #GAsyncReadyCallback to call when the request is satisfied.
 * @user_data: User data to pass to @callback.
 *
 * Like led_proxy_new() but takes a #GBusType instead of a #GDBusConnection.
 *
 * When the operation is finished, @callback will be invoked in the <link linkend="g-main-context-push-thread-default">thread-default main loop</link> of the thread you are calling this method from.
 * You can then call led_proxy_new_for_bus_finish() to get the result of the operation.
 *
 * See led_proxy_new_for_bus_sync() for the synchronous, blocking version of this constructor.
 */
void
led_proxy_new_for_bus (
    GBusType             bus_type,
    GDBusProxyFlags      flags,
    const gchar         *name,
    const gchar         *object_path,
    GCancellable        *cancellable,
    GAsyncReadyCallback  callback,
    gpointer             user_data)
{
  g_async_initable_new_async (TYPE_LED_PROXY, G_PRIORITY_DEFAULT, cancellable, callback, user_data, "g-flags", flags, "g-name", name, "g-bus-type", bus_type, "g-object-path", object_path, "g-interface-name", "org.openbmc.Led", NULL);
}

/**
 * led_proxy_new_for_bus_finish:
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to led_proxy_new_for_bus().
 * @error: Return location for error or %NULL
 *
 * Finishes an operation started with led_proxy_new_for_bus().
 *
 * Returns: (transfer full) (type LedProxy): The constructed proxy object or %NULL if @error is set.
 */
Led *
led_proxy_new_for_bus_finish (
    GAsyncResult        *res,
    GError             **error)
{
  GObject *ret;
  GObject *source_object;
  source_object = g_async_result_get_source_object (res);
  ret = g_async_initable_new_finish (G_ASYNC_INITABLE (source_object), res, error);
  g_object_unref (source_object);
  if (ret != NULL)
    return LED (ret);
  else
    return NULL;
}

/**
 * led_proxy_new_for_bus_sync:
 * @bus_type: A #GBusType.
 * @flags: Flags from the #GDBusProxyFlags enumeration.
 * @name: A bus name (well-known or unique).
 * @object_path: An object path.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @error: Return location for error or %NULL
 *
 * Like led_proxy_new_sync() but takes a #GBusType instead of a #GDBusConnection.
 *
 * The calling thread is blocked until a reply is received.
 *
 * See led_proxy_new_for_bus() for the asynchronous version of this constructor.
 *
 * Returns: (transfer full) (type LedProxy): The constructed proxy object or %NULL if @error is set.
 */
Led *
led_proxy_new_for_bus_sync (
    GBusType             bus_type,
    GDBusProxyFlags      flags,
    const gchar         *name,
    const gchar         *object_path,
    GCancellable        *cancellable,
    GError             **error)
{
  GInitable *ret;
  ret = g_initable_new (TYPE_LED_PROXY, cancellable, error, "g-flags", flags, "g-name", name, "g-bus-type", bus_type, "g-object-path", object_path, "g-interface-name", "org.openbmc.Led", NULL);
  if (ret != NULL)
    return LED (ret);
  else
    return NULL;
}


/* ------------------------------------------------------------------------ */

/**
 * LedSkeleton:
 *
 * The #LedSkeleton structure contains only private data and should only be accessed using the provided API.
 */

/**
 * LedSkeletonClass:
 * @parent_class: The parent class.
 *
 * Class structure for #LedSkeleton.
 */

struct _LedSkeletonPrivate
{
  GValue *properties;
  GList *changed_properties;
  GSource *changed_properties_idle_source;
  GMainContext *context;
  GMutex lock;
};

static void
_led_skeleton_handle_method_call (
  GDBusConnection *connection G_GNUC_UNUSED,
  const gchar *sender G_GNUC_UNUSED,
  const gchar *object_path G_GNUC_UNUSED,
  const gchar *interface_name,
  const gchar *method_name,
  GVariant *parameters,
  GDBusMethodInvocation *invocation,
  gpointer user_data)
{
  LedSkeleton *skeleton = LED_SKELETON (user_data);
  _ExtendedGDBusMethodInfo *info;
  GVariantIter iter;
  GVariant *child;
  GValue *paramv;
  guint num_params;
  guint num_extra;
  guint n;
  guint signal_id;
  GValue return_value = G_VALUE_INIT;
  info = (_ExtendedGDBusMethodInfo *) g_dbus_method_invocation_get_method_info (invocation);
  g_assert (info != NULL);
  num_params = g_variant_n_children (parameters);
  num_extra = info->pass_fdlist ? 3 : 2;  paramv = g_new0 (GValue, num_params + num_extra);
  n = 0;
  g_value_init (&paramv[n], TYPE_LED);
  g_value_set_object (&paramv[n++], skeleton);
  g_value_init (&paramv[n], G_TYPE_DBUS_METHOD_INVOCATION);
  g_value_set_object (&paramv[n++], invocation);
  if (info->pass_fdlist)
    {
#ifdef G_OS_UNIX
      g_value_init (&paramv[n], G_TYPE_UNIX_FD_LIST);
      g_value_set_object (&paramv[n++], g_dbus_message_get_unix_fd_list (g_dbus_method_invocation_get_message (invocation)));
#else
      g_assert_not_reached ();
#endif
    }
  g_variant_iter_init (&iter, parameters);
  while ((child = g_variant_iter_next_value (&iter)) != NULL)
    {
      _ExtendedGDBusArgInfo *arg_info = (_ExtendedGDBusArgInfo *) info->parent_struct.in_args[n - num_extra];
      if (arg_info->use_gvariant)
        {
          g_value_init (&paramv[n], G_TYPE_VARIANT);
          g_value_set_variant (&paramv[n], child);
          n++;
        }
      else
        g_dbus_gvariant_to_gvalue (child, &paramv[n++]);
      g_variant_unref (child);
    }
  signal_id = g_signal_lookup (info->signal_name, TYPE_LED);
  g_value_init (&return_value, G_TYPE_BOOLEAN);
  g_signal_emitv (paramv, signal_id, 0, &return_value);
  if (!g_value_get_boolean (&return_value))
    g_dbus_method_invocation_return_error (invocation, G_DBUS_ERROR, G_DBUS_ERROR_UNKNOWN_METHOD, "Method %s is not implemented on interface %s", method_name, interface_name);
  g_value_unset (&return_value);
  for (n = 0; n < num_params + num_extra; n++)
    g_value_unset (&paramv[n]);
  g_free (paramv);
}

static GVariant *
_led_skeleton_handle_get_property (
  GDBusConnection *connection G_GNUC_UNUSED,
  const gchar *sender G_GNUC_UNUSED,
  const gchar *object_path G_GNUC_UNUSED,
  const gchar *interface_name G_GNUC_UNUSED,
  const gchar *property_name,
  GError **error,
  gpointer user_data)
{
  LedSkeleton *skeleton = LED_SKELETON (user_data);
  GValue value = G_VALUE_INIT;
  GParamSpec *pspec;
  _ExtendedGDBusPropertyInfo *info;
  GVariant *ret;
  ret = NULL;
  info = (_ExtendedGDBusPropertyInfo *) g_dbus_interface_info_lookup_property ((GDBusInterfaceInfo *) &_led_interface_info.parent_struct, property_name);
  g_assert (info != NULL);
  pspec = g_object_class_find_property (G_OBJECT_GET_CLASS (skeleton), info->hyphen_name);
  if (pspec == NULL)
    {
      g_set_error (error, G_DBUS_ERROR, G_DBUS_ERROR_INVALID_ARGS, "No property with name %s", property_name);
    }
  else
    {
      g_value_init (&value, pspec->value_type);
      g_object_get_property (G_OBJECT (skeleton), info->hyphen_name, &value);
      ret = g_dbus_gvalue_to_gvariant (&value, G_VARIANT_TYPE (info->parent_struct.signature));
      g_value_unset (&value);
    }
  return ret;
}

static gboolean
_led_skeleton_handle_set_property (
  GDBusConnection *connection G_GNUC_UNUSED,
  const gchar *sender G_GNUC_UNUSED,
  const gchar *object_path G_GNUC_UNUSED,
  const gchar *interface_name G_GNUC_UNUSED,
  const gchar *property_name,
  GVariant *variant,
  GError **error,
  gpointer user_data)
{
  LedSkeleton *skeleton = LED_SKELETON (user_data);
  GValue value = G_VALUE_INIT;
  GParamSpec *pspec;
  _ExtendedGDBusPropertyInfo *info;
  gboolean ret;
  ret = FALSE;
  info = (_ExtendedGDBusPropertyInfo *) g_dbus_interface_info_lookup_property ((GDBusInterfaceInfo *) &_led_interface_info.parent_struct, property_name);
  g_assert (info != NULL);
  pspec = g_object_class_find_property (G_OBJECT_GET_CLASS (skeleton), info->hyphen_name);
  if (pspec == NULL)
    {
      g_set_error (error, G_DBUS_ERROR, G_DBUS_ERROR_INVALID_ARGS, "No property with name %s", property_name);
    }
  else
    {
      if (info->use_gvariant)
        g_value_set_variant (&value, variant);
      else
        g_dbus_gvariant_to_gvalue (variant, &value);
      g_object_set_property (G_OBJECT (skeleton), info->hyphen_name, &value);
      g_value_unset (&value);
      ret = TRUE;
    }
  return ret;
}

static const GDBusInterfaceVTable _led_skeleton_vtable =
{
  _led_skeleton_handle_method_call,
  _led_skeleton_handle_get_property,
  _led_skeleton_handle_set_property,
  {NULL}
};

static GDBusInterfaceInfo *
led_skeleton_dbus_interface_get_info (GDBusInterfaceSkeleton *skeleton G_GNUC_UNUSED)
{
  return led_interface_info ();
}

static GDBusInterfaceVTable *
led_skeleton_dbus_interface_get_vtable (GDBusInterfaceSkeleton *skeleton G_GNUC_UNUSED)
{
  return (GDBusInterfaceVTable *) &_led_skeleton_vtable;
}

static GVariant *
led_skeleton_dbus_interface_get_properties (GDBusInterfaceSkeleton *_skeleton)
{
  LedSkeleton *skeleton = LED_SKELETON (_skeleton);

  GVariantBuilder builder;
  guint n;
  g_variant_builder_init (&builder, G_VARIANT_TYPE ("a{sv}"));
  if (_led_interface_info.parent_struct.properties == NULL)
    goto out;
  for (n = 0; _led_interface_info.parent_struct.properties[n] != NULL; n++)
    {
      GDBusPropertyInfo *info = _led_interface_info.parent_struct.properties[n];
      if (info->flags & G_DBUS_PROPERTY_INFO_FLAGS_READABLE)
        {
          GVariant *value;
          value = _led_skeleton_handle_get_property (g_dbus_interface_skeleton_get_connection (G_DBUS_INTERFACE_SKELETON (skeleton)), NULL, g_dbus_interface_skeleton_get_object_path (G_DBUS_INTERFACE_SKELETON (skeleton)), "org.openbmc.Led", info->name, NULL, skeleton);
          if (value != NULL)
            {
              g_variant_take_ref (value);
              g_variant_builder_add (&builder, "{sv}", info->name, value);
              g_variant_unref (value);
            }
        }
    }
out:
  return g_variant_builder_end (&builder);
}

static gboolean _led_emit_changed (gpointer user_data);

static void
led_skeleton_dbus_interface_flush (GDBusInterfaceSkeleton *_skeleton)
{
  LedSkeleton *skeleton = LED_SKELETON (_skeleton);
  gboolean emit_changed = FALSE;

  g_mutex_lock (&skeleton->priv->lock);
  if (skeleton->priv->changed_properties_idle_source != NULL)
    {
      g_source_destroy (skeleton->priv->changed_properties_idle_source);
      skeleton->priv->changed_properties_idle_source = NULL;
      emit_changed = TRUE;
    }
  g_mutex_unlock (&skeleton->priv->lock);

  if (emit_changed)
    _led_emit_changed (skeleton);
}

static void led_skeleton_iface_init (LedIface *iface);
#if GLIB_VERSION_MAX_ALLOWED >= GLIB_VERSION_2_38
G_DEFINE_TYPE_WITH_CODE (LedSkeleton, led_skeleton, G_TYPE_DBUS_INTERFACE_SKELETON,
                         G_ADD_PRIVATE (LedSkeleton)
                         G_IMPLEMENT_INTERFACE (TYPE_LED, led_skeleton_iface_init));

#else
G_DEFINE_TYPE_WITH_CODE (LedSkeleton, led_skeleton, G_TYPE_DBUS_INTERFACE_SKELETON,
                         G_IMPLEMENT_INTERFACE (TYPE_LED, led_skeleton_iface_init));

#endif
static void
led_skeleton_finalize (GObject *object)
{
  LedSkeleton *skeleton = LED_SKELETON (object);
  guint n;
  for (n = 0; n < 2; n++)
    g_value_unset (&skeleton->priv->properties[n]);
  g_free (skeleton->priv->properties);
  g_list_free_full (skeleton->priv->changed_properties, (GDestroyNotify) _changed_property_free);
  if (skeleton->priv->changed_properties_idle_source != NULL)
    g_source_destroy (skeleton->priv->changed_properties_idle_source);
  g_main_context_unref (skeleton->priv->context);
  g_mutex_clear (&skeleton->priv->lock);
  G_OBJECT_CLASS (led_skeleton_parent_class)->finalize (object);
}

static void
led_skeleton_get_property (GObject      *object,
  guint         prop_id,
  GValue       *value,
  GParamSpec   *pspec G_GNUC_UNUSED)
{
  LedSkeleton *skeleton = LED_SKELETON (object);
  g_assert (prop_id != 0 && prop_id - 1 < 2);
  g_mutex_lock (&skeleton->priv->lock);
  g_value_copy (&skeleton->priv->properties[prop_id - 1], value);
  g_mutex_unlock (&skeleton->priv->lock);
}

static gboolean
_led_emit_changed (gpointer user_data)
{
  LedSkeleton *skeleton = LED_SKELETON (user_data);
  GList *l;
  GVariantBuilder builder;
  GVariantBuilder invalidated_builder;
  guint num_changes;

  g_mutex_lock (&skeleton->priv->lock);
  g_variant_builder_init (&builder, G_VARIANT_TYPE ("a{sv}"));
  g_variant_builder_init (&invalidated_builder, G_VARIANT_TYPE ("as"));
  for (l = skeleton->priv->changed_properties, num_changes = 0; l != NULL; l = l->next)
    {
      ChangedProperty *cp = l->data;
      GVariant *variant;
      const GValue *cur_value;

      cur_value = &skeleton->priv->properties[cp->prop_id - 1];
      if (!_g_value_equal (cur_value, &cp->orig_value))
        {
          variant = g_dbus_gvalue_to_gvariant (cur_value, G_VARIANT_TYPE (cp->info->parent_struct.signature));
          g_variant_builder_add (&builder, "{sv}", cp->info->parent_struct.name, variant);
          g_variant_unref (variant);
          num_changes++;
        }
    }
  if (num_changes > 0)
    {
      GList *connections, *ll;
      GVariant *signal_variant;
      signal_variant = g_variant_ref_sink (g_variant_new ("(sa{sv}as)", "org.openbmc.Led",
                                           &builder, &invalidated_builder));
      connections = g_dbus_interface_skeleton_get_connections (G_DBUS_INTERFACE_SKELETON (skeleton));
      for (ll = connections; ll != NULL; ll = ll->next)
        {
          GDBusConnection *connection = ll->data;

          g_dbus_connection_emit_signal (connection,
                                         NULL, g_dbus_interface_skeleton_get_object_path (G_DBUS_INTERFACE_SKELETON (skeleton)),
                                         "org.freedesktop.DBus.Properties",
                                         "PropertiesChanged",
                                         signal_variant,
                                         NULL);
        }
      g_variant_unref (signal_variant);
      g_list_free_full (connections, g_object_unref);
    }
  else
    {
      g_variant_builder_clear (&builder);
      g_variant_builder_clear (&invalidated_builder);
    }
  g_list_free_full (skeleton->priv->changed_properties, (GDestroyNotify) _changed_property_free);
  skeleton->priv->changed_properties = NULL;
  skeleton->priv->changed_properties_idle_source = NULL;
  g_mutex_unlock (&skeleton->priv->lock);
  return FALSE;
}

static void
_led_schedule_emit_changed (LedSkeleton *skeleton, const _ExtendedGDBusPropertyInfo *info, guint prop_id, const GValue *orig_value)
{
  ChangedProperty *cp;
  GList *l;
  cp = NULL;
  for (l = skeleton->priv->changed_properties; l != NULL; l = l->next)
    {
      ChangedProperty *i_cp = l->data;
      if (i_cp->info == info)
        {
          cp = i_cp;
          break;
        }
    }
  if (cp == NULL)
    {
      cp = g_new0 (ChangedProperty, 1);
      cp->prop_id = prop_id;
      cp->info = info;
      skeleton->priv->changed_properties = g_list_prepend (skeleton->priv->changed_properties, cp);
      g_value_init (&cp->orig_value, G_VALUE_TYPE (orig_value));
      g_value_copy (orig_value, &cp->orig_value);
    }
}

static void
led_skeleton_notify (GObject      *object,
  GParamSpec *pspec G_GNUC_UNUSED)
{
  LedSkeleton *skeleton = LED_SKELETON (object);
  g_mutex_lock (&skeleton->priv->lock);
  if (skeleton->priv->changed_properties != NULL &&
      skeleton->priv->changed_properties_idle_source == NULL)
    {
      skeleton->priv->changed_properties_idle_source = g_idle_source_new ();
      g_source_set_priority (skeleton->priv->changed_properties_idle_source, G_PRIORITY_DEFAULT);
      g_source_set_callback (skeleton->priv->changed_properties_idle_source, _led_emit_changed, g_object_ref (skeleton), (GDestroyNotify) g_object_unref);
      g_source_attach (skeleton->priv->changed_properties_idle_source, skeleton->priv->context);
      g_source_unref (skeleton->priv->changed_properties_idle_source);
    }
  g_mutex_unlock (&skeleton->priv->lock);
}

static void
led_skeleton_set_property (GObject      *object,
  guint         prop_id,
  const GValue *value,
  GParamSpec   *pspec)
{
  LedSkeleton *skeleton = LED_SKELETON (object);
  g_assert (prop_id != 0 && prop_id - 1 < 2);
  g_mutex_lock (&skeleton->priv->lock);
  g_object_freeze_notify (object);
  if (!_g_value_equal (value, &skeleton->priv->properties[prop_id - 1]))
    {
      if (g_dbus_interface_skeleton_get_connection (G_DBUS_INTERFACE_SKELETON (skeleton)) != NULL)
        _led_schedule_emit_changed (skeleton, _led_property_info_pointers[prop_id - 1], prop_id, &skeleton->priv->properties[prop_id - 1]);
      g_value_copy (value, &skeleton->priv->properties[prop_id - 1]);
      g_object_notify_by_pspec (object, pspec);
    }
  g_mutex_unlock (&skeleton->priv->lock);
  g_object_thaw_notify (object);
}

static void
led_skeleton_init (LedSkeleton *skeleton)
{
#if GLIB_VERSION_MAX_ALLOWED >= GLIB_VERSION_2_38
  skeleton->priv = led_skeleton_get_instance_private (skeleton);
#else
  skeleton->priv = G_TYPE_INSTANCE_GET_PRIVATE (skeleton, TYPE_LED_SKELETON, LedSkeletonPrivate);
#endif

  g_mutex_init (&skeleton->priv->lock);
  skeleton->priv->context = g_main_context_ref_thread_default ();
  skeleton->priv->properties = g_new0 (GValue, 2);
  g_value_init (&skeleton->priv->properties[0], G_TYPE_INT);
  g_value_init (&skeleton->priv->properties[1], G_TYPE_STRING);
}

static gint 
led_skeleton_get_color (Led *object)
{
  LedSkeleton *skeleton = LED_SKELETON (object);
  gint value;
  g_mutex_lock (&skeleton->priv->lock);
  value = g_value_get_int (&(skeleton->priv->properties[0]));
  g_mutex_unlock (&skeleton->priv->lock);
  return value;
}

static const gchar *
led_skeleton_get_function (Led *object)
{
  LedSkeleton *skeleton = LED_SKELETON (object);
  const gchar *value;
  g_mutex_lock (&skeleton->priv->lock);
  value = g_value_get_string (&(skeleton->priv->properties[1]));
  g_mutex_unlock (&skeleton->priv->lock);
  return value;
}

static void
led_skeleton_class_init (LedSkeletonClass *klass)
{
  GObjectClass *gobject_class;
  GDBusInterfaceSkeletonClass *skeleton_class;

  gobject_class = G_OBJECT_CLASS (klass);
  gobject_class->finalize = led_skeleton_finalize;
  gobject_class->get_property = led_skeleton_get_property;
  gobject_class->set_property = led_skeleton_set_property;
  gobject_class->notify       = led_skeleton_notify;


  led_override_properties (gobject_class, 1);

  skeleton_class = G_DBUS_INTERFACE_SKELETON_CLASS (klass);
  skeleton_class->get_info = led_skeleton_dbus_interface_get_info;
  skeleton_class->get_properties = led_skeleton_dbus_interface_get_properties;
  skeleton_class->flush = led_skeleton_dbus_interface_flush;
  skeleton_class->get_vtable = led_skeleton_dbus_interface_get_vtable;

#if GLIB_VERSION_MAX_ALLOWED < GLIB_VERSION_2_38
  g_type_class_add_private (klass, sizeof (LedSkeletonPrivate));
#endif
}

static void
led_skeleton_iface_init (LedIface *iface)
{
  iface->get_color = led_skeleton_get_color;
  iface->get_function = led_skeleton_get_function;
}

/**
 * led_skeleton_new:
 *
 * Creates a skeleton object for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-Led.top_of_page">org.openbmc.Led</link>.
 *
 * Returns: (transfer full) (type LedSkeleton): The skeleton object.
 */
Led *
led_skeleton_new (void)
{
  return LED (g_object_new (TYPE_LED_SKELETON, NULL));
}

/* ------------------------------------------------------------------------
 * Code for Object, ObjectProxy and ObjectSkeleton
 * ------------------------------------------------------------------------
 */

/**
 * SECTION:Object
 * @title: Object
 * @short_description: Specialized GDBusObject types
 *
 * This section contains the #Object, #ObjectProxy, and #ObjectSkeleton types which make it easier to work with objects implementing generated types for D-Bus interfaces.
 */

/**
 * Object:
 *
 * The #Object type is a specialized container of interfaces.
 */

/**
 * ObjectIface:
 * @parent_iface: The parent interface.
 *
 * Virtual table for the #Object interface.
 */

typedef ObjectIface ObjectInterface;
G_DEFINE_INTERFACE_WITH_CODE (Object, object, G_TYPE_OBJECT, g_type_interface_add_prerequisite (g_define_type_id, G_TYPE_DBUS_OBJECT));

static void
object_default_init (ObjectIface *iface)
{
  /**
   * Object:led:
   *
   * The #Led instance corresponding to the D-Bus interface <link linkend="gdbus-interface-org-openbmc-Led.top_of_page">org.openbmc.Led</link>, if any.
   *
   * Connect to the #GObject::notify signal to get informed of property changes.
   */
  g_object_interface_install_property (iface, g_param_spec_object ("led", "led", "led", TYPE_LED, G_PARAM_READWRITE|G_PARAM_STATIC_STRINGS));

}

/**
 * object_get_led:
 * @object: A #Object.
 *
 * Gets the #Led instance for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-Led.top_of_page">org.openbmc.Led</link> on @object, if any.
 *
 * Returns: (transfer full): A #Led that must be freed with g_object_unref() or %NULL if @object does not implement the interface.
 */
Led *object_get_led (Object *object)
{
  GDBusInterface *ret;
  ret = g_dbus_object_get_interface (G_DBUS_OBJECT (object), "org.openbmc.Led");
  if (ret == NULL)
    return NULL;
  return LED (ret);
}


/**
 * object_peek_led: (skip)
 * @object: A #Object.
 *
 * Like object_get_led() but doesn't increase the reference count on the returned object.
 *
 * <warning>It is not safe to use the returned object if you are on another thread than the one where the #GDBusObjectManagerClient or #GDBusObjectManagerServer for @object is running.</warning>
 *
 * Returns: (transfer none): A #Led or %NULL if @object does not implement the interface. Do not free the returned object, it is owned by @object.
 */
Led *object_peek_led (Object *object)
{
  GDBusInterface *ret;
  ret = g_dbus_object_get_interface (G_DBUS_OBJECT (object), "org.openbmc.Led");
  if (ret == NULL)
    return NULL;
  g_object_unref (ret);
  return LED (ret);
}


static void
object_notify (GDBusObject *object, GDBusInterface *interface)
{
  _ExtendedGDBusInterfaceInfo *info = (_ExtendedGDBusInterfaceInfo *) g_dbus_interface_get_info (interface);
  /* info can be NULL if the other end is using a D-Bus interface we don't know
   * anything about, for example old generated code in this process talking to
   * newer generated code in the other process. */
  if (info != NULL)
    g_object_notify (G_OBJECT (object), info->hyphen_name);
}

/**
 * ObjectProxy:
 *
 * The #ObjectProxy structure contains only private data and should only be accessed using the provided API.
 */

/**
 * ObjectProxyClass:
 * @parent_class: The parent class.
 *
 * Class structure for #ObjectProxy.
 */

static void
object_proxy__object_iface_init (ObjectIface *iface G_GNUC_UNUSED)
{
}

static void
object_proxy__g_dbus_object_iface_init (GDBusObjectIface *iface)
{
  iface->interface_added = object_notify;
  iface->interface_removed = object_notify;
}


G_DEFINE_TYPE_WITH_CODE (ObjectProxy, object_proxy, G_TYPE_DBUS_OBJECT_PROXY,
                         G_IMPLEMENT_INTERFACE (TYPE_OBJECT, object_proxy__object_iface_init)
                         G_IMPLEMENT_INTERFACE (G_TYPE_DBUS_OBJECT, object_proxy__g_dbus_object_iface_init));

static void
object_proxy_init (ObjectProxy *object G_GNUC_UNUSED)
{
}

static void
object_proxy_set_property (GObject      *gobject,
  guint         prop_id,
  const GValue *value G_GNUC_UNUSED,
  GParamSpec   *pspec)
{
  G_OBJECT_WARN_INVALID_PROPERTY_ID (gobject, prop_id, pspec);
}

static void
object_proxy_get_property (GObject      *gobject,
  guint         prop_id,
  GValue       *value,
  GParamSpec   *pspec)
{
  ObjectProxy *object = OBJECT_PROXY (gobject);
  GDBusInterface *interface;

  switch (prop_id)
    {
    case 1:
      interface = g_dbus_object_get_interface (G_DBUS_OBJECT (object), "org.openbmc.Led");
      g_value_take_object (value, interface);
      break;

    default:
      G_OBJECT_WARN_INVALID_PROPERTY_ID (gobject, prop_id, pspec);
      break;
  }
}

static void
object_proxy_class_init (ObjectProxyClass *klass)
{
  GObjectClass *gobject_class = G_OBJECT_CLASS (klass);

  gobject_class->set_property = object_proxy_set_property;
  gobject_class->get_property = object_proxy_get_property;

  g_object_class_override_property (gobject_class, 1, "led");
}

/**
 * object_proxy_new:
 * @connection: A #GDBusConnection.
 * @object_path: An object path.
 *
 * Creates a new proxy object.
 *
 * Returns: (transfer full): The proxy object.
 */
ObjectProxy *
object_proxy_new (GDBusConnection *connection,
  const gchar *object_path)
{
  g_return_val_if_fail (G_IS_DBUS_CONNECTION (connection), NULL);
  g_return_val_if_fail (g_variant_is_object_path (object_path), NULL);
  return OBJECT_PROXY (g_object_new (TYPE_OBJECT_PROXY, "g-connection", connection, "g-object-path", object_path, NULL));
}

/**
 * ObjectSkeleton:
 *
 * The #ObjectSkeleton structure contains only private data and should only be accessed using the provided API.
 */

/**
 * ObjectSkeletonClass:
 * @parent_class: The parent class.
 *
 * Class structure for #ObjectSkeleton.
 */

static void
object_skeleton__object_iface_init (ObjectIface *iface G_GNUC_UNUSED)
{
}


static void
object_skeleton__g_dbus_object_iface_init (GDBusObjectIface *iface)
{
  iface->interface_added = object_notify;
  iface->interface_removed = object_notify;
}

G_DEFINE_TYPE_WITH_CODE (ObjectSkeleton, object_skeleton, G_TYPE_DBUS_OBJECT_SKELETON,
                         G_IMPLEMENT_INTERFACE (TYPE_OBJECT, object_skeleton__object_iface_init)
                         G_IMPLEMENT_INTERFACE (G_TYPE_DBUS_OBJECT, object_skeleton__g_dbus_object_iface_init));

static void
object_skeleton_init (ObjectSkeleton *object G_GNUC_UNUSED)
{
}

static void
object_skeleton_set_property (GObject      *gobject,
  guint         prop_id,
  const GValue *value,
  GParamSpec   *pspec)
{
  ObjectSkeleton *object = OBJECT_SKELETON (gobject);
  GDBusInterfaceSkeleton *interface;

  switch (prop_id)
    {
    case 1:
      interface = g_value_get_object (value);
      if (interface != NULL)
        {
          g_warn_if_fail (IS_LED (interface));
          g_dbus_object_skeleton_add_interface (G_DBUS_OBJECT_SKELETON (object), interface);
        }
      else
        {
          g_dbus_object_skeleton_remove_interface_by_name (G_DBUS_OBJECT_SKELETON (object), "org.openbmc.Led");
        }
      break;

    default:
      G_OBJECT_WARN_INVALID_PROPERTY_ID (gobject, prop_id, pspec);
      break;
  }
}

static void
object_skeleton_get_property (GObject      *gobject,
  guint         prop_id,
  GValue       *value,
  GParamSpec   *pspec)
{
  ObjectSkeleton *object = OBJECT_SKELETON (gobject);
  GDBusInterface *interface;

  switch (prop_id)
    {
    case 1:
      interface = g_dbus_object_get_interface (G_DBUS_OBJECT (object), "org.openbmc.Led");
      g_value_take_object (value, interface);
      break;

    default:
      G_OBJECT_WARN_INVALID_PROPERTY_ID (gobject, prop_id, pspec);
      break;
  }
}

static void
object_skeleton_class_init (ObjectSkeletonClass *klass)
{
  GObjectClass *gobject_class = G_OBJECT_CLASS (klass);

  gobject_class->set_property = object_skeleton_set_property;
  gobject_class->get_property = object_skeleton_get_property;

  g_object_class_override_property (gobject_class, 1, "led");
}

/**
 * object_skeleton_new:
 * @object_path: An object path.
 *
 * Creates a new skeleton object.
 *
 * Returns: (transfer full): The skeleton object.
 */
ObjectSkeleton *
object_skeleton_new (const gchar *object_path)
{
  g_return_val_if_fail (g_variant_is_object_path (object_path), NULL);
  return OBJECT_SKELETON (g_object_new (TYPE_OBJECT_SKELETON, "g-object-path", object_path, NULL));
}

/**
 * object_skeleton_set_led:
 * @object: A #ObjectSkeleton.
 * @interface_: (allow-none): A #Led or %NULL to clear the interface.
 *
 * Sets the #Led instance for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-Led.top_of_page">org.openbmc.Led</link> on @object.
 */
void object_skeleton_set_led (ObjectSkeleton *object, Led *interface_)
{
  g_object_set (G_OBJECT (object), "led", interface_, NULL);
}


/* ------------------------------------------------------------------------
 * Code for ObjectManager client
 * ------------------------------------------------------------------------
 */

/**
 * SECTION:ObjectManagerClient
 * @title: ObjectManagerClient
 * @short_description: Generated GDBusObjectManagerClient type
 *
 * This section contains a #GDBusObjectManagerClient that uses object_manager_client_get_proxy_type() as the #GDBusProxyTypeFunc.
 */

/**
 * ObjectManagerClient:
 *
 * The #ObjectManagerClient structure contains only private data and should only be accessed using the provided API.
 */

/**
 * ObjectManagerClientClass:
 * @parent_class: The parent class.
 *
 * Class structure for #ObjectManagerClient.
 */

G_DEFINE_TYPE (ObjectManagerClient, object_manager_client, G_TYPE_DBUS_OBJECT_MANAGER_CLIENT);

static void
object_manager_client_init (ObjectManagerClient *manager G_GNUC_UNUSED)
{
}

static void
object_manager_client_class_init (ObjectManagerClientClass *klass G_GNUC_UNUSED)
{
}

/**
 * object_manager_client_get_proxy_type:
 * @manager: A #GDBusObjectManagerClient.
 * @object_path: The object path of the remote object (unused).
 * @interface_name: (allow-none): Interface name of the remote object or %NULL to get the object proxy #GType.
 * @user_data: User data (unused).
 *
 * A #GDBusProxyTypeFunc that maps @interface_name to the generated #GDBusObjectProxy<!-- -->- and #GDBusProxy<!-- -->-derived types.
 *
 * Returns: A #GDBusProxy<!-- -->-derived #GType if @interface_name is not %NULL, otherwise the #GType for #ObjectProxy.
 */
GType
object_manager_client_get_proxy_type (GDBusObjectManagerClient *manager G_GNUC_UNUSED, const gchar *object_path G_GNUC_UNUSED, const gchar *interface_name, gpointer user_data G_GNUC_UNUSED)
{
  static gsize once_init_value = 0;
  static GHashTable *lookup_hash;
  GType ret;

  if (interface_name == NULL)
    return TYPE_OBJECT_PROXY;
  if (g_once_init_enter (&once_init_value))
    {
      lookup_hash = g_hash_table_new (g_str_hash, g_str_equal);
      g_hash_table_insert (lookup_hash, (gpointer) "org.openbmc.Led", GSIZE_TO_POINTER (TYPE_LED_PROXY));
      g_once_init_leave (&once_init_value, 1);
    }
  ret = (GType) GPOINTER_TO_SIZE (g_hash_table_lookup (lookup_hash, interface_name));
  if (ret == (GType) 0)
    ret = G_TYPE_DBUS_PROXY;
  return ret;
}

/**
 * object_manager_client_new:
 * @connection: A #GDBusConnection.
 * @flags: Flags from the #GDBusObjectManagerClientFlags enumeration.
 * @name: (allow-none): A bus name (well-known or unique) or %NULL if @connection is not a message bus connection.
 * @object_path: An object path.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @callback: A #GAsyncReadyCallback to call when the request is satisfied.
 * @user_data: User data to pass to @callback.
 *
 * Asynchronously creates #GDBusObjectManagerClient using object_manager_client_get_proxy_type() as the #GDBusProxyTypeFunc. See g_dbus_object_manager_client_new() for more details.
 *
 * When the operation is finished, @callback will be invoked in the <link linkend="g-main-context-push-thread-default">thread-default main loop</link> of the thread you are calling this method from.
 * You can then call object_manager_client_new_finish() to get the result of the operation.
 *
 * See object_manager_client_new_sync() for the synchronous, blocking version of this constructor.
 */
void
object_manager_client_new (
    GDBusConnection        *connection,
    GDBusObjectManagerClientFlags  flags,
    const gchar            *name,
    const gchar            *object_path,
    GCancellable           *cancellable,
    GAsyncReadyCallback     callback,
    gpointer                user_data)
{
  g_async_initable_new_async (TYPE_OBJECT_MANAGER_CLIENT, G_PRIORITY_DEFAULT, cancellable, callback, user_data, "flags", flags, "name", name, "connection", connection, "object-path", object_path, "get-proxy-type-func", object_manager_client_get_proxy_type, NULL);
}

/**
 * object_manager_client_new_finish:
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to object_manager_client_new().
 * @error: Return location for error or %NULL
 *
 * Finishes an operation started with object_manager_client_new().
 *
 * Returns: (transfer full) (type ObjectManagerClient): The constructed object manager client or %NULL if @error is set.
 */
GDBusObjectManager *
object_manager_client_new_finish (
    GAsyncResult        *res,
    GError             **error)
{
  GObject *ret;
  GObject *source_object;
  source_object = g_async_result_get_source_object (res);
  ret = g_async_initable_new_finish (G_ASYNC_INITABLE (source_object), res, error);
  g_object_unref (source_object);
  if (ret != NULL)
    return G_DBUS_OBJECT_MANAGER (ret);
  else
    return NULL;
}

/**
 * object_manager_client_new_sync:
 * @connection: A #GDBusConnection.
 * @flags: Flags from the #GDBusObjectManagerClientFlags enumeration.
 * @name: (allow-none): A bus name (well-known or unique) or %NULL if @connection is not a message bus connection.
 * @object_path: An object path.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @error: Return location for error or %NULL
 *
 * Synchronously creates #GDBusObjectManagerClient using object_manager_client_get_proxy_type() as the #GDBusProxyTypeFunc. See g_dbus_object_manager_client_new_sync() for more details.
 *
 * The calling thread is blocked until a reply is received.
 *
 * See object_manager_client_new() for the asynchronous version of this constructor.
 *
 * Returns: (transfer full) (type ObjectManagerClient): The constructed object manager client or %NULL if @error is set.
 */
GDBusObjectManager *
object_manager_client_new_sync (
    GDBusConnection        *connection,
    GDBusObjectManagerClientFlags  flags,
    const gchar            *name,
    const gchar            *object_path,
    GCancellable           *cancellable,
    GError                **error)
{
  GInitable *ret;
  ret = g_initable_new (TYPE_OBJECT_MANAGER_CLIENT, cancellable, error, "flags", flags, "name", name, "connection", connection, "object-path", object_path, "get-proxy-type-func", object_manager_client_get_proxy_type, NULL);
  if (ret != NULL)
    return G_DBUS_OBJECT_MANAGER (ret);
  else
    return NULL;
}


/**
 * object_manager_client_new_for_bus:
 * @bus_type: A #GBusType.
 * @flags: Flags from the #GDBusObjectManagerClientFlags enumeration.
 * @name: A bus name (well-known or unique).
 * @object_path: An object path.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @callback: A #GAsyncReadyCallback to call when the request is satisfied.
 * @user_data: User data to pass to @callback.
 *
 * Like object_manager_client_new() but takes a #GBusType instead of a #GDBusConnection.
 *
 * When the operation is finished, @callback will be invoked in the <link linkend="g-main-context-push-thread-default">thread-default main loop</link> of the thread you are calling this method from.
 * You can then call object_manager_client_new_for_bus_finish() to get the result of the operation.
 *
 * See object_manager_client_new_for_bus_sync() for the synchronous, blocking version of this constructor.
 */
void
object_manager_client_new_for_bus (
    GBusType                bus_type,
    GDBusObjectManagerClientFlags  flags,
    const gchar            *name,
    const gchar            *object_path,
    GCancellable           *cancellable,
    GAsyncReadyCallback     callback,
    gpointer                user_data)
{
  g_async_initable_new_async (TYPE_OBJECT_MANAGER_CLIENT, G_PRIORITY_DEFAULT, cancellable, callback, user_data, "flags", flags, "name", name, "bus-type", bus_type, "object-path", object_path, "get-proxy-type-func", object_manager_client_get_proxy_type, NULL);
}

/**
 * object_manager_client_new_for_bus_finish:
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to object_manager_client_new_for_bus().
 * @error: Return location for error or %NULL
 *
 * Finishes an operation started with object_manager_client_new_for_bus().
 *
 * Returns: (transfer full) (type ObjectManagerClient): The constructed object manager client or %NULL if @error is set.
 */
GDBusObjectManager *
object_manager_client_new_for_bus_finish (
    GAsyncResult        *res,
    GError             **error)
{
  GObject *ret;
  GObject *source_object;
  source_object = g_async_result_get_source_object (res);
  ret = g_async_initable_new_finish (G_ASYNC_INITABLE (source_object), res, error);
  g_object_unref (source_object);
  if (ret != NULL)
    return G_DBUS_OBJECT_MANAGER (ret);
  else
    return NULL;
}

/**
 * object_manager_client_new_for_bus_sync:
 * @bus_type: A #GBusType.
 * @flags: Flags from the #GDBusObjectManagerClientFlags enumeration.
 * @name: A bus name (well-known or unique).
 * @object_path: An object path.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @error: Return location for error or %NULL
 *
 * Like object_manager_client_new_sync() but takes a #GBusType instead of a #GDBusConnection.
 *
 * The calling thread is blocked until a reply is received.
 *
 * See object_manager_client_new_for_bus() for the asynchronous version of this constructor.
 *
 * Returns: (transfer full) (type ObjectManagerClient): The constructed object manager client or %NULL if @error is set.
 */
GDBusObjectManager *
object_manager_client_new_for_bus_sync (
    GBusType                bus_type,
    GDBusObjectManagerClientFlags  flags,
    const gchar            *name,
    const gchar            *object_path,
    GCancellable           *cancellable,
    GError                **error)
{
  GInitable *ret;
  ret = g_initable_new (TYPE_OBJECT_MANAGER_CLIENT, cancellable, error, "flags", flags, "name", name, "bus-type", bus_type, "object-path", object_path, "get-proxy-type-func", object_manager_client_get_proxy_type, NULL);
  if (ret != NULL)
    return G_DBUS_OBJECT_MANAGER (ret);
  else
    return NULL;
}


