1 /* -*- Mode: C ; c-basic-offset: 4 -*- */
2 /*
3     Copyright (C) 2007,2008 Nedko Arnaudov
4     Copyright (C) 2007-2008 Juuso Alasuutari
5     Copyright (C) 2008 Marc-Olivier Barre
6 
7     This program is free software; you can redistribute it and/or modify
8     it under the terms of the GNU General Public License as published by
9     the Free Software Foundation; either version 2 of the License.
10 
11     This program is distributed in the hope that it will be useful,
12     but WITHOUT ANY WARRANTY; without even the implied warranty of
13     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14     GNU General Public License for more details.
15 
16     You should have received a copy of the GNU General Public License
17     along with this program; if not, write to the Free Software
18     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 
20 */
21 
22 #ifndef DBUS_H__3DB2458F_44B2_43EA_882A_9F888DF71A88__INCLUDED
23 #define DBUS_H__3DB2458F_44B2_43EA_882A_9F888DF71A88__INCLUDED
24 
25 #include <stdbool.h>
26 
27 #define JACK_DBUS_DEBUG
28 
29 //#define DISABLE_SIGNAL_MAGIC
30 
31 #define DEFAULT_XDG_CONFIG "/.config"
32 #define DEFAULT_XDG_LOG "/.log"
33 #define JACKDBUS_DIR "/jack"
34 #define JACKDBUS_LOG "/jackdbus.log"
35 #define JACKDBUS_CONF "/conf.xml"
36 
37 extern char *g_jackdbus_config_dir;
38 extern size_t g_jackdbus_config_dir_len; /* without terminating '\0' char */
39 extern int g_exit_command;
40 
41 bool
42 jack_controller_settings_init();
43 
44 void
45 jack_controller_settings_uninit();
46 
47 #define JACK_DBUS_ERROR_UNKNOWN_METHOD              "org.jackaudio.Error.UnknownMethod"
48 #define JACK_DBUS_ERROR_SERVER_NOT_RUNNING          "org.jackaudio.Error.ServerNotRunning"
49 #define JACK_DBUS_ERROR_SERVER_RUNNING              "org.jackaudio.Error.ServerRunning"
50 #define JACK_DBUS_ERROR_UNKNOWN_DRIVER              "org.jackaudio.Error.UnknownDriver"
51 #define JACK_DBUS_ERROR_UNKNOWN_INTERNAL            "org.jackaudio.Error.UnknownInternal"
52 #define JACK_DBUS_ERROR_UNKNOWN_PARAMETER           "org.jackaudio.Error.UnknownParameter"
53 #define JACK_DBUS_ERROR_INVALID_ARGS                "org.jackaudio.Error.InvalidArgs"
54 #define JACK_DBUS_ERROR_GENERIC                     "org.jackaudio.Error.Generic"
55 #define JACK_DBUS_ERROR_FATAL                       "org.jackaudio.Error.Fatal"
56 
57 struct jack_dbus_method_call
58 {
59     void *context;
60     DBusConnection *connection;
61     const char *method_name;
62     DBusMessage *message;
63     DBusMessage *reply;
64 };
65 
66 struct jack_dbus_interface_method_argument_descriptor
67 {
68     const char * name;
69     const char * type;
70     bool direction_out;     /* true - out, false - in */
71 };
72 
73 struct jack_dbus_interface_method_descriptor
74 {
75     const char * name;
76     const struct jack_dbus_interface_method_argument_descriptor * arguments;
77     void (* handler)(struct jack_dbus_method_call * call);
78 };
79 
80 struct jack_dbus_interface_signal_argument_descriptor
81 {
82     const char * name;
83     const char * type;
84 };
85 
86 struct jack_dbus_interface_signal_descriptor
87 {
88     const char * name;
89     const struct jack_dbus_interface_signal_argument_descriptor * arguments;
90 };
91 
92 struct jack_dbus_interface_descriptor
93 {
94     const char * name;
95 
96     bool
97     (* handler)(
98         struct jack_dbus_method_call * call,
99         const struct jack_dbus_interface_method_descriptor * methods);
100 
101     const struct jack_dbus_interface_method_descriptor * methods;
102     const struct jack_dbus_interface_signal_descriptor * signals;
103 };
104 
105 struct jack_dbus_object_descriptor
106 {
107     struct jack_dbus_interface_descriptor ** interfaces;
108     void * context;
109 };
110 
111 typedef union
112 {
113     unsigned char byte;
114     dbus_bool_t boolean;
115     dbus_int16_t int16;
116     dbus_uint16_t uint16;
117     dbus_int32_t int32;
118     dbus_uint32_t uint32;
119     dbus_int64_t int64;
120     dbus_uint64_t uint64;
121     double doubl;
122     const char *string;
123 } message_arg_t;
124 
125 #define JACK_DBUS_METHOD_ARGUMENTS_BEGIN(method_name)                                   \
126 static const                                                                            \
127 struct jack_dbus_interface_method_argument_descriptor method_name ## _arguments[] =     \
128 {
129 
130 #define JACK_DBUS_METHOD_ARGUMENTS_BEGIN_EX(method_name, descr)                         \
131 static const                                                                            \
132 struct jack_dbus_interface_method_argument_descriptor method_name ## _arguments[] =     \
133 {
134 
135 #define JACK_DBUS_METHOD_ARGUMENT(argument_name, argument_type, argument_direction_out) \
136         {                                                                               \
137                 .name = argument_name,                                                  \
138                 .type = argument_type,                                                  \
139                 .direction_out = argument_direction_out                                 \
140         },
141 
142 #define JACK_DBUS_METHOD_ARGUMENT_IN(argument_name, argument_type, descr)               \
143         {                                                                               \
144                 .name = argument_name,                                                  \
145                 .type = argument_type,                                                  \
146                 .direction_out = false                                                  \
147         },
148 
149 #define JACK_DBUS_METHOD_ARGUMENT_OUT(argument_name, argument_type, descr)              \
150         {                                                                               \
151                 .name = argument_name,                                                  \
152                 .type = argument_type,                                                  \
153                 .direction_out = true                                                  \
154         },
155 
156 #define JACK_DBUS_METHOD_ARGUMENT(argument_name, argument_type, argument_direction_out) \
157         {                                                                               \
158                 .name = argument_name,                                                  \
159                 .type = argument_type,                                                  \
160                 .direction_out = argument_direction_out                                 \
161         },
162 
163 #define JACK_DBUS_METHOD_ARGUMENTS_END                                                  \
164     JACK_DBUS_METHOD_ARGUMENT(NULL, NULL, false)                                        \
165 };
166 
167 #define JACK_DBUS_METHODS_BEGIN                                                         \
168 static const                                                                            \
169 struct jack_dbus_interface_method_descriptor methods_dtor[] =                           \
170 {
171 
172 #define JACK_DBUS_METHOD_DESCRIBE(method_name, handler_name)                            \
173         {                                                                               \
174             .name = # method_name,                                                      \
175             .arguments = method_name ## _arguments,                                     \
176             .handler = handler_name                                                     \
177         },
178 
179 #define JACK_DBUS_METHODS_END                                                           \
180         {                                                                               \
181             .name = NULL,                                                               \
182             .arguments = NULL,                                                          \
183             .handler = NULL                                                             \
184         }                                                                               \
185 };
186 
187 #define JACK_DBUS_SIGNAL_ARGUMENTS_BEGIN(signal_name)                                   \
188 static const                                                                            \
189 struct jack_dbus_interface_signal_argument_descriptor signal_name ## _arguments[] =     \
190 {
191 
192 #define JACK_DBUS_SIGNAL_ARGUMENT(argument_name, argument_type)                         \
193         {                                                                               \
194                 .name = argument_name,                                                  \
195                 .type = argument_type                                                   \
196         },
197 
198 #define JACK_DBUS_SIGNAL_ARGUMENTS_END                                                  \
199         JACK_DBUS_SIGNAL_ARGUMENT(NULL, NULL)                                           \
200 };
201 
202 #define JACK_DBUS_SIGNALS_BEGIN                                                         \
203 static const                                                                            \
204 struct jack_dbus_interface_signal_descriptor signals_dtor[] =                           \
205 {
206 
207 #define JACK_DBUS_SIGNAL_DESCRIBE(signal_name)                                          \
208         {                                                                               \
209                 .name = # signal_name,                                                  \
210                 .arguments = signal_name ## _arguments                                  \
211         },
212 
213 #define JACK_DBUS_SIGNALS_END                                                           \
214         {                                                                               \
215                 .name = NULL,                                                           \
216                 .arguments = NULL,                                                      \
217         }                                                                               \
218 };
219 
220 #define JACK_DBUS_IFACE_BEGIN(iface_var, iface_name)                                    \
221 struct jack_dbus_interface_descriptor iface_var =                                       \
222 {                                                                                       \
223         .name = iface_name,                                                             \
224         .handler = jack_dbus_run_method,
225 
226 #define JACK_DBUS_IFACE_HANDLER(handler_func)                                           \
227         .handler = handler_func,
228 
229 #define JACK_DBUS_IFACE_EXPOSE_METHODS                                                  \
230         .methods = methods_dtor,
231 
232 #define JACK_DBUS_IFACE_EXPOSE_SIGNALS                                                  \
233         .signals = signals_dtor,
234 
235 #define JACK_DBUS_IFACE_END                                                             \
236 };
237 
238 DBusHandlerResult
239 jack_dbus_message_handler(
240     DBusConnection *connection,
241     DBusMessage *message,
242     void *data);
243 
244 void
245 jack_dbus_message_handler_unregister(
246     DBusConnection *connection,
247     void *data);
248 
249 bool
250 jack_dbus_run_method(
251     struct jack_dbus_method_call * call,
252     const struct jack_dbus_interface_method_descriptor * methods);
253 
254 void
255 jack_dbus_error(
256     void *dbus_call_context_ptr,
257     const char *error_name,
258     const char *format,
259     ...);
260 
261 void
262 jack_dbus_only_error(
263     void *dbus_call_context_ptr,
264     const char *error_name,
265     const char *format,
266     ...);
267 
268 bool
269 jack_dbus_get_method_args(
270     struct jack_dbus_method_call *call,
271     int type,
272     ...);
273 
274 bool
275 jack_dbus_get_method_args_string_and_variant(
276     struct jack_dbus_method_call *call,
277     const char **arg1,
278     message_arg_t *arg2,
279     int *type_ptr);
280 
281 bool
282 jack_dbus_get_method_args_two_strings_and_variant(
283     struct jack_dbus_method_call *call,
284     const char **arg1,
285     const char **arg2,
286     message_arg_t *arg3,
287     int *type_ptr);
288 
289 bool
290 jack_dbus_message_append_variant(
291     DBusMessageIter *iter,
292     int type,
293     const char *signature,
294     message_arg_t *arg);
295 
296 void
297 jack_dbus_construct_method_return_empty(
298     struct jack_dbus_method_call * call);
299 
300 void
301 jack_dbus_construct_method_return_single(
302     struct jack_dbus_method_call *call,
303     int type,
304     message_arg_t arg);
305 
306 void
307 jack_dbus_construct_method_return_array_of_strings(
308     struct jack_dbus_method_call *call,
309     unsigned int num_members,
310     const char **array);
311 
312 void
313 jack_dbus_send_signal(
314     const char *sender_object_path,
315     const char *iface,
316     const char *signal_name,
317     int first_arg_type,
318     ...);
319 
320 #define JACK_CONTROLLER_OBJECT_PATH "/org/jackaudio/Controller"
321 
322 extern struct jack_dbus_interface_descriptor * g_jackcontroller_interfaces[];
323 extern DBusConnection * g_connection;
324 
325 #endif /* #ifndef DBUS_H__3DB2458F_44B2_43EA_882A_9F888DF71A88__INCLUDED */
326