From b16c4fc5855899ce9eabc64673dc96afbdebeead Mon Sep 17 00:00:00 2001 From: Sebastian Geiger Date: Sun, 3 Nov 2019 15:32:54 +0100 Subject: [PATCH] dbus: Add DBus support to tilda This adds D-Bus support to tilda. Each process registers its own D-Bus name, so it is still possible to run multiple tilda processes each with their own config file and control them separately via D-Bus. The D-Bus interface is generated via gdbus-codegen from an interface definition. The interface definition declares a single method to toggle the tilda window. Each tilda instance registers itself using a dynamically generated bus name and object path using its instance number. The first tilda instance will be on: com.github.lanoxx.tilda.Actions0 with object path: /com/github/lanoxx/tilda/Actions0 The interface name is always: com.github.lanoxx.tilda.Actions To toggle the tilda window you can use 'dbus-send': dbus-send --session --type=method_call \ --dest=com.github.lanoxx.tilda.Actions0 \ /com/github/lanoxx/tilda/Actions0 \ com.github.lanoxx.tilda.Actions.Toggle For each additional tilda instance the bus name and object path will be incremented by one (e.g. Actions1, Actions2, etc.). Many thanks to Koosha Hosseiny for the initial work that has lead to this patch. --- configure.ac | 5 ++ src/Makefile.am | 20 ++++++++ src/tilda-dbus-actions.c | 99 ++++++++++++++++++++++++++++++++++++++ src/tilda-dbus-actions.h | 10 ++++ src/tilda-dbus-actions.xml | 6 +++ src/tilda.c | 5 ++ 6 files changed, 145 insertions(+) create mode 100644 src/tilda-dbus-actions.c create mode 100644 src/tilda-dbus-actions.h create mode 100644 src/tilda-dbus-actions.xml diff --git a/configure.ac b/configure.ac index 207d1164..ac5bf7ea 100644 --- a/configure.ac +++ b/configure.ac @@ -139,6 +139,11 @@ if test x$GLIB_COMPILE_RESOURCES = xno; then AC_MSG_ERROR(Could not find a glib-compile-resources in your PATH) fi +AC_PATH_PROG(GDBUS_CODEGEN, gdbus-codegen, no) +if test x$GDBUS_CODEGEN = xno; then + AC_MSG_ERROR(Could not find a glib-codegen binary in your PATH) +fi + # Checks for programs. AC_PROG_CC AM_PROG_CC_C_O diff --git a/src/Makefile.am b/src/Makefile.am index cb497f54..a4886670 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -26,6 +26,21 @@ src/tilda-enum-types.h: $(srcdir)/src/tilda-enum-types.h.template $(ENUM_TYPES) src/tilda-enum-types.c: $(srcdir)/src/tilda-enum-types.c.template $(ENUM_TYPES) $(GLIB_MKENUMS) $(AM_V_GEN) ($(GLIB_MKENUMS) --template $(srcdir)/src/tilda-enum-types.c.template $(ENUM_TYPES)) > $@ +GDBUS_CODEGEN_OPTIONS = \ + --interface-prefix 'com.github.lanoxx.tilda.' --c-namespace TildaDbus + +GDBUS_CODEGEN_BODY_OPTIONS = \ + ${GDBUS_CODEGEN_OPTIONS} --body --output $@ + +GDBUS_CODEGEN_HEADER_OPTIONS = \ + ${GDBUS_CODEGEN_OPTIONS} --header --output $@ + +src/tilda-dbus.c: $(srcdir)/src/tilda-dbus-actions.xml $(GDBUS_CODEGEN) + $(AM_V_GEN) $(GDBUS_CODEGEN) $(GDBUS_CODEGEN_BODY_OPTIONS) $(srcdir)/src/tilda-dbus-actions.xml + +src/tilda-dbus.h: ${srcdir}/src/tilda-dbus-actions.xml $(GDBUS_CODEGEN) + $(AM_V_GEN) $(GDBUS_CODEGEN) $(GDBUS_CODEGEN_HEADER_OPTIONS) $(srcdir)/src/tilda-dbus-actions.xml + src_tilda_CPPFLAGS = \ $(AM_CPPFLAGS) \ -I$(top_builddir)/src \ @@ -39,6 +54,7 @@ src_tilda_CPPFLAGS = \ BUILT_SOURCES = \ src/glade-resources.h src/glade-resources.c \ src/tilda-enum-types.c src/tilda-enum-types.h \ + src/tilda-dbus.c src/tilda-dbus.h \ $(NULL) # Keep the headers here so that make dist-bzip2 works @@ -50,6 +66,7 @@ src_tilda_SOURCES = \ src/key_grabber.h src/key_grabber.c \ src/screen-size.h src/screen-size.c \ src/tilda.h src/tilda.c \ + src/tilda-dbus-actions.h src/tilda-dbus-actions.c \ src/tilda-keybinding.c src/tilda-keybinding.h \ src/tilda-cli-options.c src/tilda-cli-options.h \ src/tilda-context-menu.c src/tilda-context-menu.h \ @@ -98,6 +115,7 @@ EXTRA_DIST += \ src/glade-resources.gresource.xml \ src/tilda-search-box.ui \ src/menu.ui \ + src/tilda-dbus.xml \ src/tilda.ui \ src/tilda-enum-types.h.template \ src/tilda-enum-types.c.template \ @@ -108,4 +126,6 @@ CLEANFILES += \ src/glade-resources.c \ src/tilda-enum-types.h \ src/tilda-enum-types.c \ + src/tilda-dbus.c \ + src/tilda-dbus.h \ $(NULL) diff --git a/src/tilda-dbus-actions.c b/src/tilda-dbus-actions.c new file mode 100644 index 00000000..6f779550 --- /dev/null +++ b/src/tilda-dbus-actions.c @@ -0,0 +1,99 @@ +#include "tilda-dbus-actions.h" + +#include "key_grabber.h" +#include "tilda-dbus.h" + +#define TILDA_DBUS_ACTIONS_BUS_NAME "com.github.lanoxx.tilda.Actions" +#define TILDA_DBUS_ACTIONS_OBJECT_PATH "/com/github/lanoxx/tilda/Actions" + +static gchar * tilda_dbus_actions_get_object_path (tilda_window *window); + +static gboolean +on_handle_toggle (TildaDbusActions *skeleton, + GDBusMethodInvocation *invocation, + gpointer user_data) +{ + tilda_window *window; + + window = user_data; + + pull (window, PULL_TOGGLE, FALSE); + + tilda_dbus_actions_complete_toggle (skeleton, invocation); + + return GDK_EVENT_STOP; +} + +static void +on_name_acquired (GDBusConnection *connection, + const gchar *name, + gpointer window) +{ + TildaDbusActions *actions; + tilda_window *tw; + GError *error; + gchar *path; + + tw = window; + + g_debug ("TildaDbusActions: Name acquired: %s", name); + + error = NULL; + + actions = tilda_dbus_actions_skeleton_new (); + + g_signal_connect (actions, "handle-toggle",G_CALLBACK (on_handle_toggle), window); + + path = tilda_dbus_actions_get_object_path (tw); + + g_dbus_interface_skeleton_export (G_DBUS_INTERFACE_SKELETON (actions), + connection, + path, + &error); + + if (error) + { + g_error ("Error while exporting object path of DBus interface %s: %s", + TILDA_DBUS_ACTIONS_OBJECT_PATH, error->message); + } + + g_free (path); +} + +guint +tilda_dbus_actions_init (tilda_window *window) +{ + guint bus_identifier; + gchar *name; + + name = tilda_dbus_actions_get_bus_name (window); + + bus_identifier = g_bus_own_name (G_BUS_TYPE_SESSION, + name, + G_BUS_NAME_OWNER_FLAGS_NONE, + NULL, + on_name_acquired, + NULL, window, NULL); + + g_free (name); + + return bus_identifier; +} + +gchar * +tilda_dbus_actions_get_bus_name (tilda_window *window) +{ + return g_strdup_printf ("%s%d", TILDA_DBUS_ACTIONS_BUS_NAME, window->instance); +} + +static gchar * +tilda_dbus_actions_get_object_path (tilda_window *window) +{ + return g_strdup_printf ("%s%d", TILDA_DBUS_ACTIONS_OBJECT_PATH, window->instance); +} + +void +tilda_dbus_actions_finish (guint bus_identifier) +{ + g_bus_unown_name (bus_identifier); +} diff --git a/src/tilda-dbus-actions.h b/src/tilda-dbus-actions.h new file mode 100644 index 00000000..214c73c1 --- /dev/null +++ b/src/tilda-dbus-actions.h @@ -0,0 +1,10 @@ +#ifndef TILDA_DBUS_ACTIONS_H +#define TILDA_DBUS_ACTIONS_H + +#include "tilda_window.h" + +guint tilda_dbus_actions_init (tilda_window *window); + +void tilda_dbus_actions_finish (guint bus_identifier); + +#endif diff --git a/src/tilda-dbus-actions.xml b/src/tilda-dbus-actions.xml new file mode 100644 index 00000000..510259f5 --- /dev/null +++ b/src/tilda-dbus-actions.xml @@ -0,0 +1,6 @@ + + + + + + diff --git a/src/tilda.c b/src/tilda.c index e8239d01..faf39809 100644 --- a/src/tilda.c +++ b/src/tilda.c @@ -49,6 +49,7 @@ #include "tomboykeybinder.h" #include "tilda-keybinding.h" #include "tilda-cli-options.h" +#include "tilda-dbus-actions.h" #include #include @@ -771,6 +772,8 @@ int main (int argc, char *argv[]) } } + guint bus_identifier = tilda_dbus_actions_init (&tw); + pull (&tw, config_getbool ("hidden") ? PULL_UP : PULL_DOWN, FALSE); g_print ("Tilda has started. Press %s to pull down the window.\n", @@ -778,6 +781,8 @@ int main (int argc, char *argv[]) /* Whew! We're finally all set up and ready to run GTK ... */ gtk_main(); + tilda_dbus_actions_finish (bus_identifier); + initialization_failed: tilda_window_free(&tw);