_dbus_bindings: debug-impl.h -> debug.c
[dbus-python-phuang.git] / _dbus_bindings / bus.c
blob66e0d1147835e7514da7b0bbcb752178b8304cec
1 /* Implementation of Bus, a subtype of Connection.
3 * Copyright (C) 2006 Collabora Ltd.
5 * Licensed under the Academic Free License version 2.1
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 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
25 #include "dbus_bindings-internal.h"
26 #include "conn-internal.h"
28 PyDoc_STRVAR(Bus_tp_doc,
29 "BusImplementation([address: str or int])\n\n"
30 "If the address is an int it must be one of the constants BUS_SESSION,\n"
31 "BUS_SYSTEM, BUS_STARTER. The default is BUS_SESSION.\n"
34 /* Bus definition =================================================== */
36 static PyTypeObject BusType;
38 #define Bus_Check(ob) PyObject_TypeCheck(ob, &BusType)
40 /* Bus methods ====================================================== */
42 static PyObject *
43 Bus_tp_new (PyTypeObject *cls, PyObject *args, PyObject *kwargs)
45 PyObject *first = NULL, *mainloop = NULL;
46 DBusConnection *conn;
47 DBusError error;
48 Connection *self;
49 dbus_bool_t ret;
50 long type;
51 static char *argnames[] = {"address_or_type", "mainloop", NULL};
53 if (!PyArg_ParseTupleAndKeywords (args, kwargs, "|OO", argnames,
54 &first, &mainloop)) {
55 return NULL;
58 dbus_error_init (&error);
60 if (first && PyString_Check(first)) {
61 /* It's a custom address. First connect to it, then register. */
63 self = (Connection *)(DBusPyConnectionType.tp_new)(cls, args, kwargs);
64 if (!self) return NULL;
66 Py_BEGIN_ALLOW_THREADS
67 ret = dbus_bus_register(self->conn, &error);
68 Py_END_ALLOW_THREADS
69 if (!ret) {
70 DBusPyException_ConsumeError(&error);
71 Py_DECREF(self);
72 return NULL;
75 return (PyObject *)self;
78 /* If the first argument isn't a string, it must be an integer
79 representing one of the well-known bus types. */
81 if (first && !PyInt_Check (first)) {
82 PyErr_SetString(PyExc_TypeError, "A string address or an integer "
83 "bus type is required");
84 return NULL;
86 if (first) {
87 type = PyInt_AsLong (first);
89 else {
90 type = DBUS_BUS_SESSION;
93 if (type != DBUS_BUS_SESSION && type != DBUS_BUS_SYSTEM
94 && type != DBUS_BUS_STARTER) {
95 PyErr_Format(PyExc_ValueError, "Unknown bus type %d", (int)type);
96 return NULL;
99 Py_BEGIN_ALLOW_THREADS
100 conn = dbus_bus_get_private (type, &error);
101 Py_END_ALLOW_THREADS
103 if (!conn) {
104 DBusPyException_ConsumeError (&error);
105 return NULL;
107 return DBusPyConnection_NewConsumingDBusConnection(cls, conn, mainloop);
110 PyDoc_STRVAR(Bus_get_unique_name__doc__,
111 "get_unique_name() -> str\n\n"
112 "Return this application's unique name on this bus.\n");
113 static PyObject *
114 Bus_get_unique_name (Connection *self, PyObject *args UNUSED)
116 const char *name;
118 Py_BEGIN_ALLOW_THREADS
119 name = dbus_bus_get_unique_name (self->conn);
120 Py_END_ALLOW_THREADS
121 if (!name) {
122 /* shouldn't happen, but C subtypes could have done something stupid */
123 PyErr_SetString(DBusPyException, "Unable to retrieve unique name");
124 return NULL;
126 return PyString_FromString (name);
129 PyDoc_STRVAR(Bus_get_unix_user__doc__,
130 "get_unix_user(bus_name: str) -> int\n"
131 "\n"
132 "Get the numeric uid of the process which owns the given bus name\n"
133 "on the connected bus daemon.\n"
134 "\n"
135 ":Parameters:\n"
136 " `bus_name` : str\n"
137 " A bus name (may be either a unique name or a well-known name)\n"
139 static PyObject *
140 Bus_get_unix_user (Connection *self, PyObject *args)
142 DBusError error;
143 unsigned long uid;
144 const char *bus_name;
146 if (!PyArg_ParseTuple(args, "s:get_unix_user", &bus_name)) {
147 return NULL;
150 dbus_error_init (&error);
151 Py_BEGIN_ALLOW_THREADS
152 uid = dbus_bus_get_unix_user (self->conn, bus_name, &error);
153 Py_END_ALLOW_THREADS
154 if (uid == (unsigned long)(-1)) return DBusPyException_ConsumeError(&error);
155 return PyLong_FromUnsignedLong (uid);
158 PyDoc_STRVAR(Bus_start_service_by_name__doc__,
159 "start_service_by_name(bus_name: str) -> (True, int)\n\
161 Start a service which will implement the given bus name on this\n\
162 Bus.\n\
164 :Parameters:\n\
165 `bus_name` : str\n\
166 The well-known bus name for which an implementation is required\n\
168 :Returns: A tuple of 2 elements. The first is always True, the second is\n\
169 either START_REPLY_SUCCESS or START_REPLY_ALREADY_RUNNING.\n\
171 :Raises DBusException: if the service could not be started.\n\
173 FIXME: Fix return signature?\n\
175 static PyObject *
176 Bus_start_service_by_name (Connection *self, PyObject *args)
178 DBusError error;
179 const char *bus_name;
180 dbus_uint32_t ret;
181 dbus_bool_t success;
183 if (!PyArg_ParseTuple(args, "s:start_service_by_name", &bus_name)) {
184 return NULL;
186 dbus_error_init (&error);
187 Py_BEGIN_ALLOW_THREADS
188 success = dbus_bus_start_service_by_name (self->conn, bus_name,
189 0 /* flags */, &ret, &error);
190 Py_END_ALLOW_THREADS
191 if (!success) {
192 return DBusPyException_ConsumeError(&error);
194 return Py_BuildValue ("(Ol)", Py_True, (long)ret);
197 /* FIXME: signal IN_QUEUE, EXISTS by exception? */
198 PyDoc_STRVAR(Bus_request_name__doc__, "");
199 static PyObject *
200 Bus_request_name (Connection *self, PyObject *args)
202 unsigned int flags = 0;
203 const char *bus_name;
204 int ret;
205 DBusError error;
207 if (!PyArg_ParseTuple(args, "s|I:request_name", &bus_name, &flags)) {
208 return NULL;
210 if (!dbus_py_validate_bus_name(bus_name, 0, 1)) return NULL;
212 dbus_error_init (&error);
213 Py_BEGIN_ALLOW_THREADS
214 ret = dbus_bus_request_name(self->conn, bus_name, flags, &error);
215 Py_END_ALLOW_THREADS
216 if (ret == -1) return DBusPyException_ConsumeError(&error);
218 return PyInt_FromLong(ret);
221 PyDoc_STRVAR(Bus_release_name__doc__, "");
222 static PyObject *
223 Bus_release_name (Connection *self, PyObject *args)
225 const char *bus_name;
226 int ret;
227 DBusError error;
229 if (!PyArg_ParseTuple(args, "s:release_name", &bus_name)) return NULL;
231 dbus_error_init (&error);
232 Py_BEGIN_ALLOW_THREADS
233 ret = dbus_bus_release_name(self->conn, bus_name, &error);
234 Py_END_ALLOW_THREADS
235 if (ret == -1) return DBusPyException_ConsumeError(&error);
237 return PyInt_FromLong(ret);
240 PyDoc_STRVAR (Bus_name_has_owner__doc__,
241 "name_has_owner(bus_name: str) -> bool\n\n"
242 "Return True if and only if the given bus name has an owner on this bus.\n");
243 static PyObject *
244 Bus_name_has_owner (Connection *self, PyObject *args)
246 const char *bus_name;
247 int ret;
248 DBusError error;
250 if (!PyArg_ParseTuple(args, "s:name_has_owner", &bus_name)) return NULL;
251 dbus_error_init (&error);
252 Py_BEGIN_ALLOW_THREADS
253 ret = dbus_bus_name_has_owner(self->conn, bus_name, &error);
254 Py_END_ALLOW_THREADS
255 if (dbus_error_is_set (&error)) {
256 return DBusPyException_ConsumeError(&error);
258 return PyBool_FromLong(ret);
261 PyDoc_STRVAR (Bus_add_match_string__doc__,
262 "add_match_string(rule: str)\n\n"
263 "Arrange for this application to receive messages on the bus that match\n"
264 "the given rule. This version will block and raises DBusException on error.\n");
265 static PyObject *
266 Bus_add_match_string (Connection *self, PyObject *args)
268 const char *rule;
269 DBusError error;
271 if (!PyArg_ParseTuple(args, "s:add_match", &rule)) return NULL;
272 dbus_error_init (&error);
273 Py_BEGIN_ALLOW_THREADS
274 dbus_bus_add_match (self->conn, rule, &error);
275 Py_END_ALLOW_THREADS
276 if (dbus_error_is_set (&error)) {
277 return DBusPyException_ConsumeError(&error);
279 Py_RETURN_NONE;
282 PyDoc_STRVAR (Bus_add_match_string_non_blocking__doc__,
283 "add_match_string_non_blocking(rule: str)\n\n"
284 "Arrange for this application to receive messages on the bus that match\n"
285 "the given rule. This version does not block, but any errors will be\n"
286 "ignored.\n");
287 static PyObject *
288 Bus_add_match_string_non_blocking (Connection *self, PyObject *args)
290 const char *rule;
292 if (!PyArg_ParseTuple(args, "s:add_match", &rule)) return NULL;
293 Py_BEGIN_ALLOW_THREADS
294 dbus_bus_add_match (self->conn, rule, NULL);
295 Py_END_ALLOW_THREADS
296 Py_RETURN_NONE;
299 PyDoc_STRVAR (Bus_remove_match_string__doc__,
300 "remove_match_string(rule: str)\n\n"
301 "Remove the given match rule; if it has been added more than once,\n"
302 "remove one of the identical copies, leaving the others active.\n"
303 "This version blocks, and raises DBusException on error.\n");
304 static PyObject *
305 Bus_remove_match_string (Connection *self, PyObject *args)
307 const char *rule;
308 DBusError error;
310 if (!PyArg_ParseTuple(args, "s:remove_match", &rule)) return NULL;
311 dbus_error_init (&error);
312 Py_BEGIN_ALLOW_THREADS
313 dbus_bus_remove_match (self->conn, rule, &error);
314 Py_END_ALLOW_THREADS
315 if (dbus_error_is_set (&error)) {
316 return DBusPyException_ConsumeError(&error);
318 Py_RETURN_NONE;
321 PyDoc_STRVAR (Bus_remove_match_string_non_blocking__doc__,
322 "remove_match_string_non_blocking(rule: str)\n\n"
323 "Remove the given match rule; if it has been added more than once,\n"
324 "remove one of the identical copies, leaving the others active.\n"
325 "This version does not block, but causes any errors to be ignored.\n");
326 static PyObject *
327 Bus_remove_match_string_non_blocking (Connection *self, PyObject *args)
329 const char *rule;
331 if (!PyArg_ParseTuple(args, "s:remove_match", &rule)) return NULL;
332 Py_BEGIN_ALLOW_THREADS
333 dbus_bus_remove_match (self->conn, rule, NULL);
334 Py_END_ALLOW_THREADS
335 Py_RETURN_NONE;
338 /* Bus type object ================================================== */
340 static struct PyMethodDef Bus_tp_methods[] = {
341 #define ENTRY(name, flags) {#name, (PyCFunction)Bus_##name, flags, Bus_##name##__doc__},
342 ENTRY(get_unique_name, METH_NOARGS)
343 ENTRY(get_unix_user, METH_VARARGS)
344 ENTRY(start_service_by_name, METH_VARARGS)
345 ENTRY(request_name, METH_VARARGS)
346 ENTRY(release_name, METH_VARARGS)
347 ENTRY(name_has_owner, METH_VARARGS)
348 ENTRY(add_match_string, METH_VARARGS)
349 ENTRY(add_match_string_non_blocking, METH_VARARGS)
350 ENTRY(remove_match_string, METH_VARARGS)
351 ENTRY(remove_match_string_non_blocking, METH_VARARGS)
352 #undef ENTRY
353 {NULL},
356 static PyTypeObject BusType = {
357 PyObject_HEAD_INIT(NULL)
358 0, /*ob_size*/
359 "_dbus_bindings.BusImplementation", /*tp_name*/
360 0, /*tp_basicsize*/
361 0, /*tp_itemsize*/
362 /* methods */
363 0, /*tp_dealloc*/
364 0, /*tp_print*/
365 0, /*tp_getattr*/
366 0, /*tp_setattr*/
367 0, /*tp_compare*/
368 0, /*tp_repr*/
369 0, /*tp_as_number*/
370 0, /*tp_as_sequence*/
371 0, /*tp_as_mapping*/
372 0, /*tp_hash*/
373 0, /*tp_call*/
374 0, /*tp_str*/
375 0, /*tp_getattro*/
376 0, /*tp_setattro*/
377 0, /*tp_as_buffer*/
378 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /*tp_flags*/
379 Bus_tp_doc, /*tp_doc*/
380 0, /*tp_traverse*/
381 0, /*tp_clear*/
382 0, /*tp_richcompare*/
383 0, /*tp_weaklistoffset*/
384 0, /*tp_iter*/
385 0, /*tp_iternext*/
386 Bus_tp_methods, /*tp_methods*/
387 0, /*tp_members*/
388 0, /*tp_getset*/
389 DEFERRED_ADDRESS(&ConnectionType), /*tp_base*/
390 0, /*tp_dict*/
391 0, /*tp_descr_get*/
392 0, /*tp_descr_set*/
393 0, /*tp_dictoffset*/
394 0, /*tp_init*/
395 0, /*tp_alloc*/
396 Bus_tp_new, /*tp_new*/
397 0, /*tp_free*/
398 0, /*tp_is_gc*/
401 dbus_bool_t
402 dbus_py_init_bus_types (void)
404 BusType.tp_base = &DBusPyConnectionType;
405 if (PyType_Ready (&BusType) < 0) return 0;
406 return 1;
409 dbus_bool_t
410 dbus_py_insert_bus_types (PyObject *this_module)
412 if (PyModule_AddObject (this_module, "BusImplementation",
413 (PyObject *)&BusType) < 0) return 0;
414 return 1;
417 /* vim:set ft=c cino< sw=4 sts=4 et: */