/*
 * 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/power_control.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.control.Power
 * ------------------------------------------------------------------------
 */

/**
 * SECTION:ControlPower
 * @title: ControlPower
 * @short_description: Generated C code for the org.openbmc.control.Power D-Bus interface
 *
 * This section contains code for working with the <link linkend="gdbus-interface-org-openbmc-control-Power.top_of_page">org.openbmc.control.Power</link> D-Bus interface in C.
 */

/* ---- Introspection data for org.openbmc.control.Power ---- */

static const _ExtendedGDBusArgInfo _control_power_method_info_set_power_state_IN_ARG_state =
{
  {
    -1,
    (gchar *) "state",
    (gchar *) "i",
    NULL
  },
  FALSE
};

static const _ExtendedGDBusArgInfo * const _control_power_method_info_set_power_state_IN_ARG_pointers[] =
{
  &_control_power_method_info_set_power_state_IN_ARG_state,
  NULL
};

static const _ExtendedGDBusMethodInfo _control_power_method_info_set_power_state =
{
  {
    -1,
    (gchar *) "setPowerState",
    (GDBusArgInfo **) &_control_power_method_info_set_power_state_IN_ARG_pointers,
    NULL,
    NULL
  },
  "handle-set-power-state",
  FALSE
};

static const _ExtendedGDBusArgInfo _control_power_method_info_get_power_state_OUT_ARG_state =
{
  {
    -1,
    (gchar *) "state",
    (gchar *) "i",
    NULL
  },
  FALSE
};

static const _ExtendedGDBusArgInfo * const _control_power_method_info_get_power_state_OUT_ARG_pointers[] =
{
  &_control_power_method_info_get_power_state_OUT_ARG_state,
  NULL
};

static const _ExtendedGDBusMethodInfo _control_power_method_info_get_power_state =
{
  {
    -1,
    (gchar *) "getPowerState",
    NULL,
    (GDBusArgInfo **) &_control_power_method_info_get_power_state_OUT_ARG_pointers,
    NULL
  },
  "handle-get-power-state",
  FALSE
};

static const _ExtendedGDBusMethodInfo * const _control_power_method_info_pointers[] =
{
  &_control_power_method_info_set_power_state,
  &_control_power_method_info_get_power_state,
  NULL
};

static const _ExtendedGDBusSignalInfo _control_power_signal_info_power_good =
{
  {
    -1,
    (gchar *) "PowerGood",
    NULL,
    NULL
  },
  "power-good"
};

static const _ExtendedGDBusSignalInfo _control_power_signal_info_power_lost =
{
  {
    -1,
    (gchar *) "PowerLost",
    NULL,
    NULL
  },
  "power-lost"
};

static const _ExtendedGDBusSignalInfo * const _control_power_signal_info_pointers[] =
{
  &_control_power_signal_info_power_good,
  &_control_power_signal_info_power_lost,
  NULL
};

static const _ExtendedGDBusPropertyInfo _control_power_property_info_pgood =
{
  {
    -1,
    (gchar *) "pgood",
    (gchar *) "i",
    G_DBUS_PROPERTY_INFO_FLAGS_READABLE,
    NULL
  },
  "pgood",
  FALSE
};

static const _ExtendedGDBusPropertyInfo _control_power_property_info_state =
{
  {
    -1,
    (gchar *) "state",
    (gchar *) "i",
    G_DBUS_PROPERTY_INFO_FLAGS_READABLE,
    NULL
  },
  "state",
  FALSE
};

static const _ExtendedGDBusPropertyInfo * const _control_power_property_info_pointers[] =
{
  &_control_power_property_info_pgood,
  &_control_power_property_info_state,
  NULL
};

static const _ExtendedGDBusInterfaceInfo _control_power_interface_info =
{
  {
    -1,
    (gchar *) "org.openbmc.control.Power",
    (GDBusMethodInfo **) &_control_power_method_info_pointers,
    (GDBusSignalInfo **) &_control_power_signal_info_pointers,
    (GDBusPropertyInfo **) &_control_power_property_info_pointers,
    NULL
  },
  "control-power",
};


/**
 * control_power_interface_info:
 *
 * Gets a machine-readable description of the <link linkend="gdbus-interface-org-openbmc-control-Power.top_of_page">org.openbmc.control.Power</link> D-Bus interface.
 *
 * Returns: (transfer none): A #GDBusInterfaceInfo. Do not free.
 */
GDBusInterfaceInfo *
control_power_interface_info (void)
{
  return (GDBusInterfaceInfo *) &_control_power_interface_info.parent_struct;
}

/**
 * control_power_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 #ControlPower interface for a concrete class.
 * The properties are overridden in the order they are defined.
 *
 * Returns: The last property id.
 */
guint
control_power_override_properties (GObjectClass *klass, guint property_id_begin)
{
  g_object_class_override_property (klass, property_id_begin++, "pgood");
  g_object_class_override_property (klass, property_id_begin++, "state");
  return property_id_begin - 1;
}



/**
 * ControlPower:
 *
 * Abstract interface type for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-control-Power.top_of_page">org.openbmc.control.Power</link>.
 */

/**
 * ControlPowerIface:
 * @parent_iface: The parent interface.
 * @handle_get_power_state: Handler for the #ControlPower::handle-get-power-state signal.
 * @handle_set_power_state: Handler for the #ControlPower::handle-set-power-state signal.
 * @get_pgood: Getter for the #ControlPower:pgood property.
 * @get_state: Getter for the #ControlPower:state property.
 * @power_good: Handler for the #ControlPower::power-good signal.
 * @power_lost: Handler for the #ControlPower::power-lost signal.
 *
 * Virtual table for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-control-Power.top_of_page">org.openbmc.control.Power</link>.
 */

typedef ControlPowerIface ControlPowerInterface;
G_DEFINE_INTERFACE (ControlPower, control_power, G_TYPE_OBJECT);

static void
control_power_default_init (ControlPowerIface *iface)
{
  /* GObject signals for incoming D-Bus method calls: */
  /**
   * ControlPower::handle-set-power-state:
   * @object: A #ControlPower.
   * @invocation: A #GDBusMethodInvocation.
   * @arg_state: Argument passed by remote caller.
   *
   * Signal emitted when a remote caller is invoking the <link linkend="gdbus-method-org-openbmc-control-Power.setPowerState">setPowerState()</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 control_power_complete_set_power_state() 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-power-state",
    G_TYPE_FROM_INTERFACE (iface),
    G_SIGNAL_RUN_LAST,
    G_STRUCT_OFFSET (ControlPowerIface, handle_set_power_state),
    g_signal_accumulator_true_handled,
    NULL,
    g_cclosure_marshal_generic,
    G_TYPE_BOOLEAN,
    2,
    G_TYPE_DBUS_METHOD_INVOCATION, G_TYPE_INT);

  /**
   * ControlPower::handle-get-power-state:
   * @object: A #ControlPower.
   * @invocation: A #GDBusMethodInvocation.
   *
   * Signal emitted when a remote caller is invoking the <link linkend="gdbus-method-org-openbmc-control-Power.getPowerState">getPowerState()</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 control_power_complete_get_power_state() 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-get-power-state",
    G_TYPE_FROM_INTERFACE (iface),
    G_SIGNAL_RUN_LAST,
    G_STRUCT_OFFSET (ControlPowerIface, handle_get_power_state),
    g_signal_accumulator_true_handled,
    NULL,
    g_cclosure_marshal_generic,
    G_TYPE_BOOLEAN,
    1,
    G_TYPE_DBUS_METHOD_INVOCATION);

  /* GObject signals for received D-Bus signals: */
  /**
   * ControlPower::power-good:
   * @object: A #ControlPower.
   *
   * On the client-side, this signal is emitted whenever the D-Bus signal <link linkend="gdbus-signal-org-openbmc-control-Power.PowerGood">"PowerGood"</link> is received.
   *
   * On the service-side, this signal can be used with e.g. g_signal_emit_by_name() to make the object emit the D-Bus signal.
   */
  g_signal_new ("power-good",
    G_TYPE_FROM_INTERFACE (iface),
    G_SIGNAL_RUN_LAST,
    G_STRUCT_OFFSET (ControlPowerIface, power_good),
    NULL,
    NULL,
    g_cclosure_marshal_generic,
    G_TYPE_NONE,
    0);

  /**
   * ControlPower::power-lost:
   * @object: A #ControlPower.
   *
   * On the client-side, this signal is emitted whenever the D-Bus signal <link linkend="gdbus-signal-org-openbmc-control-Power.PowerLost">"PowerLost"</link> is received.
   *
   * On the service-side, this signal can be used with e.g. g_signal_emit_by_name() to make the object emit the D-Bus signal.
   */
  g_signal_new ("power-lost",
    G_TYPE_FROM_INTERFACE (iface),
    G_SIGNAL_RUN_LAST,
    G_STRUCT_OFFSET (ControlPowerIface, power_lost),
    NULL,
    NULL,
    g_cclosure_marshal_generic,
    G_TYPE_NONE,
    0);

  /* GObject properties for D-Bus properties: */
  /**
   * ControlPower:pgood:
   *
   * Represents the D-Bus property <link linkend="gdbus-property-org-openbmc-control-Power.pgood">"pgood"</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 ("pgood", "pgood", "pgood", G_MININT32, G_MAXINT32, 0, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  /**
   * ControlPower:state:
   *
   * Represents the D-Bus property <link linkend="gdbus-property-org-openbmc-control-Power.state">"state"</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 ("state", "state", "state", G_MININT32, G_MAXINT32, 0, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
}

/**
 * control_power_get_pgood: (skip)
 * @object: A #ControlPower.
 *
 * Gets the value of the <link linkend="gdbus-property-org-openbmc-control-Power.pgood">"pgood"</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 
control_power_get_pgood (ControlPower *object)
{
  return CONTROL_POWER_GET_IFACE (object)->get_pgood (object);
}

/**
 * control_power_set_pgood: (skip)
 * @object: A #ControlPower.
 * @value: The value to set.
 *
 * Sets the <link linkend="gdbus-property-org-openbmc-control-Power.pgood">"pgood"</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
control_power_set_pgood (ControlPower *object, gint value)
{
  g_object_set (G_OBJECT (object), "pgood", value, NULL);
}

/**
 * control_power_get_state: (skip)
 * @object: A #ControlPower.
 *
 * Gets the value of the <link linkend="gdbus-property-org-openbmc-control-Power.state">"state"</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 
control_power_get_state (ControlPower *object)
{
  return CONTROL_POWER_GET_IFACE (object)->get_state (object);
}

/**
 * control_power_set_state: (skip)
 * @object: A #ControlPower.
 * @value: The value to set.
 *
 * Sets the <link linkend="gdbus-property-org-openbmc-control-Power.state">"state"</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
control_power_set_state (ControlPower *object, gint value)
{
  g_object_set (G_OBJECT (object), "state", value, NULL);
}

/**
 * control_power_emit_power_good:
 * @object: A #ControlPower.
 *
 * Emits the <link linkend="gdbus-signal-org-openbmc-control-Power.PowerGood">"PowerGood"</link> D-Bus signal.
 */
void
control_power_emit_power_good (
    ControlPower *object)
{
  g_signal_emit_by_name (object, "power-good");
}

/**
 * control_power_emit_power_lost:
 * @object: A #ControlPower.
 *
 * Emits the <link linkend="gdbus-signal-org-openbmc-control-Power.PowerLost">"PowerLost"</link> D-Bus signal.
 */
void
control_power_emit_power_lost (
    ControlPower *object)
{
  g_signal_emit_by_name (object, "power-lost");
}

/**
 * control_power_call_set_power_state:
 * @proxy: A #ControlPowerProxy.
 * @arg_state: Argument to pass with the method invocation.
 * @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-control-Power.setPowerState">setPowerState()</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 control_power_call_set_power_state_finish() to get the result of the operation.
 *
 * See control_power_call_set_power_state_sync() for the synchronous, blocking version of this method.
 */
void
control_power_call_set_power_state (
    ControlPower *proxy,
    gint arg_state,
    GCancellable *cancellable,
    GAsyncReadyCallback callback,
    gpointer user_data)
{
  g_dbus_proxy_call (G_DBUS_PROXY (proxy),
    "setPowerState",
    g_variant_new ("(i)",
                   arg_state),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    callback,
    user_data);
}

/**
 * control_power_call_set_power_state_finish:
 * @proxy: A #ControlPowerProxy.
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to control_power_call_set_power_state().
 * @error: Return location for error or %NULL.
 *
 * Finishes an operation started with control_power_call_set_power_state().
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
control_power_call_set_power_state_finish (
    ControlPower *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;
}

/**
 * control_power_call_set_power_state_sync:
 * @proxy: A #ControlPowerProxy.
 * @arg_state: Argument to pass with the method invocation.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @error: Return location for error or %NULL.
 *
 * Synchronously invokes the <link linkend="gdbus-method-org-openbmc-control-Power.setPowerState">setPowerState()</link> D-Bus method on @proxy. The calling thread is blocked until a reply is received.
 *
 * See control_power_call_set_power_state() for the asynchronous version of this method.
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
control_power_call_set_power_state_sync (
    ControlPower *proxy,
    gint arg_state,
    GCancellable *cancellable,
    GError **error)
{
  GVariant *_ret;
  _ret = g_dbus_proxy_call_sync (G_DBUS_PROXY (proxy),
    "setPowerState",
    g_variant_new ("(i)",
                   arg_state),
    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;
}

/**
 * control_power_call_get_power_state:
 * @proxy: A #ControlPowerProxy.
 * @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-control-Power.getPowerState">getPowerState()</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 control_power_call_get_power_state_finish() to get the result of the operation.
 *
 * See control_power_call_get_power_state_sync() for the synchronous, blocking version of this method.
 */
void
control_power_call_get_power_state (
    ControlPower *proxy,
    GCancellable *cancellable,
    GAsyncReadyCallback callback,
    gpointer user_data)
{
  g_dbus_proxy_call (G_DBUS_PROXY (proxy),
    "getPowerState",
    g_variant_new ("()"),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    callback,
    user_data);
}

/**
 * control_power_call_get_power_state_finish:
 * @proxy: A #ControlPowerProxy.
 * @out_state: (out): Return location for return parameter or %NULL to ignore.
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to control_power_call_get_power_state().
 * @error: Return location for error or %NULL.
 *
 * Finishes an operation started with control_power_call_get_power_state().
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
control_power_call_get_power_state_finish (
    ControlPower *proxy,
    gint *out_state,
    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,
                 "(i)",
                 out_state);
  g_variant_unref (_ret);
_out:
  return _ret != NULL;
}

/**
 * control_power_call_get_power_state_sync:
 * @proxy: A #ControlPowerProxy.
 * @out_state: (out): Return location for return parameter or %NULL to ignore.
 * @cancellable: (allow-none): A #GCancellable or %NULL.
 * @error: Return location for error or %NULL.
 *
 * Synchronously invokes the <link linkend="gdbus-method-org-openbmc-control-Power.getPowerState">getPowerState()</link> D-Bus method on @proxy. The calling thread is blocked until a reply is received.
 *
 * See control_power_call_get_power_state() for the asynchronous version of this method.
 *
 * Returns: (skip): %TRUE if the call succeded, %FALSE if @error is set.
 */
gboolean
control_power_call_get_power_state_sync (
    ControlPower *proxy,
    gint *out_state,
    GCancellable *cancellable,
    GError **error)
{
  GVariant *_ret;
  _ret = g_dbus_proxy_call_sync (G_DBUS_PROXY (proxy),
    "getPowerState",
    g_variant_new ("()"),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    cancellable,
    error);
  if (_ret == NULL)
    goto _out;
  g_variant_get (_ret,
                 "(i)",
                 out_state);
  g_variant_unref (_ret);
_out:
  return _ret != NULL;
}

/**
 * control_power_complete_set_power_state:
 * @object: A #ControlPower.
 * @invocation: (transfer full): A #GDBusMethodInvocation.
 *
 * Helper function used in service implementations to finish handling invocations of the <link linkend="gdbus-method-org-openbmc-control-Power.setPowerState">setPowerState()</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
control_power_complete_set_power_state (
    ControlPower *object,
    GDBusMethodInvocation *invocation)
{
  g_dbus_method_invocation_return_value (invocation,
    g_variant_new ("()"));
}

/**
 * control_power_complete_get_power_state:
 * @object: A #ControlPower.
 * @invocation: (transfer full): A #GDBusMethodInvocation.
 * @state: Parameter to return.
 *
 * Helper function used in service implementations to finish handling invocations of the <link linkend="gdbus-method-org-openbmc-control-Power.getPowerState">getPowerState()</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
control_power_complete_get_power_state (
    ControlPower *object,
    GDBusMethodInvocation *invocation,
    gint state)
{
  g_dbus_method_invocation_return_value (invocation,
    g_variant_new ("(i)",
                   state));
}

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

/**
 * ControlPowerProxy:
 *
 * The #ControlPowerProxy structure contains only private data and should only be accessed using the provided API.
 */

/**
 * ControlPowerProxyClass:
 * @parent_class: The parent class.
 *
 * Class structure for #ControlPowerProxy.
 */

struct _ControlPowerProxyPrivate
{
  GData *qdata;
};

static void control_power_proxy_iface_init (ControlPowerIface *iface);

#if GLIB_VERSION_MAX_ALLOWED >= GLIB_VERSION_2_38
G_DEFINE_TYPE_WITH_CODE (ControlPowerProxy, control_power_proxy, G_TYPE_DBUS_PROXY,
                         G_ADD_PRIVATE (ControlPowerProxy)
                         G_IMPLEMENT_INTERFACE (TYPE_CONTROL_POWER, control_power_proxy_iface_init));

#else
G_DEFINE_TYPE_WITH_CODE (ControlPowerProxy, control_power_proxy, G_TYPE_DBUS_PROXY,
                         G_IMPLEMENT_INTERFACE (TYPE_CONTROL_POWER, control_power_proxy_iface_init));

#endif
static void
control_power_proxy_finalize (GObject *object)
{
  ControlPowerProxy *proxy = CONTROL_POWER_PROXY (object);
  g_datalist_clear (&proxy->priv->qdata);
  G_OBJECT_CLASS (control_power_proxy_parent_class)->finalize (object);
}

static void
control_power_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 = _control_power_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
control_power_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.control.Power: %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
control_power_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 = _control_power_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.control.Power", info->parent_struct.name, variant),
    G_DBUS_CALL_FLAGS_NONE,
    -1,
    NULL, (GAsyncReadyCallback) control_power_proxy_set_property_cb, (GDBusPropertyInfo *) &info->parent_struct);
  g_variant_unref (variant);
}

static void
control_power_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 *) &_control_power_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_CONTROL_POWER);
  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_CONTROL_POWER);
  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
control_power_proxy_g_properties_changed (GDBusProxy *_proxy,
  GVariant *changed_properties,
  const gchar *const *invalidated_properties)
{
  ControlPowerProxy *proxy = CONTROL_POWER_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 *) &_control_power_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 *) &_control_power_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 
control_power_proxy_get_pgood (ControlPower *object)
{
  ControlPowerProxy *proxy = CONTROL_POWER_PROXY (object);
  GVariant *variant;
  gint value = 0;
  variant = g_dbus_proxy_get_cached_property (G_DBUS_PROXY (proxy), "pgood");
  if (variant != NULL)
    {
      value = g_variant_get_int32 (variant);
      g_variant_unref (variant);
    }
  return value;
}

static gint 
control_power_proxy_get_state (ControlPower *object)
{
  ControlPowerProxy *proxy = CONTROL_POWER_PROXY (object);
  GVariant *variant;
  gint value = 0;
  variant = g_dbus_proxy_get_cached_property (G_DBUS_PROXY (proxy), "state");
  if (variant != NULL)
    {
      value = g_variant_get_int32 (variant);
      g_variant_unref (variant);
    }
  return value;
}

static void
control_power_proxy_init (ControlPowerProxy *proxy)
{
#if GLIB_VERSION_MAX_ALLOWED >= GLIB_VERSION_2_38
  proxy->priv = control_power_proxy_get_instance_private (proxy);
#else
  proxy->priv = G_TYPE_INSTANCE_GET_PRIVATE (proxy, TYPE_CONTROL_POWER_PROXY, ControlPowerProxyPrivate);
#endif

  g_dbus_proxy_set_interface_info (G_DBUS_PROXY (proxy), control_power_interface_info ());
}

static void
control_power_proxy_class_init (ControlPowerProxyClass *klass)
{
  GObjectClass *gobject_class;
  GDBusProxyClass *proxy_class;

  gobject_class = G_OBJECT_CLASS (klass);
  gobject_class->finalize     = control_power_proxy_finalize;
  gobject_class->get_property = control_power_proxy_get_property;
  gobject_class->set_property = control_power_proxy_set_property;

  proxy_class = G_DBUS_PROXY_CLASS (klass);
  proxy_class->g_signal = control_power_proxy_g_signal;
  proxy_class->g_properties_changed = control_power_proxy_g_properties_changed;

  control_power_override_properties (gobject_class, 1);

#if GLIB_VERSION_MAX_ALLOWED < GLIB_VERSION_2_38
  g_type_class_add_private (klass, sizeof (ControlPowerProxyPrivate));
#endif
}

static void
control_power_proxy_iface_init (ControlPowerIface *iface)
{
  iface->get_pgood = control_power_proxy_get_pgood;
  iface->get_state = control_power_proxy_get_state;
}

/**
 * control_power_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-control-Power.top_of_page">org.openbmc.control.Power</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 control_power_proxy_new_finish() to get the result of the operation.
 *
 * See control_power_proxy_new_sync() for the synchronous, blocking version of this constructor.
 */
void
control_power_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_CONTROL_POWER_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.control.Power", NULL);
}

/**
 * control_power_proxy_new_finish:
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to control_power_proxy_new().
 * @error: Return location for error or %NULL
 *
 * Finishes an operation started with control_power_proxy_new().
 *
 * Returns: (transfer full) (type ControlPowerProxy): The constructed proxy object or %NULL if @error is set.
 */
ControlPower *
control_power_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 CONTROL_POWER (ret);
  else
    return NULL;
}

/**
 * control_power_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-control-Power.top_of_page">org.openbmc.control.Power</link>. See g_dbus_proxy_new_sync() for more details.
 *
 * The calling thread is blocked until a reply is received.
 *
 * See control_power_proxy_new() for the asynchronous version of this constructor.
 *
 * Returns: (transfer full) (type ControlPowerProxy): The constructed proxy object or %NULL if @error is set.
 */
ControlPower *
control_power_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_CONTROL_POWER_PROXY, cancellable, error, "g-flags", flags, "g-name", name, "g-connection", connection, "g-object-path", object_path, "g-interface-name", "org.openbmc.control.Power", NULL);
  if (ret != NULL)
    return CONTROL_POWER (ret);
  else
    return NULL;
}


/**
 * control_power_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 control_power_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 control_power_proxy_new_for_bus_finish() to get the result of the operation.
 *
 * See control_power_proxy_new_for_bus_sync() for the synchronous, blocking version of this constructor.
 */
void
control_power_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_CONTROL_POWER_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.control.Power", NULL);
}

/**
 * control_power_proxy_new_for_bus_finish:
 * @res: The #GAsyncResult obtained from the #GAsyncReadyCallback passed to control_power_proxy_new_for_bus().
 * @error: Return location for error or %NULL
 *
 * Finishes an operation started with control_power_proxy_new_for_bus().
 *
 * Returns: (transfer full) (type ControlPowerProxy): The constructed proxy object or %NULL if @error is set.
 */
ControlPower *
control_power_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 CONTROL_POWER (ret);
  else
    return NULL;
}

/**
 * control_power_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 control_power_proxy_new_sync() but takes a #GBusType instead of a #GDBusConnection.
 *
 * The calling thread is blocked until a reply is received.
 *
 * See control_power_proxy_new_for_bus() for the asynchronous version of this constructor.
 *
 * Returns: (transfer full) (type ControlPowerProxy): The constructed proxy object or %NULL if @error is set.
 */
ControlPower *
control_power_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_CONTROL_POWER_PROXY, cancellable, error, "g-flags", flags, "g-name", name, "g-bus-type", bus_type, "g-object-path", object_path, "g-interface-name", "org.openbmc.control.Power", NULL);
  if (ret != NULL)
    return CONTROL_POWER (ret);
  else
    return NULL;
}


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

/**
 * ControlPowerSkeleton:
 *
 * The #ControlPowerSkeleton structure contains only private data and should only be accessed using the provided API.
 */

/**
 * ControlPowerSkeletonClass:
 * @parent_class: The parent class.
 *
 * Class structure for #ControlPowerSkeleton.
 */

struct _ControlPowerSkeletonPrivate
{
  GValue *properties;
  GList *changed_properties;
  GSource *changed_properties_idle_source;
  GMainContext *context;
  GMutex lock;
};

static void
_control_power_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)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_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_CONTROL_POWER);
  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_CONTROL_POWER);
  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 *
_control_power_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)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_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 *) &_control_power_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
_control_power_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)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_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 *) &_control_power_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 _control_power_skeleton_vtable =
{
  _control_power_skeleton_handle_method_call,
  _control_power_skeleton_handle_get_property,
  _control_power_skeleton_handle_set_property,
  {NULL}
};

static GDBusInterfaceInfo *
control_power_skeleton_dbus_interface_get_info (GDBusInterfaceSkeleton *skeleton G_GNUC_UNUSED)
{
  return control_power_interface_info ();
}

static GDBusInterfaceVTable *
control_power_skeleton_dbus_interface_get_vtable (GDBusInterfaceSkeleton *skeleton G_GNUC_UNUSED)
{
  return (GDBusInterfaceVTable *) &_control_power_skeleton_vtable;
}

static GVariant *
control_power_skeleton_dbus_interface_get_properties (GDBusInterfaceSkeleton *_skeleton)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_SKELETON (_skeleton);

  GVariantBuilder builder;
  guint n;
  g_variant_builder_init (&builder, G_VARIANT_TYPE ("a{sv}"));
  if (_control_power_interface_info.parent_struct.properties == NULL)
    goto out;
  for (n = 0; _control_power_interface_info.parent_struct.properties[n] != NULL; n++)
    {
      GDBusPropertyInfo *info = _control_power_interface_info.parent_struct.properties[n];
      if (info->flags & G_DBUS_PROPERTY_INFO_FLAGS_READABLE)
        {
          GVariant *value;
          value = _control_power_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.control.Power", 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 _control_power_emit_changed (gpointer user_data);

static void
control_power_skeleton_dbus_interface_flush (GDBusInterfaceSkeleton *_skeleton)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_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)
    _control_power_emit_changed (skeleton);
}

static void
_control_power_on_signal_power_good (
    ControlPower *object)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_SKELETON (object);

  GList      *connections, *l;
  GVariant   *signal_variant;
  connections = g_dbus_interface_skeleton_get_connections (G_DBUS_INTERFACE_SKELETON (skeleton));

  signal_variant = g_variant_ref_sink (g_variant_new ("()"));
  for (l = connections; l != NULL; l = l->next)
    {
      GDBusConnection *connection = l->data;
      g_dbus_connection_emit_signal (connection,
        NULL, g_dbus_interface_skeleton_get_object_path (G_DBUS_INTERFACE_SKELETON (skeleton)), "org.openbmc.control.Power", "PowerGood",
        signal_variant, NULL);
    }
  g_variant_unref (signal_variant);
  g_list_free_full (connections, g_object_unref);
}

static void
_control_power_on_signal_power_lost (
    ControlPower *object)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_SKELETON (object);

  GList      *connections, *l;
  GVariant   *signal_variant;
  connections = g_dbus_interface_skeleton_get_connections (G_DBUS_INTERFACE_SKELETON (skeleton));

  signal_variant = g_variant_ref_sink (g_variant_new ("()"));
  for (l = connections; l != NULL; l = l->next)
    {
      GDBusConnection *connection = l->data;
      g_dbus_connection_emit_signal (connection,
        NULL, g_dbus_interface_skeleton_get_object_path (G_DBUS_INTERFACE_SKELETON (skeleton)), "org.openbmc.control.Power", "PowerLost",
        signal_variant, NULL);
    }
  g_variant_unref (signal_variant);
  g_list_free_full (connections, g_object_unref);
}

static void control_power_skeleton_iface_init (ControlPowerIface *iface);
#if GLIB_VERSION_MAX_ALLOWED >= GLIB_VERSION_2_38
G_DEFINE_TYPE_WITH_CODE (ControlPowerSkeleton, control_power_skeleton, G_TYPE_DBUS_INTERFACE_SKELETON,
                         G_ADD_PRIVATE (ControlPowerSkeleton)
                         G_IMPLEMENT_INTERFACE (TYPE_CONTROL_POWER, control_power_skeleton_iface_init));

#else
G_DEFINE_TYPE_WITH_CODE (ControlPowerSkeleton, control_power_skeleton, G_TYPE_DBUS_INTERFACE_SKELETON,
                         G_IMPLEMENT_INTERFACE (TYPE_CONTROL_POWER, control_power_skeleton_iface_init));

#endif
static void
control_power_skeleton_finalize (GObject *object)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_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 (control_power_skeleton_parent_class)->finalize (object);
}

static void
control_power_skeleton_get_property (GObject      *object,
  guint         prop_id,
  GValue       *value,
  GParamSpec   *pspec G_GNUC_UNUSED)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_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
_control_power_emit_changed (gpointer user_data)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_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.control.Power",
                                           &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
_control_power_schedule_emit_changed (ControlPowerSkeleton *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
control_power_skeleton_notify (GObject      *object,
  GParamSpec *pspec G_GNUC_UNUSED)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_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, _control_power_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
control_power_skeleton_set_property (GObject      *object,
  guint         prop_id,
  const GValue *value,
  GParamSpec   *pspec)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_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)
        _control_power_schedule_emit_changed (skeleton, _control_power_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
control_power_skeleton_init (ControlPowerSkeleton *skeleton)
{
#if GLIB_VERSION_MAX_ALLOWED >= GLIB_VERSION_2_38
  skeleton->priv = control_power_skeleton_get_instance_private (skeleton);
#else
  skeleton->priv = G_TYPE_INSTANCE_GET_PRIVATE (skeleton, TYPE_CONTROL_POWER_SKELETON, ControlPowerSkeletonPrivate);
#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_INT);
}

static gint 
control_power_skeleton_get_pgood (ControlPower *object)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_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 gint 
control_power_skeleton_get_state (ControlPower *object)
{
  ControlPowerSkeleton *skeleton = CONTROL_POWER_SKELETON (object);
  gint value;
  g_mutex_lock (&skeleton->priv->lock);
  value = g_value_get_int (&(skeleton->priv->properties[1]));
  g_mutex_unlock (&skeleton->priv->lock);
  return value;
}

static void
control_power_skeleton_class_init (ControlPowerSkeletonClass *klass)
{
  GObjectClass *gobject_class;
  GDBusInterfaceSkeletonClass *skeleton_class;

  gobject_class = G_OBJECT_CLASS (klass);
  gobject_class->finalize = control_power_skeleton_finalize;
  gobject_class->get_property = control_power_skeleton_get_property;
  gobject_class->set_property = control_power_skeleton_set_property;
  gobject_class->notify       = control_power_skeleton_notify;


  control_power_override_properties (gobject_class, 1);

  skeleton_class = G_DBUS_INTERFACE_SKELETON_CLASS (klass);
  skeleton_class->get_info = control_power_skeleton_dbus_interface_get_info;
  skeleton_class->get_properties = control_power_skeleton_dbus_interface_get_properties;
  skeleton_class->flush = control_power_skeleton_dbus_interface_flush;
  skeleton_class->get_vtable = control_power_skeleton_dbus_interface_get_vtable;

#if GLIB_VERSION_MAX_ALLOWED < GLIB_VERSION_2_38
  g_type_class_add_private (klass, sizeof (ControlPowerSkeletonPrivate));
#endif
}

static void
control_power_skeleton_iface_init (ControlPowerIface *iface)
{
  iface->power_good = _control_power_on_signal_power_good;
  iface->power_lost = _control_power_on_signal_power_lost;
  iface->get_pgood = control_power_skeleton_get_pgood;
  iface->get_state = control_power_skeleton_get_state;
}

/**
 * control_power_skeleton_new:
 *
 * Creates a skeleton object for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-control-Power.top_of_page">org.openbmc.control.Power</link>.
 *
 * Returns: (transfer full) (type ControlPowerSkeleton): The skeleton object.
 */
ControlPower *
control_power_skeleton_new (void)
{
  return CONTROL_POWER (g_object_new (TYPE_CONTROL_POWER_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:control-power:
   *
   * The #ControlPower instance corresponding to the D-Bus interface <link linkend="gdbus-interface-org-openbmc-control-Power.top_of_page">org.openbmc.control.Power</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 ("control-power", "control-power", "control-power", TYPE_CONTROL_POWER, G_PARAM_READWRITE|G_PARAM_STATIC_STRINGS));

}

/**
 * object_get_control_power:
 * @object: A #Object.
 *
 * Gets the #ControlPower instance for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-control-Power.top_of_page">org.openbmc.control.Power</link> on @object, if any.
 *
 * Returns: (transfer full): A #ControlPower that must be freed with g_object_unref() or %NULL if @object does not implement the interface.
 */
ControlPower *object_get_control_power (Object *object)
{
  GDBusInterface *ret;
  ret = g_dbus_object_get_interface (G_DBUS_OBJECT (object), "org.openbmc.control.Power");
  if (ret == NULL)
    return NULL;
  return CONTROL_POWER (ret);
}


/**
 * object_peek_control_power: (skip)
 * @object: A #Object.
 *
 * Like object_get_control_power() 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 #ControlPower or %NULL if @object does not implement the interface. Do not free the returned object, it is owned by @object.
 */
ControlPower *object_peek_control_power (Object *object)
{
  GDBusInterface *ret;
  ret = g_dbus_object_get_interface (G_DBUS_OBJECT (object), "org.openbmc.control.Power");
  if (ret == NULL)
    return NULL;
  g_object_unref (ret);
  return CONTROL_POWER (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.control.Power");
      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, "control-power");
}

/**
 * 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_CONTROL_POWER (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.control.Power");
        }
      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.control.Power");
      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, "control-power");
}

/**
 * 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_control_power:
 * @object: A #ObjectSkeleton.
 * @interface_: (allow-none): A #ControlPower or %NULL to clear the interface.
 *
 * Sets the #ControlPower instance for the D-Bus interface <link linkend="gdbus-interface-org-openbmc-control-Power.top_of_page">org.openbmc.control.Power</link> on @object.
 */
void object_skeleton_set_control_power (ObjectSkeleton *object, ControlPower *interface_)
{
  g_object_set (G_OBJECT (object), "control-power", 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.control.Power", GSIZE_TO_POINTER (TYPE_CONTROL_POWER_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;
}


