1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
|
/*
* Copyright (c) 2012, 2013, Intel Corporation
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* * Neither the name of Intel Corporation nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef __MURPHY_DBUS_LIBDBUS_H__
#define __MURPHY_DBUS_LIBDBUS_H__
#include <murphy/common/mainloop.h>
#include <murphy/common/dbus-error.h>
#include <dbus/dbus.h>
/** Type for a D-Bus (connection). */
struct mrp_dbus_s;
typedef struct mrp_dbus_s mrp_dbus_t;
/** Type for a D-Bus message. */
struct mrp_dbus_msg_s;
typedef struct mrp_dbus_msg_s mrp_dbus_msg_t;
/** Type for a D-Bus error. */
typedef DBusError mrp_dbus_err_t;
/** D-BUS method or signal callback type. */
typedef int (*mrp_dbus_handler_t)(mrp_dbus_t *, mrp_dbus_msg_t *, void *);
/** Create a new connection to the given bus. */
mrp_dbus_t *mrp_dbus_connect(mrp_mainloop_t *ml, const char *address,
mrp_dbus_err_t *errp);
#define mrp_dbus_get mrp_dbus_connect
/** Set up a DBusConnection with a mainloop. */
int mrp_dbus_setup_connection(mrp_mainloop_t *ml, DBusConnection *conn);
/** Increase the reference count of the given DBus (connection). */
mrp_dbus_t *mrp_dbus_ref(mrp_dbus_t *dbus);
/** Decrease the reference count of the given DBus (connection). */
int mrp_dbus_unref(mrp_dbus_t *dbus);
/** Acquire the given name on the given bus (connection). */
int mrp_dbus_acquire_name(mrp_dbus_t *dbus, const char *name,
mrp_dbus_err_t *error);
/** Release the given name on the given bus (connection). */
int mrp_dbus_release_name(mrp_dbus_t *dbus, const char *name,
mrp_dbus_err_t *error);
/** Type for a name tracking callback. */
typedef void (*mrp_dbus_name_cb_t)(mrp_dbus_t *, const char *, int,
const char *, void *);
/** Start tracking the given name. */
int mrp_dbus_follow_name(mrp_dbus_t *dbus, const char *name,
mrp_dbus_name_cb_t cb, void *user_data);
/** Stop tracking the given name. */
int mrp_dbus_forget_name(mrp_dbus_t *dbus, const char *name,
mrp_dbus_name_cb_t cb, void *user_data);
/** Export a method to the bus. */
int mrp_dbus_export_method(mrp_dbus_t *dbus, const char *path,
const char *interface, const char *member,
mrp_dbus_handler_t handler, void *user_data);
/** Remove an exported method. */
int mrp_dbus_remove_method(mrp_dbus_t *dbus, const char *path,
const char *interface, const char *member,
mrp_dbus_handler_t handler, void *user_data);
/** Install a filter and add a handler for the given signal on the bus. */
MRP_NULLTERM int mrp_dbus_subscribe_signal(mrp_dbus_t *dbus,
mrp_dbus_handler_t handler,
void *user_data,
const char *sender,
const char *path,
const char *interface,
const char *member, ...);
/** Remove the signal handler and filter for the given signal on the bus. */
MRP_NULLTERM int mrp_dbus_unsubscribe_signal(mrp_dbus_t *dbus,
mrp_dbus_handler_t handler,
void *user_data,
const char *sender,
const char *path,
const char *interface,
const char *member, ...);
/** Install a filter for the given message on the bus. */
MRP_NULLTERM int mrp_dbus_install_filter(mrp_dbus_t *dbus,
const char *sender,
const char *path,
const char *interface,
const char *member, ...);
/** Install a filter for the given message on the bus. */
int mrp_dbus_install_filterv(mrp_dbus_t *dbus,
const char *sender,
const char *path,
const char *interface,
const char *member,
va_list ap);
/** Remove a filter for the given message on the bus. */
MRP_NULLTERM int mrp_dbus_remove_filter(mrp_dbus_t *dbus,
const char *sender,
const char *path,
const char *interface,
const char *member, ...);
/** Remove a filter for the given message on the bus. */
int mrp_dbus_remove_filterv(mrp_dbus_t *dbus,
const char *sender,
const char *path,
const char *interface,
const char *member,
va_list ap);
/** Add a signal handler for the gvien signal on the bus. */
int mrp_dbus_add_signal_handler(mrp_dbus_t *dbus, const char *sender,
const char *path, const char *interface,
const char *member, mrp_dbus_handler_t handler,
void *user_data);
/** Remove the given signal handler for the given signal on the bus. */
int mrp_dbus_del_signal_handler(mrp_dbus_t *dbus, const char *sender,
const char *path, const char *interface,
const char *member, mrp_dbus_handler_t handler,
void *user_data);
/** Type of a method call reply callback. */
typedef void (*mrp_dbus_reply_cb_t)(mrp_dbus_t *dbus, mrp_dbus_msg_t *reply,
void *user_data);
/** Call the given method on the bus. */
int32_t mrp_dbus_call(mrp_dbus_t *dbus, const char *dest,
const char *path, const char *interface,
const char *member, int timeout,
mrp_dbus_reply_cb_t cb, void *user_data,
int dbus_type, ...);
/** Cancel an ongoing method call on the bus. */
int mrp_dbus_call_cancel(mrp_dbus_t *dbus, int32_t id);
/** Send a reply to the given method call on the bus. */
int mrp_dbus_reply(mrp_dbus_t *dbus, mrp_dbus_msg_t *msg, int type, ...);
/** Send an error reply to the given method call on the bus. */
int mrp_dbus_reply_error(mrp_dbus_t *dbus, mrp_dbus_msg_t *msg,
const char *errname, const char *errmsg,
int type, ...);
/** Emit the given signal on the bus. */
int mrp_dbus_signal(mrp_dbus_t *dbus, const char *dest, const char *path,
const char *interface, const char *member, int type, ...);
/** Send the given method call message on the bus. */
int32_t mrp_dbus_send(mrp_dbus_t *dbus, const char *dest, const char *path,
const char *interface, const char *member, int timeout,
mrp_dbus_reply_cb_t cb, void *user_data,
mrp_dbus_msg_t *msg);
/** Send the given message on the bus. */
int mrp_dbus_send_msg(mrp_dbus_t *dbus, mrp_dbus_msg_t *msg);
/** Get our unique name on the bus. */
const char *mrp_dbus_get_unique_name(mrp_dbus_t *dbus);
/** Initialize the given error. */
static inline mrp_dbus_err_t *mrp_dbus_error_init(mrp_dbus_err_t *err)
{
if (err != NULL)
dbus_error_init(err);
return err;
}
/** Set the given error buffer up with the error name and message. */
static inline mrp_dbus_err_t *mrp_dbus_error_set(mrp_dbus_err_t *err,
const char *name,
const char *message)
{
dbus_set_error_const(err, name, message);
return err;
}
/** Get the error message from the given bus error message. */
static inline const char *mrp_dbus_errmsg(mrp_dbus_err_t *err)
{
if (err && dbus_error_is_set(err))
return err->message;
else
return "unknown DBUS error";
}
/** Increase the reference count of a message. */
mrp_dbus_msg_t *mrp_dbus_msg_ref(mrp_dbus_msg_t *m);
/** Decrease the reference count of a message, freeing it if necessary. */
int mrp_dbus_msg_unref(mrp_dbus_msg_t *m);
/** Create a new method call message. */
mrp_dbus_msg_t *mrp_dbus_msg_method_call(mrp_dbus_t *bus,
const char *destination,
const char *path,
const char *interface,
const char *member);
/** Create a new method return message. */
mrp_dbus_msg_t *mrp_dbus_msg_method_return(mrp_dbus_t *bus,
mrp_dbus_msg_t *msg);
/** Create a new error reply message. */
mrp_dbus_msg_t *mrp_dbus_msg_error(mrp_dbus_t *bus, mrp_dbus_msg_t *msg,
mrp_dbus_err_t *err);
/** Create a new signal message. */
mrp_dbus_msg_t *mrp_dbus_msg_signal(mrp_dbus_t *bus,
const char *destination,
const char *path,
const char *interface,
const char *member);
/** Bus message types. */
typedef enum {
# define TYPE(type) MRP_DBUS_MESSAGE_TYPE_##type = DBUS_MESSAGE_TYPE_##type
TYPE(INVALID),
TYPE(METHOD_CALL),
TYPE(METHOD_RETURN),
TYPE(ERROR),
TYPE(SIGNAL)
# undef TYPE
} mrp_dbus_msg_type_t;
/** Get the type of the given message. */
mrp_dbus_msg_type_t mrp_dbus_msg_type(mrp_dbus_msg_t *msg);
/** Message type checking convenience functions. */
#define TYPE_CHECK_FUNCTION(type, TYPE) \
static inline int mrp_dbus_msg_is_##type(mrp_dbus_msg_t *msg) \
{ \
return mrp_dbus_msg_type(msg) == MRP_DBUS_MESSAGE_TYPE_##TYPE; \
} \
struct __mrp_dbus_allow_traling_semicolon
TYPE_CHECK_FUNCTION(method_call , METHOD_CALL);
TYPE_CHECK_FUNCTION(method_return, METHOD_RETURN);
TYPE_CHECK_FUNCTION(error , ERROR);
TYPE_CHECK_FUNCTION(signal , SIGNAL);
/** Message argument types. */
typedef enum {
#define TYPE(t) MRP_DBUS_TYPE_##t = DBUS_TYPE_##t
TYPE(INVALID),
TYPE(BYTE),
TYPE(BOOLEAN),
TYPE(INT16),
TYPE(UINT16),
TYPE(INT32),
TYPE(UINT32),
TYPE(INT64),
TYPE(UINT64),
TYPE(DOUBLE),
TYPE(STRING),
TYPE(OBJECT_PATH),
TYPE(SIGNATURE),
TYPE(UNIX_FD),
TYPE(ARRAY),
TYPE(VARIANT),
TYPE(STRUCT),
TYPE(DICT_ENTRY),
#undef TYPE
} mrp_dbus_type_t;
/** Message argument types as strings. */
#define MRP_DBUS_TYPE_BYTE_AS_STRING DBUS_TYPE_BYTE_AS_STRING
#define MRP_DBUS_TYPE_BOOLEAN_AS_STRING DBUS_TYPE_BOOLEAN_AS_STRING
#define MRP_DBUS_TYPE_INT16_AS_STRING DBUS_TYPE_INT16_AS_STRING
#define MRP_DBUS_TYPE_UINT16_AS_STRING DBUS_TYPE_UINT16_AS_STRING
#define MRP_DBUS_TYPE_INT32_AS_STRING DBUS_TYPE_INT32_AS_STRING
#define MRP_DBUS_TYPE_UINT32_AS_STRING DBUS_TYPE_UINT32_AS_STRING
#define MRP_DBUS_TYPE_INT64_AS_STRING DBUS_TYPE_INT64_AS_STRING
#define MRP_DBUS_TYPE_UINT64_AS_STRING DBUS_TYPE_UINT64_AS_STRING
#define MRP_DBUS_TYPE_DOUBLE_AS_STRING DBUS_TYPE_DOUBLE_AS_STRING
#define MRP_DBUS_TYPE_STRING_AS_STRING DBUS_TYPE_STRING_AS_STRING
#define MRP_DBUS_TYPE_OBJECT_PATH_AS_STRING DBUS_TYPE_OBJECT_PATH_AS_STRING
#define MRP_DBUS_TYPE_SIGNATURE_AS_STRING DBUS_TYPE_SIGNATURE_AS_STRING
#define MRP_DBUS_TYPE_UNIX_FD_AS_STRING DBUS_TYPE_UNIX_FD_AS_STRING
#define MRP_DBUS_TYPE_ARRAY_AS_STRING DBUS_TYPE_ARRAY_AS_STRING
#define MRP_DBUS_TYPE_VARIANT_AS_STRING DBUS_TYPE_VARIANT_AS_STRING
#define MRP_DBUS_TYPE_STRUCT_AS_STRING DBUS_TYPE_STRUCT_AS_STRING
#define MRP_DBUS_TYPE_DICT_ENTRY_AS_STRING DBUS_TYPE_DICT_ENTRY_AS_STRING
/** Get the path of the given message. */
const char *mrp_dbus_msg_path(mrp_dbus_msg_t *msg);
/** Get the interface of the given message. */
const char *mrp_dbus_msg_interface(mrp_dbus_msg_t *msg);
/** Get the member of the given message. */
const char *mrp_dbus_msg_member(mrp_dbus_msg_t *msg);
/** Get the destination of the given message. */
const char *mrp_dbus_msg_destination(mrp_dbus_msg_t *msg);
/** Get the sender of the given message. */
const char *mrp_dbus_msg_sender(mrp_dbus_msg_t *msg);
/** Open a new container of the given type and cotained types. */
int mrp_dbus_msg_open_container(mrp_dbus_msg_t *m, char type,
const char *contents);
/** Close the current container. */
int mrp_dbus_msg_close_container(mrp_dbus_msg_t *m);
/** Append an argument of a basic type to the given message. */
int mrp_dbus_msg_append_basic(mrp_dbus_msg_t *m, char type, void *valuep);
/** Get the type of the current message argument. */
mrp_dbus_type_t mrp_dbus_msg_arg_type(mrp_dbus_msg_t *m, const char **contents);
/** Open the current container (of the given type and contents) for reading. */
int mrp_dbus_msg_enter_container(mrp_dbus_msg_t *msg, char type,
const char *contents);
/** Exit from the container being currently read. */
int mrp_dbus_msg_exit_container(mrp_dbus_msg_t *m);
/** Read the next argument (of basic type) from the given message. */
int mrp_dbus_msg_read_basic(mrp_dbus_msg_t *m, char type, void *valuep);
/** Read the next array of one of the basic types. */
int mrp_dbus_msg_read_array(mrp_dbus_msg_t *msg, char type,
void **itemsp, size_t *nitemp);
#endif /* __MURPHY_DBUS_LIBDBUS_H__ */
|