summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRichard Hughes <richard@hughsie.com>2011-03-30 15:09:57 +0100
committerRichard Hughes <richard@hughsie.com>2011-05-04 17:57:13 +0100
commit0fd304c3f3ed41b503fdd4b0e36fe84ba939fb69 (patch)
tree0b4b47e6c5f217573fc8b2021532094035c6a767
parent62024c49c8de4c447a1b04a927f32366f3760960 (diff)
Add new NotifySleep() and NotifyResume() signals that include the sleep type
This allows session power managers to do different actions depending on whether the user is suspending or hibernating. This allows the session policy agent to poke other things (for instance, the screensaver) even if another process initiated the sleep. This is based on a patch from Phillip Susi <psusi@cfl.rr.com>, many thanks.
-rw-r--r--libupower-glib/up-client.c78
-rw-r--r--libupower-glib/up-client.h11
-rw-r--r--libupower-glib/up-types.c52
-rw-r--r--libupower-glib/up-types.h16
-rw-r--r--src/org.freedesktop.UPower.xml56
-rw-r--r--src/up-daemon.c31
-rw-r--r--src/up-daemon.h1
7 files changed, 237 insertions, 8 deletions
diff --git a/libupower-glib/up-client.c b/libupower-glib/up-client.c
index 3da75ef..8dccbde 100644
--- a/libupower-glib/up-client.c
+++ b/libupower-glib/up-client.c
@@ -74,6 +74,8 @@ enum {
UP_CLIENT_DEVICE_CHANGED,
UP_CLIENT_DEVICE_REMOVED,
UP_CLIENT_CHANGED,
+ UP_CLIENT_NOTIFY_SLEEP,
+ UP_CLIENT_NOTIFY_RESUME,
UP_CLIENT_LAST_SIGNAL
};
@@ -251,6 +253,7 @@ out:
/**
* up_client_about_to_sleep_sync:
* @client: a #UpClient instance.
+ * @sleep_kind: a sleep type, e.g. %UP_SLEEP_KIND_SUSPEND
* @cancellable: a #GCancellable or %NULL
* @error: a #GError, or %NULL.
*
@@ -259,10 +262,13 @@ out:
*
* Return value: TRUE if system suspended okay, FALSE other wise.
*
- * Since: 0.9.1
+ * Since: 0.9.11
**/
gboolean
-up_client_about_to_sleep_sync (UpClient *client, GCancellable *cancellable, GError **error)
+up_client_about_to_sleep_sync (UpClient *client,
+ UpSleepKind sleep_kind,
+ GCancellable *cancellable,
+ GError **error)
{
gboolean ret;
GError *error_local = NULL;
@@ -271,7 +277,9 @@ up_client_about_to_sleep_sync (UpClient *client, GCancellable *cancellable, GErr
g_return_val_if_fail (client->priv->proxy != NULL, FALSE);
ret = dbus_g_proxy_call (client->priv->proxy, "AboutToSleep", &error_local,
- G_TYPE_INVALID, G_TYPE_INVALID);
+ G_TYPE_STRING, sleep_kind,
+ G_TYPE_INVALID,
+ G_TYPE_INVALID);
if (!ret) {
/* DBus might time out, which is okay */
if (g_error_matches (error_local, DBUS_GERROR, DBUS_GERROR_NO_REPLY)) {
@@ -656,6 +664,26 @@ up_device_changed_cb (DBusGProxy *proxy, const gchar *object_path, UpClient *cli
}
/*
+ * up_client_notify_sleep_cb:
+ */
+static void
+up_client_notify_sleep_cb (DBusGProxy *proxy, const gchar *sleep_kind, UpClient *client)
+{
+ g_signal_emit (client, signals [UP_CLIENT_NOTIFY_SLEEP], 0,
+ up_sleep_kind_from_string (sleep_kind));
+}
+
+/*
+ * up_client_notify_resume_cb:
+ */
+static void
+up_client_notify_resume_cb (DBusGProxy *proxy, const gchar *sleep_kind, UpClient *client)
+{
+ g_signal_emit (client, signals [UP_CLIENT_NOTIFY_RESUME], 0,
+ up_sleep_kind_from_string (sleep_kind));
+}
+
+/*
* up_client_removed_cb:
*/
static void
@@ -915,7 +943,7 @@ up_client_class_init (UpClientClass *klass)
/**
* UpClient::changed:
- * @client: the #UpDevice instance that emitted the signal
+ * @client: the #UpClient instance that emitted the signal
*
* The ::changed signal is emitted when properties may have changed.
*
@@ -928,6 +956,42 @@ up_client_class_init (UpClientClass *klass)
NULL, NULL, g_cclosure_marshal_VOID__VOID,
G_TYPE_NONE, 0);
+ /**
+ * UpClient::notify-sleep:
+ * @client: the #UpClient instance that emitted the signal
+ * @sleep_kind: the #UpSleepKind
+ *
+ * The ::notify-sleep signal is emitted when system sleep is
+ * about to occur. Applications have about 1 second to do
+ * anything they need to do. There is no way to stop the sleep
+ * process.
+ *
+ * Since: 0.9.11
+ **/
+ signals [UP_CLIENT_NOTIFY_SLEEP] =
+ g_signal_new ("notify-sleep",
+ G_TYPE_FROM_CLASS (object_class), G_SIGNAL_RUN_LAST,
+ G_STRUCT_OFFSET (UpClientClass, notify_sleep),
+ NULL, NULL, g_cclosure_marshal_VOID__UINT,
+ G_TYPE_NONE, 1, G_TYPE_UINT);
+
+ /**
+ * UpClient::notify-resume:
+ * @client: the #UpClient instance that emitted the signal
+ * @sleep_kind: the #UpSleepKind
+ *
+ * The ::notify-resume signal is emitted when the system has
+ * resumed.
+ *
+ * Since: 0.9.11
+ **/
+ signals [UP_CLIENT_NOTIFY_RESUME] =
+ g_signal_new ("notify-resume",
+ G_TYPE_FROM_CLASS (object_class), G_SIGNAL_RUN_LAST,
+ G_STRUCT_OFFSET (UpClientClass, notify_resume),
+ NULL, NULL, g_cclosure_marshal_VOID__UINT,
+ G_TYPE_NONE, 1, G_TYPE_UINT);
+
g_type_class_add_private (klass, sizeof (UpClientPrivate));
}
@@ -1017,6 +1081,8 @@ up_client_init (UpClient *client)
dbus_g_proxy_add_signal (client->priv->proxy, "DeviceRemoved", G_TYPE_STRING, G_TYPE_INVALID);
dbus_g_proxy_add_signal (client->priv->proxy, "DeviceChanged", G_TYPE_STRING, G_TYPE_INVALID);
dbus_g_proxy_add_signal (client->priv->proxy, "Changed", G_TYPE_INVALID);
+ dbus_g_proxy_add_signal (client->priv->proxy, "NotifySleep", G_TYPE_STRING, G_TYPE_INVALID);
+ dbus_g_proxy_add_signal (client->priv->proxy, "NotifyResume", G_TYPE_STRING, G_TYPE_INVALID);
/* all callbacks */
dbus_g_proxy_connect_signal (client->priv->proxy, "DeviceAdded",
@@ -1027,6 +1093,10 @@ up_client_init (UpClient *client)
G_CALLBACK (up_device_changed_cb), client, NULL);
dbus_g_proxy_connect_signal (client->priv->proxy, "Changed",
G_CALLBACK (up_client_changed_cb), client, NULL);
+ dbus_g_proxy_connect_signal (client->priv->proxy, "NotifySleep",
+ G_CALLBACK (up_client_notify_sleep_cb), client, NULL);
+ dbus_g_proxy_connect_signal (client->priv->proxy, "NotifyResume",
+ G_CALLBACK (up_client_notify_resume_cb), client, NULL);
out:
return;
}
diff --git a/libupower-glib/up-client.h b/libupower-glib/up-client.h
index aa522ab..482cd90 100644
--- a/libupower-glib/up-client.h
+++ b/libupower-glib/up-client.h
@@ -55,11 +55,15 @@ typedef struct
GObjectClass parent_class;
void (*device_added) (UpClient *client,
UpDevice *device);
- void (*device_changed) (UpClient *client,
+ void (*device_changed) (UpClient *client,
UpDevice *device);
- void (*device_removed) (UpClient *client,
+ void (*device_removed) (UpClient *client,
UpDevice *device);
- void (*changed) (UpClient *client);
+ void (*changed) (UpClient *client);
+ void (*notify_sleep) (UpClient *client,
+ UpSleepKind sleep_kind);
+ void (*notify_resume) (UpClient *client,
+ UpSleepKind sleep_kind);
/*< private >*/
/* Padding for future expansion */
void (*_up_client_reserved1) (void);
@@ -87,6 +91,7 @@ gboolean up_client_suspend_sync (UpClient *client,
GCancellable *cancellable,
GError **error);
gboolean up_client_about_to_sleep_sync (UpClient *client,
+ UpSleepKind sleep_kind,
GCancellable *cancellable,
GError **error);
gboolean up_client_hibernate_sync (UpClient *client,
diff --git a/libupower-glib/up-types.c b/libupower-glib/up-types.c
index 9109c54..4f7643f 100644
--- a/libupower-glib/up-types.c
+++ b/libupower-glib/up-types.c
@@ -300,3 +300,55 @@ up_qos_kind_from_string (const gchar *type)
return UP_QOS_KIND_UNKNOWN;
}
+/**
+ * up_sleep_kind_to_string:
+ *
+ * Converts a #UpSleepKind to a string.
+ *
+ * Return value: identifier string
+ *
+ * Since: 0.9.10
+ **/
+const gchar *
+up_sleep_kind_to_string (UpSleepKind sleep_kind_enum)
+{
+ const gchar *sleep_kind = NULL;
+ switch (sleep_kind_enum) {
+ case UP_SLEEP_KIND_SUSPEND:
+ sleep_kind = "suspend";
+ break;
+ case UP_SLEEP_KIND_HIBERNATE:
+ sleep_kind = "hibernate";
+ break;
+ case UP_SLEEP_KIND_HYBRID:
+ sleep_kind = "hybrid";
+ break;
+ default:
+ sleep_kind = "unknown";
+ break;
+ }
+ return sleep_kind;
+}
+
+/**
+ * up_sleep_kind_from_string:
+ *
+ * Converts a string to a #UpSleepKind.
+ *
+ * Return value: enumerated value
+ *
+ * Since: 0.9.10
+ **/
+UpSleepKind
+up_sleep_kind_from_string (const gchar *sleep_kind)
+{
+ if (sleep_kind == NULL)
+ return UP_SLEEP_KIND_UNKNOWN;
+ if (g_strcmp0 (sleep_kind, "suspend") == 0)
+ return UP_SLEEP_KIND_SUSPEND;
+ if (g_strcmp0 (sleep_kind, "hibernate") == 0)
+ return UP_SLEEP_KIND_HIBERNATE;
+ if (g_strcmp0 (sleep_kind, "hybrid") == 0)
+ return UP_SLEEP_KIND_HYBRID;
+ return UP_SLEEP_KIND_UNKNOWN;
+}
diff --git a/libupower-glib/up-types.h b/libupower-glib/up-types.h
index 4e1d285..083d3d9 100644
--- a/libupower-glib/up-types.h
+++ b/libupower-glib/up-types.h
@@ -95,6 +95,19 @@ typedef enum {
UP_QOS_KIND_LAST
} UpQosKind;
+/**
+ * UpSleepKind:
+ *
+ * The type of QOS request.
+ **/
+typedef enum {
+ UP_SLEEP_KIND_UNKNOWN,
+ UP_SLEEP_KIND_SUSPEND,
+ UP_SLEEP_KIND_HIBERNATE,
+ UP_SLEEP_KIND_HYBRID,
+ UP_SLEEP_KIND_LAST
+} UpSleepKind;
+
const gchar *up_device_kind_to_string (UpDeviceKind type_enum);
const gchar *up_device_state_to_string (UpDeviceState state_enum);
const gchar *up_device_technology_to_string (UpDeviceTechnology technology_enum);
@@ -103,6 +116,9 @@ UpDeviceState up_device_state_from_string (const gchar *state);
UpDeviceTechnology up_device_technology_from_string (const gchar *technology);
const gchar *up_qos_kind_to_string (UpQosKind type);
UpQosKind up_qos_kind_from_string (const gchar *type);
+const gchar *up_sleep_kind_to_string (UpSleepKind sleep_kind_enum);
+UpSleepKind up_sleep_kind_from_string (const gchar *sleep_kind);
+
G_END_DECLS
diff --git a/src/org.freedesktop.UPower.xml b/src/org.freedesktop.UPower.xml
index c37d218..a3f0004 100644
--- a/src/org.freedesktop.UPower.xml
+++ b/src/org.freedesktop.UPower.xml
@@ -119,12 +119,36 @@ method return sender=:1.386 -> dest=:1.451 reply_serial=2
<doc:para>
This signal is sent when the session is about to be suspended or
hibernated.
+ </doc:para>
+ <doc:para>
+ This signal is DEPRECATED. Use NotifySleep() instead.
+ </doc:para>
+ </doc:description>
+ </doc:doc>
+ </signal>
+
+ <!-- ************************************************************ -->
+
+ <signal name="NotifySleep">
+ <doc:doc>
+ <doc:description>
+ <doc:para>
+ This signal is sent when the session is about to be suspended or
+ hibernated.
Session and system programs have one second to do anything required
before the sleep action is taken (such as sending out Avahi or
Jabber messages).
</doc:para>
</doc:description>
</doc:doc>
+ <arg name="action" direction="out" type="s">
+ <doc:doc>
+ <doc:summary>
+ The sleep action type, e.g. <doc:tt>suspend</doc:tt>,
+ <doc:tt>hibernate</doc:tt> or <doc:tt>hybrid</doc:tt>.
+ </doc:summary>
+ </doc:doc>
+ </arg>
</signal>
<!-- ************************************************************ -->
@@ -135,11 +159,35 @@ method return sender=:1.386 -> dest=:1.451 reply_serial=2
<doc:para>
This signal is sent when the session has just returned from
Suspend() or Hibernate().
+ </doc:para>
+ <doc:para>
+ This signal is DEPRECATED. Use NotifyResume() instead.
+ </doc:para>
+ </doc:description>
+ </doc:doc>
+ </signal>
+
+ <!-- ************************************************************ -->
+
+ <signal name="NotifyResume">
+ <doc:doc>
+ <doc:description>
+ <doc:para>
+ This signal is sent when the session has just returned from
+ Suspend() or Hibernate().
Session and system programs can then do anything required (such as
sending out Avahi or Jabber messages).
</doc:para>
</doc:description>
</doc:doc>
+ <arg name="action" direction="out" type="s">
+ <doc:doc>
+ <doc:summary>
+ The sleep action type, e.g. <doc:tt>suspend</doc:tt>,
+ <doc:tt>hibernate</doc:tt> or <doc:tt>hybrid</doc:tt>.
+ </doc:summary>
+ </doc:doc>
+ </arg>
</signal>
<!-- ************************************************************ -->
@@ -168,6 +216,14 @@ method return sender=:1.386 -> dest=:1.451 reply_serial=2
</doc:para>
</doc:description>
</doc:doc>
+ <arg name="action" direction="in" type="s">
+ <doc:doc>
+ <doc:summary>
+ The sleep action type, e.g. <doc:tt>suspend</doc:tt> or
+ <doc:tt>hibernate</doc:tt>.
+ </doc:summary>
+ </doc:doc>
+ </arg>
</method>
<!-- ************************************************************ -->
diff --git a/src/up-daemon.c b/src/up-daemon.c
index 0adf705..db02eae 100644
--- a/src/up-daemon.c
+++ b/src/up-daemon.c
@@ -65,6 +65,8 @@ enum
SIGNAL_CHANGED,
SIGNAL_SLEEPING,
SIGNAL_RESUMING,
+ SIGNAL_NOTIFY_SLEEP,
+ SIGNAL_NOTIFY_RESUME,
SIGNAL_LAST,
};
@@ -95,6 +97,7 @@ struct UpDaemonPrivate
guint about_to_sleep_id;
guint conf_sleep_timeout;
gboolean conf_allow_hibernate_encrypted_swap;
+ const gchar *sleep_kind;
};
static void up_daemon_finalize (GObject *object);
@@ -330,7 +333,9 @@ up_daemon_enumerate_devices (UpDaemon *daemon, DBusGMethodInvocation *context)
* up_daemon_about_to_sleep:
**/
gboolean
-up_daemon_about_to_sleep (UpDaemon *daemon, DBusGMethodInvocation *context)
+up_daemon_about_to_sleep (UpDaemon *daemon,
+ const gchar *sleep_kind,
+ DBusGMethodInvocation *context)
{
PolkitSubject *subject = NULL;
GError *error;
@@ -357,6 +362,8 @@ up_daemon_about_to_sleep (UpDaemon *daemon, DBusGMethodInvocation *context)
/* we've told the clients we're going down */
g_debug ("emitting sleeping");
g_signal_emit (daemon, signals[SIGNAL_SLEEPING], 0);
+ g_signal_emit (daemon, signals[SIGNAL_NOTIFY_SLEEP], 0,
+ sleep_kind);
g_timer_start (priv->about_to_sleep_timer);
daemon->priv->sent_sleeping_signal = TRUE;
@@ -403,6 +410,8 @@ up_daemon_deferred_sleep_cb (UpDaemonDeferredSleep *sleep)
/* emit signal for session components */
g_debug ("emitting resuming");
g_signal_emit (daemon, signals[SIGNAL_RESUMING], 0);
+ g_signal_emit (daemon, signals[SIGNAL_NOTIFY_RESUME], 0,
+ priv->sleep_kind);
/* reset the about-to-sleep logic */
g_timer_reset (priv->about_to_sleep_timer);
@@ -447,6 +456,8 @@ up_daemon_deferred_sleep (UpDaemon *daemon, const gchar *command, DBusGMethodInv
if (!priv->sent_sleeping_signal) {
g_debug ("no AboutToSleep(), so emitting ::Sleeping()");
g_signal_emit (daemon, signals[SIGNAL_SLEEPING], 0);
+ g_signal_emit (daemon, signals[SIGNAL_NOTIFY_SLEEP], 0,
+ priv->sleep_kind);
priv->about_to_sleep_id = g_timeout_add (priv->conf_sleep_timeout,
(GSourceFunc) up_daemon_deferred_sleep_cb, sleep);
#if GLIB_CHECK_VERSION(2,25,8)
@@ -513,6 +524,7 @@ up_daemon_suspend (UpDaemon *daemon, DBusGMethodInvocation *context)
}
/* do this deferred action */
+ priv->sleep_kind = "suspend";
command = up_backend_get_suspend_command (priv->backend);
up_daemon_deferred_sleep (daemon, command, context);
out:
@@ -637,6 +649,7 @@ up_daemon_hibernate (UpDaemon *daemon, DBusGMethodInvocation *context)
}
/* do this deferred action */
+ priv->sleep_kind = "hibernate";
command = up_backend_get_hibernate_command (priv->backend);
up_daemon_deferred_sleep (daemon, command, context);
out:
@@ -1274,6 +1287,14 @@ up_daemon_class_init (UpDaemonClass *klass)
g_cclosure_marshal_VOID__VOID,
G_TYPE_NONE, 0);
+ signals[SIGNAL_NOTIFY_SLEEP] =
+ g_signal_new ("notify-sleep",
+ G_OBJECT_CLASS_TYPE (klass),
+ G_SIGNAL_RUN_LAST | G_SIGNAL_DETAILED,
+ 0, NULL, NULL,
+ g_cclosure_marshal_VOID__STRING,
+ G_TYPE_NONE, 1, G_TYPE_STRING);
+
signals[SIGNAL_RESUMING] =
g_signal_new ("resuming",
G_OBJECT_CLASS_TYPE (klass),
@@ -1282,6 +1303,14 @@ up_daemon_class_init (UpDaemonClass *klass)
g_cclosure_marshal_VOID__VOID,
G_TYPE_NONE, 0);
+ signals[SIGNAL_NOTIFY_RESUME] =
+ g_signal_new ("notify-resume",
+ G_OBJECT_CLASS_TYPE (klass),
+ G_SIGNAL_RUN_LAST | G_SIGNAL_DETAILED,
+ 0, NULL, NULL,
+ g_cclosure_marshal_VOID__STRING,
+ G_TYPE_NONE, 1, G_TYPE_STRING);
+
g_object_class_install_property (object_class,
PROP_DAEMON_VERSION,
g_param_spec_string ("daemon-version",
diff --git a/src/up-daemon.h b/src/up-daemon.h
index 09252b2..6feff2f 100644
--- a/src/up-daemon.h
+++ b/src/up-daemon.h
@@ -98,6 +98,7 @@ gboolean up_daemon_get_low_battery (UpDaemon *daemon,
gboolean up_daemon_suspend (UpDaemon *daemon,
DBusGMethodInvocation *context);
gboolean up_daemon_about_to_sleep (UpDaemon *daemon,
+ const gchar *sleep_kind,
DBusGMethodInvocation *context);
gboolean up_daemon_suspend_allowed (UpDaemon *daemon,
DBusGMethodInvocation *context);