[PATCH v2 18/28] Add weston-control to allow reloading the config file

Jan Arne Petersen jpetersen at openismus.com
Thu Apr 18 07:47:32 PDT 2013


From: Jan Arne Petersen <jpetersen at openismus.com>

Signed-off-by: Jan Arne Petersen <jpetersen at openismus.com>
---
 clients/.gitignore       |   3 ++
 clients/Makefile.am      |   9 +++++
 clients/weston-control.c | 101 +++++++++++++++++++++++++++++++++++++++++++++++
 protocol/Makefile.am     |   1 +
 protocol/control.xml     |  35 ++++++++++++++++
 src/.gitignore           |   3 ++
 src/Makefile.am          |  14 ++++++-
 src/compositor.c         |   2 +
 src/compositor.h         |   3 ++
 src/control.c            |  88 +++++++++++++++++++++++++++++++++++++++++
 src/text-backend.c       |  68 ++++++++++++++++++++++++++++++-
 11 files changed, 325 insertions(+), 2 deletions(-)
 create mode 100644 clients/weston-control.c
 create mode 100644 protocol/control.xml
 create mode 100644 src/control.c

diff --git a/clients/.gitignore b/clients/.gitignore
index dcd4564..626b09d 100644
--- a/clients/.gitignore
+++ b/clients/.gitignore
@@ -1,6 +1,8 @@
 calibrator
 clickdot
 cliptest
+control-client-protocol.h
+control-protocol.c
 desktop-shell-client-protocol.h
 desktop-shell-protocol.c
 dnd
@@ -28,6 +30,7 @@ text-cursor-position-protocol.c
 text-protocol.c
 transformed
 view
+weston-control
 weston-desktop-shell
 weston-info
 weston-screensaver
diff --git a/clients/Makefile.am b/clients/Makefile.am
index 8c9bcd4..d9236cf 100644
--- a/clients/Makefile.am
+++ b/clients/Makefile.am
@@ -1,5 +1,6 @@
 bin_PROGRAMS =					\
 	weston-info				\
+	weston-control				\
 	$(terminal)
 
 noinst_PROGRAMS =				\
@@ -160,6 +161,12 @@ weston_info_SOURCES =				\
 	../shared/os-compatibility.h
 weston_info_LDADD = $(WESTON_INFO_LIBS)
 
+weston_control_SOURCES =			\
+	weston-control.c			\
+	control-protocol.c			\
+	control-client-protocol.h
+weston_control_LDADD = libtoytoolkit.la
+
 weston_desktop_shell_SOURCES =			\
 	desktop-shell.c				\
 	desktop-shell-client-protocol.h		\
@@ -185,6 +192,8 @@ BUILT_SOURCES =					\
 	desktop-shell-protocol.c		\
 	tablet-shell-client-protocol.h		\
 	tablet-shell-protocol.c			\
+	control-protocol.c			\
+	control-client-protocol.h		\
 	workspaces-client-protocol.h		\
 	workspaces-protocol.c
 
diff --git a/clients/weston-control.c b/clients/weston-control.c
new file mode 100644
index 0000000..07ef8d0
--- /dev/null
+++ b/clients/weston-control.c
@@ -0,0 +1,101 @@
+/*
+ * Copyright © 2013 Intel Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission.  The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose.  It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <wayland-client.h>
+
+#include "control-client-protocol.h"
+
+struct control {
+	struct weston_control *weston_control;
+};
+
+static void
+global_handler(void *data, struct wl_registry *registry, uint32_t id,
+	       const char *interface, uint32_t version)
+{
+	struct control *control = data;
+
+	if (strcmp(interface, "weston_control") == 0) {
+		control->weston_control = wl_registry_bind(registry,
+							   id,
+							   &weston_control_interface,
+							   1);
+	}
+}
+
+static void
+global_remove_handler(void *data, struct wl_registry *registry, uint32_t name)
+{
+}
+
+static const struct wl_registry_listener registry_listener = {
+	global_handler,
+	global_remove_handler
+};
+
+int
+main(int argc, char **argv)
+{
+	struct control control;
+	struct wl_display *display;
+	struct wl_registry *registry;
+	int i;
+
+	memset(&control, 0, sizeof control);
+
+	display = wl_display_connect(NULL);
+	if (!display) {
+		fprintf(stderr, "failed to create display: %m\n");
+		return -1;
+	}
+
+	registry = wl_display_get_registry(display);
+	wl_registry_add_listener(registry, &registry_listener, &control);
+
+	wl_display_roundtrip(display);
+
+	if (!control.weston_control) {
+		fprintf(stderr, "failed to access weston_control global object.\n");
+		return -1;
+	}
+
+	for (i = 1; i < argc; i++) {
+		if (strcmp("--reload-config", argv[i]) == 0) {
+			weston_control_reload_config(control.weston_control);
+		} else if (strcmp("--set-input-method", argv[i]) == 0) {
+			if (++i < argc) {
+				weston_control_set_input_method(control.weston_control,
+								argv[i]);
+			}
+		}
+	}
+
+	wl_display_roundtrip(display);
+
+	return 0;
+}
+
+
diff --git a/protocol/Makefile.am b/protocol/Makefile.am
index 8c1803c..7141cc4 100644
--- a/protocol/Makefile.am
+++ b/protocol/Makefile.am
@@ -1,4 +1,5 @@
 EXTRA_DIST =					\
+	config.xml				\
 	desktop-shell.xml			\
 	screenshooter.xml			\
 	tablet-shell.xml			\
diff --git a/protocol/control.xml b/protocol/control.xml
new file mode 100644
index 0000000..3629272
--- /dev/null
+++ b/protocol/control.xml
@@ -0,0 +1,35 @@
+<protocol name="weston_control">
+  <copyright>
+    Copyright © 2013 Intel Corporation
+
+    Permission to use, copy, modify, distribute, and sell this
+    software and its documentation for any purpose is hereby granted
+    without fee, provided that the above copyright notice appear in
+    all copies and that both that copyright notice and this permission
+    notice appear in supporting documentation, and that the name of
+    the copyright holders not be used in advertising or publicity
+    pertaining to distribution of the software without specific,
+    written prior permission.  The copyright holders make no
+    representations about the suitability of this software for any
+    purpose.  It is provided "as is" without express or implied
+    warranty.
+
+    THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+    SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+    FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+    SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+    WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN
+    AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
+    ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+    THIS SOFTWARE.
+  </copyright>
+
+  <interface name="weston_control" version="1">
+    <request name="reload_config">
+    </request>
+
+    <request name="set_input_method">
+      <arg name="path" type="string"/>
+    </request>
+  </interface>
+</protocol>
diff --git a/src/.gitignore b/src/.gitignore
index 8c0fea6..c5f42c3 100644
--- a/src/.gitignore
+++ b/src/.gitignore
@@ -18,3 +18,6 @@ workspaces-protocol.c
 workspaces-server-protocol.h
 input-method-protocol.c
 input-method-server-protocol.h
+control-server-protocol.h
+control-protocol.c
+
diff --git a/src/Makefile.am b/src/Makefile.am
index 77b24b5..1530762 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -100,7 +100,8 @@ module_LTLIBRARIES =				\
 	$(wayland_backend)			\
 	$(headless_backend)			\
 	$(fbdev_backend)			\
-	$(rdp_backend)
+	$(rdp_backend)				\
+	$(weston_control)
 
 noinst_LTLIBRARIES =
 
@@ -252,6 +253,15 @@ tablet_shell_la_SOURCES =			\
 	tablet-shell-server-protocol.h
 endif
 
+weston_control = weston-control.la
+weston_control_la_LDFLAGS = -module -avoid-version
+weston_control_la_LIBADD = $(COMPOSITOR_LIBS)
+weston_control_la_CFLAGS = $(GCC_CFLAGS) $(COMPOSITOR_CFLAGS)
+weston_control_la_SOURCES =			\
+	control.c				\
+	control-protocol.c			\
+	control-server-protocol.h
+
 BUILT_SOURCES =					\
 	screenshooter-server-protocol.h		\
 	screenshooter-protocol.c		\
@@ -267,6 +277,8 @@ BUILT_SOURCES =					\
 	input-method-server-protocol.h		\
 	workspaces-server-protocol.h		\
 	workspaces-protocol.c			\
+	control-protocol.c			\
+	control-server-protocol.h		\
 	git-version.h
 
 CLEANFILES = $(BUILT_SOURCES)
diff --git a/src/compositor.c b/src/compositor.c
index 82a3fa9..c23140e 100644
--- a/src/compositor.c
+++ b/src/compositor.c
@@ -3151,6 +3151,8 @@ weston_compositor_init(struct weston_compositor *ec,
 	wl_signal_init(&ec->show_input_panel_signal);
 	wl_signal_init(&ec->hide_input_panel_signal);
 	wl_signal_init(&ec->update_input_panel_signal);
+	wl_signal_init(&ec->reload_config_signal);
+	wl_signal_init(&ec->set_input_method_signal);
 	wl_signal_init(&ec->seat_created_signal);
 	ec->launcher_sock = weston_environment_get_fd("WESTON_LAUNCHER_SOCK");
 
diff --git a/src/compositor.h b/src/compositor.h
index 5c2c404..a113165 100644
--- a/src/compositor.h
+++ b/src/compositor.h
@@ -313,6 +313,9 @@ struct weston_compositor {
 	struct wl_signal hide_input_panel_signal;
 	struct wl_signal update_input_panel_signal;
 
+	struct wl_signal reload_config_signal;
+	struct wl_signal set_input_method_signal;
+
 	struct wl_signal seat_created_signal;
 
 	struct wl_event_loop *input_loop;
diff --git a/src/control.c b/src/control.c
new file mode 100644
index 0000000..fe8c495
--- /dev/null
+++ b/src/control.c
@@ -0,0 +1,88 @@
+/*
+ * Copyright © 2013 Intel Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission.  The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose.  It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include <stdlib.h>
+#include <string.h>
+
+#include "compositor.h"
+
+#include "control-server-protocol.h"
+
+struct control {
+	struct weston_compositor *compositor;
+	struct wl_global *global;
+	struct wl_resource *binding;
+};
+
+static void
+reload_config(struct wl_client *client, struct wl_resource *resource)
+{
+	struct control *control = resource->data;
+
+	wl_signal_emit(&control->compositor->reload_config_signal, control->compositor);
+}
+
+static void
+set_input_method(struct wl_client *client,
+		 struct wl_resource *resource,
+		 const char *path)
+{
+	struct control *control = resource->data;
+
+	wl_signal_emit(&control->compositor->set_input_method_signal, path);
+}
+
+static const struct weston_control_interface control_implementation = {
+	reload_config,
+	set_input_method
+};
+
+static void
+bind_control(struct wl_client *client, void *data, uint32_t version, uint32_t id)
+{
+	struct control *control = data;
+
+	control->binding = wl_client_add_object(client, &weston_control_interface,
+						&control_implementation, id, control);
+}
+
+WL_EXPORT int
+module_init(struct weston_compositor *ec,
+	    int *argc, char *argv[], const char *config_file)
+{
+	struct control *control;
+
+	control = malloc(sizeof *control);
+	if (control == NULL)
+		return -1;
+
+	memset(control, 0, sizeof *control);
+	control->compositor = ec;
+
+	control->global = wl_display_add_global(ec->wl_display, &weston_control_interface,
+						control, bind_control);
+	if (control->global == NULL)
+		return -1;
+
+	return 0;	
+}
+
diff --git a/src/text-backend.c b/src/text-backend.c
index 53aa92c..a14e048 100644
--- a/src/text-backend.c
+++ b/src/text-backend.c
@@ -21,6 +21,7 @@
  * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
  */
 
+#include <signal.h>
 #include <stdlib.h>
 #include <string.h>
 
@@ -91,10 +92,15 @@ struct text_backend {
 		struct wl_resource *binding;
 		struct weston_process process;
 		struct wl_client *client;
+
+		uint32_t deathcount;
+		uint32_t deathstamp;
 	} input_method;
 
 	struct wl_listener seat_created_listener;
 	struct wl_listener destroy_listener;
+	struct wl_listener reload_config_listener;
+	struct wl_listener set_input_method_listener;
 };
 
 static void input_method_context_create(struct text_input *model,
@@ -103,6 +109,7 @@ static void input_method_context_create(struct text_input *model,
 static void input_method_context_end_keyboard_grab(struct input_method_context *context);
 
 static void input_method_init_seat(struct weston_seat *seat);
+static void launch_input_method(struct text_backend *text_backend);
 
 static void
 deactivate_text_input(struct text_input *text_input,
@@ -830,9 +837,30 @@ handle_input_method_sigchld(struct weston_process *process, int status)
 {
 	struct text_backend *text_backend =
 		container_of(process, struct text_backend, input_method.process);
+	uint32_t time;
 
 	text_backend->input_method.process.pid = 0;
 	text_backend->input_method.client = NULL;
+
+	/* respawn */
+	time = weston_compositor_get_time();
+	if (time - text_backend->input_method.deathstamp > 30000) {
+		text_backend->input_method.deathstamp = time;
+		text_backend->input_method.deathcount = 0;
+	}
+
+	text_backend->input_method.deathcount++;
+
+	if (text_backend->input_method.deathcount > 5) {
+		text_backend->input_method.deathstamp = time;
+
+		weston_log("input method died, giving up.\n");
+		return;
+	}
+
+	weston_log("input method died, respawning...\n");
+
+	launch_input_method(text_backend);
 }
 
 static void
@@ -913,6 +941,39 @@ text_backend_configuration(struct text_backend *text_backend)
 }
 
 static void
+text_backend_reload_configuration(struct wl_listener *listener, void *data)
+{
+	struct text_backend *text_backend =
+		container_of(listener, struct text_backend, reload_config_listener);
+	char *old_input_method_path;
+
+	old_input_method_path = text_backend->input_method.path;
+
+	text_backend_configuration(text_backend);
+
+	if (strcmp(text_backend->input_method.path, old_input_method_path) != 0) {
+		kill(text_backend->input_method.process.pid, SIGTERM);
+	}
+
+	free(old_input_method_path);
+}
+
+static void
+text_backend_set_input_method(struct wl_listener *listener, void *data)
+{
+	struct text_backend *text_backend =
+		container_of(listener, struct text_backend, set_input_method_listener);
+	const char *path = data;
+
+	if (strcmp(text_backend->input_method.path, path) != 0) {
+		free(text_backend->input_method.path);
+		text_backend->input_method.path = strdup(path);
+		kill(text_backend->input_method.process.pid, SIGTERM);
+	}
+
+}
+
+static void
 text_backend_notifier_destroy(struct wl_listener *listener, void *data)
 {
 	struct text_backend *text_backend =
@@ -926,7 +987,6 @@ text_backend_notifier_destroy(struct wl_listener *listener, void *data)
 	free(text_backend);
 }
 
-
 WL_EXPORT int
 text_backend_init(struct weston_compositor *ec)
 {
@@ -943,6 +1003,12 @@ text_backend_init(struct weston_compositor *ec)
 	text_backend->destroy_listener.notify = text_backend_notifier_destroy;
 	wl_signal_add(&ec->destroy_signal, &text_backend->destroy_listener);
 
+	text_backend->reload_config_listener.notify = text_backend_reload_configuration;
+	wl_signal_add(&ec->reload_config_signal, &text_backend->reload_config_listener);
+
+	text_backend->set_input_method_listener.notify = text_backend_set_input_method;
+	wl_signal_add(&ec->set_input_method_signal, &text_backend->set_input_method_listener);
+
 	text_backend_configuration(text_backend);
 
 	text_input_manager_create(ec);
-- 
1.8.1.4



More information about the wayland-devel mailing list