summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJannis Pohlmann <jannis.pohlmann@codethink.co.uk>2012-08-06 13:06:43 +0100
committerJannis Pohlmann <jannis.pohlmann@codethink.co.uk>2012-08-06 14:11:59 +0100
commit39dcfd5d9381c4494fad324b50588f9df1bc946e (patch)
tree2686371bdf2d15b81d709231e437e46ba330ace6
parent53d25fc8ddba4de1340cad4885ba9fce880bc3fe (diff)
downloadnode-startup-controller-39dcfd5d9381c4494fad324b50588f9df1bc946e.tar.gz
Unregister all shutdown consumers when receiving SIGTERM
systemd uses SIGTERM to stop its units. We want to cleanly shut down the NSC when receiving this signal. Part of that is to unregister all shutdown consumers. If we don't do this, the NSM will later during its shutdown phase call all shutdown consumers registered by the NSC. And if the NSC was no longer running, this would cause the NSM to wait for a timeout for every single one of these shutdown consumers. Obviously, that is not desirable.
-rw-r--r--node-startup-controller/node-startup-controller-application.c125
1 files changed, 88 insertions, 37 deletions
diff --git a/node-startup-controller/node-startup-controller-application.c b/node-startup-controller/node-startup-controller-application.c
index b2edc1b..e3684fa 100644
--- a/node-startup-controller/node-startup-controller-application.c
+++ b/node-startup-controller/node-startup-controller-application.c
@@ -52,29 +52,31 @@ enum
-static void node_startup_controller_application_finalize (GObject *object);
-static void node_startup_controller_application_constructed (GObject *object);
-static void node_startup_controller_application_get_property (GObject *object,
- guint prop_id,
- GValue *value,
- GParamSpec *pspec);
-static gboolean node_startup_controller_application_handle_lifecycle_request (ShutdownConsumer *interface,
- GDBusMethodInvocation *invocation,
- NSMShutdownType request,
- guint request_id,
- NodeStartupControllerApplication *application);
-static void node_startup_controller_application_handle_register_finish (GObject *object,
- GAsyncResult *res,
- gpointer user_data);
-static void node_startup_controller_application_handle_unregister_finish (GObject *object,
- GAsyncResult *res,
- gpointer user_data);
-static void node_startup_controller_application_set_property (GObject *object,
- guint prop_id,
- const GValue *value,
- GParamSpec *pspec);
-static void node_startup_controller_application_luc_groups_started (LUCStarter *starter,
- NodeStartupControllerApplication *application);
+static void node_startup_controller_application_finalize (GObject *object);
+static void node_startup_controller_application_constructed (GObject *object);
+static void node_startup_controller_application_get_property (GObject *object,
+ guint prop_id,
+ GValue *value,
+ GParamSpec *pspec);
+static gboolean node_startup_controller_application_handle_lifecycle_request (ShutdownConsumer *interface,
+ GDBusMethodInvocation *invocation,
+ NSMShutdownType request,
+ guint request_id,
+ NodeStartupControllerApplication *application);
+static void node_startup_controller_application_handle_register_finish (GObject *object,
+ GAsyncResult *res,
+ gpointer user_data);
+static void node_startup_controller_application_handle_unregister_finish (GObject *object,
+ GAsyncResult *res,
+ gpointer user_data);
+static void node_startup_controller_application_set_property (GObject *object,
+ guint prop_id,
+ const GValue *value,
+ GParamSpec *pspec);
+static void node_startup_controller_application_luc_groups_started (LUCStarter *starter,
+ NodeStartupControllerApplication *application);
+static gboolean node_startup_controller_application_handle_sigterm (gpointer user_data);
+static void node_startup_controller_application_unregister_shutdown_consumer (NodeStartupControllerApplication *application);
@@ -114,6 +116,9 @@ struct _NodeStartupControllerApplication
/* shutdown client for the node startup controller itself */
ShutdownClient *client;
+
+ /* source ID for the SIGTERM handler */
+ guint sigterm_id;
};
@@ -226,6 +231,12 @@ node_startup_controller_application_init (NodeStartupControllerApplication *appl
DLT_STRING ("Updating the systemd watchdog timestamp every"),
DLT_UINT (watchdog_sec), DLT_STRING ("seconds"));
}
+
+ /* release all registered shutdown consumers upon receiving SIGTERM */
+ application->sigterm_id =
+ g_unix_signal_add (SIGTERM,
+ node_startup_controller_application_handle_sigterm,
+ application);
}
@@ -270,6 +281,10 @@ node_startup_controller_application_finalize (GObject *object)
/* release the main loop */
g_main_loop_unref (application->main_loop);
+ /* remove the SIGTERM handler source */
+ if (application->sigterm_id > 0)
+ g_source_remove (application->sigterm_id);
+
(*G_OBJECT_CLASS (node_startup_controller_application_parent_class)->finalize) (object);
}
@@ -430,11 +445,6 @@ node_startup_controller_application_handle_lifecycle_request (ShutdownConsumer
guint request_id,
NodeStartupControllerApplication *application)
{
- NSMConsumer *nsm_consumer;
- const gchar *bus_name;
- const gchar *object_path;
- gint shutdown_mode;
-
g_return_val_if_fail (IS_SHUTDOWN_CONSUMER (consumer), FALSE);
g_return_val_if_fail (G_IS_DBUS_METHOD_INVOCATION (invocation), FALSE);
g_return_val_if_fail (IS_NODE_STARTUP_CONTROLLER_APPLICATION (application), FALSE);
@@ -445,19 +455,13 @@ node_startup_controller_application_handle_lifecycle_request (ShutdownConsumer
/* deregister the shutdown consumers */
la_handler_service_deregister_consumers (application->la_handler);
+ /* deregister the shutdown consumer of the application itself */
+ node_startup_controller_application_unregister_shutdown_consumer (application);
+
/* let the NSM know that we have handled the lifecycle request */
shutdown_consumer_complete_lifecycle_request (consumer, invocation,
NSM_ERROR_STATUS_OK);
- /* deregister the node startup controller as a shutdown client itself */
- nsm_consumer = la_handler_service_get_nsm_consumer (application->la_handler);
- bus_name = shutdown_client_get_bus_name (application->client);
- object_path = shutdown_client_get_object_path (application->client);
- shutdown_mode = shutdown_client_get_shutdown_mode (application->client);
- nsm_consumer_call_un_register_shutdown_client (nsm_consumer, bus_name,
- object_path, shutdown_mode, NULL,
- node_startup_controller_application_handle_unregister_finish,
- application);
return TRUE;
}
@@ -546,6 +550,53 @@ node_startup_controller_application_luc_groups_started (LUCStarter
+static gboolean
+node_startup_controller_application_handle_sigterm (gpointer user_data)
+{
+ NodeStartupControllerApplication *application = NODE_STARTUP_CONTROLLER_APPLICATION (user_data);
+
+ g_return_val_if_fail (IS_NODE_STARTUP_CONTROLLER_APPLICATION (application), FALSE);
+
+ /* deregister the shutdown consumers of legacy applications */
+ la_handler_service_deregister_consumers (application->la_handler);
+
+ /* unregister the shutdown client for the app itself */
+ node_startup_controller_application_unregister_shutdown_consumer (application);
+
+ /* quit the application */
+ g_main_loop_quit (application->main_loop);
+
+ /* reset the source ID */
+ application->sigterm_id = 0;
+
+ return FALSE;
+}
+
+
+
+static void
+node_startup_controller_application_unregister_shutdown_consumer (NodeStartupControllerApplication *application)
+{
+ NSMConsumer *nsm_consumer;
+ const gchar *bus_name;
+ const gchar *object_path;
+ gint shutdown_mode;
+
+ g_return_if_fail (IS_NODE_STARTUP_CONTROLLER_APPLICATION (application));
+
+ /* deregister the node startup controller as a shutdown client itself */
+ nsm_consumer = la_handler_service_get_nsm_consumer (application->la_handler);
+ bus_name = shutdown_client_get_bus_name (application->client);
+ object_path = shutdown_client_get_object_path (application->client);
+ shutdown_mode = shutdown_client_get_shutdown_mode (application->client);
+ nsm_consumer_call_un_register_shutdown_client (nsm_consumer, bus_name,
+ object_path, shutdown_mode, NULL,
+ node_startup_controller_application_handle_unregister_finish,
+ application);
+}
+
+
+
NodeStartupControllerApplication *
node_startup_controller_application_new (GMainLoop *main_loop,
GDBusConnection *connection,