diff options
author | 2017-11-09 12:58:32 -0700 | |
---|---|---|
committer | 2017-12-29 12:11:51 -0700 | |
commit | 87035380e33c7da10b53c6da713c56f3d89a1577 (patch) | |
tree | 4b31ad282fe07227f5720928b1ba07715bc7ea48 /swaybar/tray/tray.c | |
parent | Plug memory `dbus_message_iter_get_signature` leak (diff) | |
download | sway-87035380e33c7da10b53c6da713c56f3d89a1577.tar.gz sway-87035380e33c7da10b53c6da713c56f3d89a1577.tar.zst sway-87035380e33c7da10b53c6da713c56f3d89a1577.zip |
Add `dbus_get_prop_async` utility
This drastically reduces the amount of boilerplate needed to get a
property from a bus object.
Diffstat (limited to 'swaybar/tray/tray.c')
-rw-r--r-- | swaybar/tray/tray.c | 139 |
1 files changed, 12 insertions, 127 deletions
diff --git a/swaybar/tray/tray.c b/swaybar/tray/tray.c index f1ecb429..89e7c3e2 100644 --- a/swaybar/tray/tray.c +++ b/swaybar/tray/tray.c | |||
@@ -38,47 +38,13 @@ static void register_host(char *name) { | |||
38 | dbus_message_unref(message); | 38 | dbus_message_unref(message); |
39 | } | 39 | } |
40 | 40 | ||
41 | static void get_items_reply(DBusPendingCall *pending, void *_data) { | 41 | static void get_items_reply(DBusMessageIter *iter, void *_data) { |
42 | DBusMessage *reply = dbus_pending_call_steal_reply(pending); | ||
43 | |||
44 | if (!reply) { | ||
45 | sway_log(L_ERROR, "Got no items reply from sni watcher"); | ||
46 | goto bail; | ||
47 | } | ||
48 | |||
49 | int message_type = dbus_message_get_type(reply); | ||
50 | |||
51 | if (message_type == DBUS_MESSAGE_TYPE_ERROR) { | ||
52 | char *msg; | ||
53 | |||
54 | dbus_message_get_args(reply, NULL, | ||
55 | DBUS_TYPE_STRING, &msg, | ||
56 | DBUS_TYPE_INVALID); | ||
57 | |||
58 | sway_log(L_ERROR, "Message is error: %s", msg); | ||
59 | goto bail; | ||
60 | } | ||
61 | |||
62 | DBusMessageIter iter; | ||
63 | DBusMessageIter variant; | ||
64 | DBusMessageIter array; | 42 | DBusMessageIter array; |
65 | 43 | ||
66 | dbus_message_iter_init(reply, &iter); | ||
67 | if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT) { | ||
68 | sway_log(L_ERROR, "Replyed with wrong type, not v(as)"); | ||
69 | goto bail; | ||
70 | } | ||
71 | dbus_message_iter_recurse(&iter, &variant); | ||
72 | if (dbus_message_iter_get_arg_type(&variant) != DBUS_TYPE_ARRAY || | ||
73 | dbus_message_iter_get_element_type(&variant) != DBUS_TYPE_STRING) { | ||
74 | sway_log(L_ERROR, "Replyed with wrong type, not v(as)"); | ||
75 | goto bail; | ||
76 | } | ||
77 | |||
78 | // O(n) function, could be faster dynamically reading values | 44 | // O(n) function, could be faster dynamically reading values |
79 | int len = dbus_message_iter_get_element_count(&variant); | 45 | int len = dbus_message_iter_get_element_count(iter); |
80 | 46 | ||
81 | dbus_message_iter_recurse(&variant, &array); | 47 | dbus_message_iter_recurse(iter, &array); |
82 | for (int i = 0; i < len; i++) { | 48 | for (int i = 0; i < len; i++) { |
83 | const char *name; | 49 | const char *name; |
84 | dbus_message_iter_get_basic(&array, &name); | 50 | dbus_message_iter_get_basic(&array, &name); |
@@ -93,52 +59,14 @@ static void get_items_reply(DBusPendingCall *pending, void *_data) { | |||
93 | } | 59 | } |
94 | } | 60 | } |
95 | } | 61 | } |
96 | |||
97 | bail: | ||
98 | dbus_message_unref(reply); | ||
99 | dbus_pending_call_unref(pending); | ||
100 | return; | ||
101 | } | 62 | } |
102 | static void get_obj_items_reply(DBusPendingCall *pending, void *_data) { | 63 | static void get_obj_items_reply(DBusMessageIter *iter, void *_data) { |
103 | DBusMessage *reply = dbus_pending_call_steal_reply(pending); | ||
104 | |||
105 | if (!reply) { | ||
106 | sway_log(L_ERROR, "Got no object path items reply from sni watcher"); | ||
107 | goto bail; | ||
108 | } | ||
109 | |||
110 | int message_type = dbus_message_get_type(reply); | ||
111 | |||
112 | if (message_type == DBUS_MESSAGE_TYPE_ERROR) { | ||
113 | char *msg; | ||
114 | |||
115 | dbus_message_get_args(reply, NULL, | ||
116 | DBUS_TYPE_STRING, &msg, | ||
117 | DBUS_TYPE_INVALID); | ||
118 | |||
119 | sway_log(L_ERROR, "Message is error: %s", msg); | ||
120 | goto bail; | ||
121 | } | ||
122 | |||
123 | DBusMessageIter iter; | ||
124 | DBusMessageIter variant; | ||
125 | DBusMessageIter array; | 64 | DBusMessageIter array; |
126 | DBusMessageIter dstruct; | 65 | DBusMessageIter dstruct; |
127 | 66 | ||
128 | dbus_message_iter_init(reply, &iter); | 67 | int len = dbus_message_iter_get_element_count(iter); |
129 | if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT) { | ||
130 | sway_log(L_ERROR, "Replyed with wrong type, not v(a(os))"); | ||
131 | goto bail; | ||
132 | } | ||
133 | dbus_message_iter_recurse(&iter, &variant); | ||
134 | if (dbus_message_iter_check_signature(&iter, "a(os)")) { | ||
135 | sway_log(L_ERROR, "Replyed with wrong type not a(os)"); | ||
136 | goto bail; | ||
137 | } | ||
138 | |||
139 | int len = dbus_message_iter_get_element_count(&variant); | ||
140 | 68 | ||
141 | dbus_message_iter_recurse(&variant, &array); | 69 | dbus_message_iter_recurse(iter, &array); |
142 | for (int i = 0; i < len; i++) { | 70 | for (int i = 0; i < len; i++) { |
143 | const char *object_path; | 71 | const char *object_path; |
144 | const char *unique_name; | 72 | const char *unique_name; |
@@ -164,10 +92,6 @@ static void get_obj_items_reply(DBusPendingCall *pending, void *_data) { | |||
164 | } | 92 | } |
165 | } | 93 | } |
166 | } | 94 | } |
167 | |||
168 | bail: | ||
169 | dbus_message_unref(reply); | ||
170 | dbus_pending_call_unref(pending); | ||
171 | } | 95 | } |
172 | 96 | ||
173 | static void get_items() { | 97 | static void get_items() { |
@@ -176,52 +100,13 @@ static void get_items() { | |||
176 | list_free(tray->items); | 100 | list_free(tray->items); |
177 | tray->items = create_list(); | 101 | tray->items = create_list(); |
178 | 102 | ||
179 | DBusPendingCall *pending; | 103 | dbus_get_prop_async("org.freedesktop.StatusNotifierWatcher", |
180 | DBusMessage *message = dbus_message_new_method_call( | 104 | "/StatusNotifierWatcher","org.freedesktop.StatusNotifierWatcher", |
181 | "org.freedesktop.StatusNotifierWatcher", | 105 | "RegisteredStatusNotifierItems", "as", get_items_reply, NULL); |
182 | "/StatusNotifierWatcher", | ||
183 | "org.freedesktop.DBus.Properties", | ||
184 | "Get"); | ||
185 | |||
186 | const char *iface = "org.freedesktop.StatusNotifierWatcher"; | ||
187 | const char *prop = "RegisteredStatusNotifierItems"; | ||
188 | dbus_message_append_args(message, | ||
189 | DBUS_TYPE_STRING, &iface, | ||
190 | DBUS_TYPE_STRING, &prop, | ||
191 | DBUS_TYPE_INVALID); | ||
192 | |||
193 | bool status = | ||
194 | dbus_connection_send_with_reply(conn, message, &pending, -1); | ||
195 | dbus_message_unref(message); | ||
196 | |||
197 | if (!(pending || status)) { | ||
198 | sway_log(L_ERROR, "Could not get items"); | ||
199 | return; | ||
200 | } | ||
201 | |||
202 | dbus_pending_call_set_notify(pending, get_items_reply, NULL, NULL); | ||
203 | 106 | ||
204 | message = dbus_message_new_method_call( | 107 | dbus_get_prop_async("org.freedesktop.StatusNotifierWatcher", |
205 | "org.freedesktop.StatusNotifierWatcher", | 108 | "/StatusNotifierWatcher","org.swaywm.LessSuckyStatusNotifierWatcher", |
206 | "/StatusNotifierWatcher", | 109 | "RegisteredObjectPathItems", "a(os)", get_obj_items_reply, NULL); |
207 | "org.freedesktop.DBus.Properties", | ||
208 | "Get"); | ||
209 | |||
210 | iface = "org.swaywm.LessSuckyStatusNotifierWatcher"; | ||
211 | prop = "RegisteredObjectPathItems"; | ||
212 | dbus_message_append_args(message, | ||
213 | DBUS_TYPE_STRING, &iface, | ||
214 | DBUS_TYPE_STRING, &prop, | ||
215 | DBUS_TYPE_INVALID); | ||
216 | |||
217 | status = dbus_connection_send_with_reply(conn, message, &pending, -1); | ||
218 | dbus_message_unref(message); | ||
219 | |||
220 | if (!(pending || status)) { | ||
221 | sway_log(L_ERROR, "Could not get items"); | ||
222 | return; | ||
223 | } | ||
224 | dbus_pending_call_set_notify(pending, get_obj_items_reply, NULL, NULL); | ||
225 | } | 110 | } |
226 | 111 | ||
227 | static DBusHandlerResult signal_handler(DBusConnection *connection, | 112 | static DBusHandlerResult signal_handler(DBusConnection *connection, |