diff options
Diffstat (limited to 'src/dbus-common.c')
-rw-r--r-- | src/dbus-common.c | 254 |
1 files changed, 254 insertions, 0 deletions
diff --git a/src/dbus-common.c b/src/dbus-common.c new file mode 100644 index 0000000..8436100 --- /dev/null +++ b/src/dbus-common.c @@ -0,0 +1,254 @@ +/* + * + * BlueZ - Bluetooth protocol stack for Linux + * + * Copyright (C) 2006-2010 Nokia Corporation + * Copyright (C) 2004-2010 Marcel Holtmann <marcel@holtmann.org> + * Copyright (C) 2005-2007 Johan Hedberg <johan.hedberg@nokia.com> + * + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +#include <stdio.h> +#include <errno.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/ioctl.h> + +#include <bluetooth/bluetooth.h> + +#include <glib.h> +#include <dbus/dbus.h> +#include <gdbus.h> + +#include "log.h" + +#include "adapter.h" +#include "manager.h" +#include "event.h" +#include "dbus-common.h" + +static DBusConnection *connection = NULL; + +static void append_variant(DBusMessageIter *iter, int type, void *val) +{ + DBusMessageIter value; + char sig[2] = { type, '\0' }; + + dbus_message_iter_open_container(iter, DBUS_TYPE_VARIANT, sig, &value); + + dbus_message_iter_append_basic(&value, type, val); + + dbus_message_iter_close_container(iter, &value); +} + +static void append_array_variant(DBusMessageIter *iter, int type, void *val, + int n_elements) +{ + DBusMessageIter variant, array; + char type_sig[2] = { type, '\0' }; + char array_sig[3] = { DBUS_TYPE_ARRAY, type, '\0' }; + + dbus_message_iter_open_container(iter, DBUS_TYPE_VARIANT, + array_sig, &variant); + + dbus_message_iter_open_container(&variant, DBUS_TYPE_ARRAY, + type_sig, &array); + + if (dbus_type_is_fixed(type) == TRUE) { + dbus_message_iter_append_fixed_array(&array, type, val, + n_elements); + } else if (type == DBUS_TYPE_STRING || type == DBUS_TYPE_OBJECT_PATH) { + const char ***str_array = val; + int i; + + for (i = 0; i < n_elements; i++) + dbus_message_iter_append_basic(&array, type, + &((*str_array)[i])); + } + + dbus_message_iter_close_container(&variant, &array); + + dbus_message_iter_close_container(iter, &variant); +} + +void dict_append_entry(DBusMessageIter *dict, + const char *key, int type, void *val) +{ + DBusMessageIter entry; + + if (type == DBUS_TYPE_STRING) { + const char *str = *((const char **) val); + if (str == NULL) + return; + } + + dbus_message_iter_open_container(dict, DBUS_TYPE_DICT_ENTRY, + NULL, &entry); + + dbus_message_iter_append_basic(&entry, DBUS_TYPE_STRING, &key); + + append_variant(&entry, type, val); + + dbus_message_iter_close_container(dict, &entry); +} + +void dict_append_array(DBusMessageIter *dict, const char *key, int type, + void *val, int n_elements) +{ + DBusMessageIter entry; + + dbus_message_iter_open_container(dict, DBUS_TYPE_DICT_ENTRY, + NULL, &entry); + + dbus_message_iter_append_basic(&entry, DBUS_TYPE_STRING, &key); + + append_array_variant(&entry, type, val, n_elements); + + dbus_message_iter_close_container(dict, &entry); +} + +dbus_bool_t emit_property_changed(DBusConnection *conn, + const char *path, + const char *interface, + const char *name, + int type, void *value) +{ + DBusMessage *signal; + DBusMessageIter iter; + + signal = dbus_message_new_signal(path, interface, "PropertyChanged"); + + if (!signal) { + error("Unable to allocate new %s.PropertyChanged signal", + interface); + return FALSE; + } + + dbus_message_iter_init_append(signal, &iter); + + dbus_message_iter_append_basic(&iter, DBUS_TYPE_STRING, &name); + + append_variant(&iter, type, value); + + return g_dbus_send_message(conn, signal); +} + +dbus_bool_t emit_array_property_changed(DBusConnection *conn, + const char *path, + const char *interface, + const char *name, + int type, void *value, int num) +{ + DBusMessage *signal; + DBusMessageIter iter; + + signal = dbus_message_new_signal(path, interface, "PropertyChanged"); + + if (!signal) { + error("Unable to allocate new %s.PropertyChanged signal", + interface); + return FALSE; + } + + dbus_message_iter_init_append(signal, &iter); + + dbus_message_iter_append_basic(&iter, DBUS_TYPE_STRING, &name); + + append_array_variant(&iter, type, value, num); + + return g_dbus_send_message(conn, signal); +} + +void set_dbus_connection(DBusConnection *conn) +{ + connection = conn; +} + +DBusConnection *get_dbus_connection(void) +{ + return connection; +} + +const char *class_to_icon(uint32_t class) +{ + switch ((class & 0x1f00) >> 8) { + case 0x01: + return "computer"; + case 0x02: + switch ((class & 0xfc) >> 2) { + case 0x01: + case 0x02: + case 0x03: + case 0x05: + return "phone"; + case 0x04: + return "modem"; + } + break; + case 0x03: + return "network-wireless"; + case 0x04: + switch ((class & 0xfc) >> 2) { + case 0x01: + case 0x02: + return "audio-card"; /* Headset */ + case 0x06: + return "audio-card"; /* Headphone */ + case 0x0b: /* VCR */ + case 0x0c: /* Video Camera */ + case 0x0d: /* Camcorder */ + return "camera-video"; + default: + return "audio-card"; /* Other audio device */ + } + break; + case 0x05: + switch ((class & 0xc0) >> 6) { + case 0x00: + switch ((class & 0x1e) >> 2) { + case 0x01: + case 0x02: + return "input-gaming"; + } + break; + case 0x01: + return "input-keyboard"; + case 0x02: + switch ((class & 0x1e) >> 2) { + case 0x05: + return "input-tablet"; + default: + return "input-mouse"; + } + } + break; + case 0x06: + if (class & 0x80) + return "printer"; + if (class & 0x20) + return "camera-photo"; + break; + } + + return NULL; +} |