aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/global_shortcuts.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/global_shortcuts.c')
-rw-r--r--src/global_shortcuts.c91
1 files changed, 62 insertions, 29 deletions
diff --git a/src/global_shortcuts.c b/src/global_shortcuts.c
index a7540f0..794de04 100644
--- a/src/global_shortcuts.c
+++ b/src/global_shortcuts.c
@@ -5,14 +5,9 @@
#include <sys/random.h>
#include <gio/gio.h>
-/* TODO: Remove G_DBUS_CALL_FLAGS_NO_AUTO_START and G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START? also in gpu screen recorder equivalent */
-/* TODO: More error handling and clean up resources after done */
-/* TODO: Use GArray instead of GVariant where possible */
-
static bool generate_random_characters(char *buffer, int buffer_size, const char *alphabet, size_t alphabet_size) {
- /* TODO: Use other functions on other platforms than linux */
if(getrandom(buffer, buffer_size, 0) < buffer_size) {
- fprintf(stderr, "gsr error: generate_random_characters: failed to get random bytes, error: %s\n", strerror(errno));
+ g_warning("generate_random_characters: failed to get random bytes: %s", strerror(errno));
return false;
}
@@ -35,11 +30,11 @@ static void handle_shortcuts_data(GVariant *shortcuts, gsr_shortcut_callback cal
GVariant *shortcut_values = NULL;
g_variant_get_child(shortcuts, i, "(s@a{sv})", &shortcut_id, &shortcut_values);
- if(!shortcut_id || !shortcut_values)
+ if(!shortcut_id || !shortcut_values) {
+ g_free(shortcut_id);
+ if(shortcut_values) g_variant_unref(shortcut_values);
continue;
-
- // gchar *description = NULL;
- // g_variant_lookup(shortcut_values, "description", "s", &description);
+ }
gchar *trigger_description = NULL;
g_variant_lookup(shortcut_values, "trigger_description", "s", &trigger_description);
@@ -48,6 +43,10 @@ static void handle_shortcuts_data(GVariant *shortcuts, gsr_shortcut_callback cal
shortcut.id = shortcut_id;
shortcut.trigger_description = trigger_description ? trigger_description : "";
callback(shortcut, userdata);
+
+ g_free(shortcut_id);
+ g_free(trigger_description);
+ g_variant_unref(shortcut_values);
}
}
@@ -67,14 +66,20 @@ static void dbus_signal_list_bind(GDBusProxy *proxy, gchar *sender_name, gchar *
GVariant *results = NULL;
g_variant_get(parameters, "(u@a{sv})", &response, &results);
- if(response != 0 || !results)
+ if(response != 0 || !results) {
+ if(results) g_variant_unref(results);
goto done;
+ }
GVariant *shortcuts = g_variant_lookup_value(results, "shortcuts", G_VARIANT_TYPE("a(sa{sv})"));
- if(!shortcuts)
+ if(!shortcuts) {
+ g_variant_unref(results);
goto done;
+ }
handle_shortcuts_data(shortcuts, userdata->callback, userdata->userdata);
+ g_variant_unref(shortcuts);
+ g_variant_unref(results);
done:
free(userdata);
@@ -107,12 +112,16 @@ static void signal_callback(GDBusConnection *connection,
if(strcmp(signal_name, "Deactivated") == 0) {
gchar *session_handle = NULL;
gchar *shortcut_id = NULL;
- gchar *timestamp = NULL;
+ guint64 timestamp = 0;
GVariant *options = NULL;
g_variant_get(parameters, "(ost@a{sv})", &session_handle, &shortcut_id, &timestamp, &options);
if(session_handle && shortcut_id && strcmp(session_handle, cu->self->session_handle) == 0)
cu->deactivated_callback(shortcut_id, cu->userdata);
+
+ g_free(session_handle);
+ g_free(shortcut_id);
+ if(options) g_variant_unref(options);
} else if(strcmp(signal_name, "ShortcutsChanged") == 0) {
gchar *session_handle = NULL;
GVariant *shortcuts = NULL;
@@ -120,6 +129,9 @@ static void signal_callback(GDBusConnection *connection,
if(session_handle && shortcuts && strcmp(session_handle, cu->self->session_handle) == 0)
handle_shortcuts_data(shortcuts, cu->shortcut_changed_callback, cu->userdata);
+
+ g_free(session_handle);
+ if(shortcuts) g_variant_unref(shortcuts);
}
}
@@ -141,6 +153,7 @@ static void dbus_signal_create_session(GDBusProxy *proxy, gchar *sender_name, gc
if(response != 0 || !results) {
cu->callback(false, cu->userdata);
+ if(results) g_variant_unref(results);
goto done;
}
@@ -149,18 +162,22 @@ static void dbus_signal_create_session(GDBusProxy *proxy, gchar *sender_name, gc
cu->self->session_handle = strdup(session_handle);
cu->self->session_created = true;
cu->callback(true, cu->userdata);
+ g_free(session_handle);
+ } else {
+ cu->callback(false, cu->userdata);
}
+ g_variant_unref(results);
done:
free(cu);
}
static bool gsr_global_shortcuts_create_session(gsr_global_shortcuts *self, gsr_init_callback callback, void *userdata) {
- char handle_token[64];
+ char handle_token[128];
gsr_dbus_portal_get_unique_handle_token(self, handle_token, sizeof(handle_token));
- char session_handle_token[64];
- snprintf(session_handle_token, sizeof(session_handle_token), "gpu_screen_recorder_adwaita");
+ char session_handle_token[128];
+ snprintf(session_handle_token, sizeof(session_handle_token), "gpu_screen_recorder_adwaita_%s", self->random_str);
GVariantBuilder builder;
g_variant_builder_init(&builder, G_VARIANT_TYPE("a{sv}"));
@@ -173,16 +190,21 @@ static bool gsr_global_shortcuts_create_session(gsr_global_shortcuts *self, gsr_
if(ret) {
const gchar *val = NULL;
g_variant_get(ret, "(&o)", &val);
- if(!val)
+ if(!val) {
+ g_variant_unref(ret);
return false;
- //g_variant_unref(ret);
+ }
GDBusProxy *proxy = g_dbus_proxy_new_for_bus_sync(G_BUS_TYPE_SESSION, G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, NULL, "org.freedesktop.portal.Desktop", val, "org.freedesktop.portal.Request", NULL, NULL);
+ g_variant_unref(ret);
if(!proxy)
return false;
- //g_object_unref(proxy);
signal_create_session_userdata *cu = malloc(sizeof(signal_create_session_userdata));
+ if(!cu) {
+ g_object_unref(proxy);
+ return false;
+ }
cu->self = self;
cu->callback = callback;
cu->userdata = userdata;
@@ -198,13 +220,13 @@ bool gsr_global_shortcuts_init(gsr_global_shortcuts *self, gsr_init_callback cal
self->random_str[DBUS_RANDOM_STR_SIZE] = '\0';
if(!generate_random_characters(self->random_str, DBUS_RANDOM_STR_SIZE, "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789", 62)) {
- fprintf(stderr, "gsr error: gsr_global_shortcuts_init: failed to generate random string\n");
+ g_warning("gsr_global_shortcuts_init: failed to generate random string");
return false;
}
self->gdbus_con = g_bus_get_sync(G_BUS_TYPE_SESSION, NULL, NULL);
if(!self->gdbus_con) {
- fprintf(stderr, "gsr error: gsr_global_shortcuts_init: g_bus_get_sync failed\n");
+ g_warning("gsr_global_shortcuts_init: g_bus_get_sync failed");
return false;
}
@@ -218,8 +240,7 @@ bool gsr_global_shortcuts_init(gsr_global_shortcuts *self, gsr_init_callback cal
void gsr_global_shortcuts_deinit(gsr_global_shortcuts *self) {
if(self->gdbus_con) {
- /* TODO: Re-add this. Right now it causes errors as the connection is already closed, but checking if it's already closed here has no effect */
- //g_dbus_connection_close(self->gdbus_con, NULL, NULL, NULL);
+ g_object_unref(self->gdbus_con);
self->gdbus_con = NULL;
}
@@ -233,7 +254,7 @@ bool gsr_global_shortcuts_list_shortcuts(gsr_global_shortcuts *self, gsr_shortcu
if(!self->session_created)
return false;
- char handle_token[64];
+ char handle_token[128];
gsr_dbus_portal_get_unique_handle_token(self, handle_token, sizeof(handle_token));
GVariant *session_handle_obj = g_variant_new_object_path(self->session_handle);
@@ -249,15 +270,21 @@ bool gsr_global_shortcuts_list_shortcuts(gsr_global_shortcuts *self, gsr_shortcu
if(ret) {
const gchar *val = NULL;
g_variant_get(ret, "(&o)", &val);
- if(!val)
+ if(!val) {
+ g_variant_unref(ret);
return false;
+ }
GDBusProxy *proxy = g_dbus_proxy_new_for_bus_sync(G_BUS_TYPE_SESSION, G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, NULL, "org.freedesktop.portal.Desktop", val, "org.freedesktop.portal.Request", NULL, NULL);
+ g_variant_unref(ret);
if(!proxy)
return false;
- //g_object_unref(proxy);
signal_list_bind_userdata *cu = malloc(sizeof(signal_list_bind_userdata));
+ if(!cu) {
+ g_object_unref(proxy);
+ return false;
+ }
cu->self = self;
cu->callback = callback;
cu->userdata = userdata;
@@ -272,7 +299,7 @@ bool gsr_global_shortcuts_bind_shortcuts(gsr_global_shortcuts *self, const gsr_b
if(!self->session_created)
return false;
- char handle_token[64];
+ char handle_token[128];
gsr_dbus_portal_get_unique_handle_token(self, handle_token, sizeof(handle_token));
GVariant *session_handle_obj = g_variant_new_object_path(self->session_handle);
@@ -303,15 +330,21 @@ bool gsr_global_shortcuts_bind_shortcuts(gsr_global_shortcuts *self, const gsr_b
if(ret) {
const gchar *val = NULL;
g_variant_get(ret, "(&o)", &val);
- if(!val)
+ if(!val) {
+ g_variant_unref(ret);
return false;
+ }
GDBusProxy *proxy = g_dbus_proxy_new_for_bus_sync(G_BUS_TYPE_SESSION, G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, NULL, "org.freedesktop.portal.Desktop", val, "org.freedesktop.portal.Request", NULL, NULL);
+ g_variant_unref(ret);
if(!proxy)
return false;
- //g_object_unref(proxy);
signal_list_bind_userdata *cu = malloc(sizeof(signal_list_bind_userdata));
+ if(!cu) {
+ g_object_unref(proxy);
+ return false;
+ }
cu->self = self;
cu->callback = callback;
cu->userdata = userdata;