From 00e08e05f39aad7194b3959a8583071b1551ecbe Mon Sep 17 00:00:00 2001 From: Luiz Augusto von Dentz Date: Tue, 12 Aug 2008 18:53:29 -0300 Subject: Make network plugin to register adapter drivers. --- network/manager.c | 106 +++++++++--- network/server.c | 499 ++++++++++++++++++++---------------------------------- network/server.h | 1 + 3 files changed, 266 insertions(+), 340 deletions(-) (limited to 'network') diff --git a/network/manager.c b/network/manager.c index c0af5d34..371820cc 100644 --- a/network/manager.c +++ b/network/manager.c @@ -57,29 +57,11 @@ static struct network_conf *conf = NULL;/* Network service configuration */ -static DBusConnection *connection = NULL; - -static void register_server(uint16_t id) -{ - char path[MAX_PATH_LENGTH]; - bdaddr_t src; - int dev_id; - - if (!conf->server_enabled) - return; - - snprintf(path, MAX_PATH_LENGTH, NETWORK_PATH "/%s", bnep_name(id)); +static struct btd_adapter_driver network_panu_server_driver; +static struct btd_adapter_driver network_gn_server_driver; +static struct btd_adapter_driver network_nap_server_driver; - bacpy(&src, BDADDR_ANY); - dev_id = hci_get_route(&src); - if (dev_id < 0 || hci_devba(dev_id, &src)) - return; - - if (server_register(path, &src, id) < 0) - return; - - server_store(path); -} +static DBusConnection *connection = NULL; static int network_probe(struct btd_device_driver *driver, struct btd_device *device, GSList *records) @@ -113,6 +95,62 @@ static void network_remove(struct btd_device_driver *driver, connection_unregister(path, id); } +static int network_server_probe(struct adapter *adapter, uint16_t id) +{ + const gchar *path = adapter_get_path(adapter); + const char *source; + bdaddr_t src; + + DBG("path %s", path); + + if (!conf->server_enabled) + return 0; + + source = adapter_get_address(adapter); + str2ba(source, &src); + + return server_register(path, &src, id); +} + +static void network_server_remove(struct adapter *adapter, uint16_t id) +{ + const gchar *path = adapter_get_path(adapter); + + DBG("path %s", path); + + server_unregister(path, id); +} + +static int network_panu_server_probe(struct adapter *adapter) +{ + return network_server_probe(adapter, BNEP_SVC_PANU); +} + +static int network_gn_server_probe(struct adapter *adapter) +{ + return network_server_probe(adapter, BNEP_SVC_GN); +} + +static int network_nap_server_probe(struct adapter *adapter) +{ + return network_server_probe(adapter, BNEP_SVC_NAP); +} + +static void network_panu_server_remove(struct adapter *adapter) +{ + network_server_remove(adapter, BNEP_SVC_PANU); +} + +static void network_gn_server_remove(struct adapter *adapter) +{ + network_server_remove(adapter, BNEP_SVC_GN); +} + +static void network_nap_server_remove(struct adapter *adapter) +{ + network_server_remove(adapter, BNEP_SVC_NAP); +} + static struct btd_device_driver network_panu_driver = { .name = "network-panu", .uuids = BTD_UUIDS(PANU_UUID), @@ -134,6 +172,24 @@ static struct btd_device_driver network_nap_driver = { .remove = network_remove, }; +static struct btd_adapter_driver network_panu_server_driver = { + .name = "network-panu-server", + .probe = network_panu_server_probe, + .remove = network_panu_server_remove, +}; + +static struct btd_adapter_driver network_gn_server_driver = { + .name = "network-gn-server", + .probe = network_gn_server_probe, + .remove = network_gn_server_remove, +}; + +static struct btd_adapter_driver network_nap_server_driver = { + .name = "network-nap-server", + .probe = network_nap_server_probe, + .remove = network_nap_server_remove, +}; + int network_manager_init(DBusConnection *conn, struct network_conf *service_conf) { conf = service_conf; @@ -159,9 +215,9 @@ int network_manager_init(DBusConnection *conn, struct network_conf *service_conf /* Register PANU, GN and NAP servers if they don't exist */ /* FIXME: server should be registered as adapter driver */ - register_server(BNEP_SVC_PANU); - register_server(BNEP_SVC_GN); - register_server(BNEP_SVC_NAP); + btd_register_adapter_driver(&network_panu_server_driver); + btd_register_adapter_driver(&network_gn_server_driver); + btd_register_adapter_driver(&network_nap_server_driver); if (connection_init(conn, conf->iface_prefix) < 0) return -1; diff --git a/network/server.c b/network/server.c index 1f57a174..f4fabed9 100644 --- a/network/server.c +++ b/network/server.c @@ -55,7 +55,9 @@ #include "sdpd.h" #include "glib-helper.h" -#define NETWORK_SERVER_INTERFACE "org.bluez.network.Server" +#define NETWORK_PEER_INTERFACE "org.bluez.network.Peer" +#define NETWORK_HUB_INTERFACE "org.bluez.network.Hub" +#define NETWORK_ROUTER_INTERFACE "org.bluez.network.Router" #define SETUP_TIMEOUT 1000 #define MAX_SETUP_ATTEMPTS 3 @@ -77,32 +79,58 @@ struct timeout { guint watch; /* BNEP socket watch */ }; +struct network_adapter { + bdaddr_t src; /* Bluetooth Local Address */ + char *path; /* D-Bus path */ + GIOChannel *io; /* Bnep socket */ + struct timeout *to; /* Socket timeout */ + GSList *servers; /* Server register to adapter */ +}; + /* Main server structure */ struct network_server { - bdaddr_t src; /* Bluetooth Local Address */ - char *iface; /* Routing interface */ + char *iface; /* DBus interface */ char *name; /* Server service name */ char *range; /* IP Address range */ - char *path; /* D-Bus path */ gboolean enable; /* Enable flag */ uint32_t record_id; /* Service record id */ uint16_t id; /* Service class identifier */ GSList *clients; /* Active connections */ + struct network_adapter *na; /* Adapter reference */ }; -static GIOChannel *bnep_io = NULL; static DBusConnection *connection = NULL; static struct setup_session *setup = NULL; -static GSList *servers = NULL; +static GSList *adapters = NULL; static const char *prefix = NULL; static gboolean security = TRUE; -gint find_server(gconstpointer a, gconstpointer b) +static struct network_adapter *find_adapter(GSList *list, const char *path) { - const struct network_server *ns = a; - const char *path = b; + GSList *l; - return strcmp(ns->path, path); + for (l = list; l; l = l->next) { + struct network_adapter *na = l->data; + + if (g_str_equal(na->path, path)) + return na; + } + + return NULL; +} + +static struct network_server *find_server(GSList *list, uint16_t id) +{ + GSList *l; + + for (l = list; l; l = l->next) { + struct network_server *ns = l->data; + + if (ns->id == id) + return ns; + } + + return NULL; } static struct setup_session *setup_session_new(gchar *address, @@ -127,39 +155,6 @@ static void setup_session_free(struct setup_session *setup) g_free(setup); } -static struct network_server *server_find(bdaddr_t *src, uint16_t role) -{ - struct network_server *ns; - GSList *l; - - for (l = servers; l; l = l->next) { - ns = l->data; - if (bacmp(&ns->src, src) != 0) - continue; - if (ns->id == role) - return ns; - } - - return NULL; -} - -static int store_property(bdaddr_t *src, uint16_t id, - const char *key, const char *value) -{ - char filename[PATH_MAX + 1]; - char addr[18]; - - ba2str(src, addr); - if (id == BNEP_SVC_NAP) - create_name(filename, PATH_MAX, STORAGEDIR, addr, "nap"); - else if (id == BNEP_SVC_GN) - create_name(filename, PATH_MAX, STORAGEDIR, addr, "gn"); - else if (id == BNEP_SVC_PANU) - create_name(filename, PATH_MAX, STORAGEDIR, addr, "panu"); - - return textfile_put(filename, key, value); -} - static void add_lang_attr(sdp_record_t *r) { sdp_lang_attr_t base_lang; @@ -351,6 +346,7 @@ static int server_connadd(struct network_server *ns, int nsk, static void req_auth_cb(DBusError *derr, void *user_data) { struct network_server *ns = user_data; + struct network_adapter *na = ns->na; uint16_t val; if (!setup) { @@ -363,7 +359,7 @@ static void req_auth_cb(DBusError *derr, void *user_data) if (dbus_error_has_name(derr, DBUS_ERROR_NO_REPLY)) { bdaddr_t dst; str2ba(setup->address, &dst); - service_cancel_auth(&ns->src, &dst); + service_cancel_auth(&na->src, &dst); } val = BNEP_CONN_NOT_ALLOWED; goto done; @@ -383,14 +379,15 @@ done: static int authorize_connection(struct network_server *ns, const char *address) { + struct network_adapter *na; const char *uuid; bdaddr_t dst; int ret_val; - uuid = bnep_uuid(ns->id); + uuid = bnep_uuid(ns->id); str2ba(address, &dst); - ret_val = service_req_auth(&ns->src, &dst, uuid, req_auth_cb, ns); + ret_val = service_req_auth(&na->src, &dst, uuid, req_auth_cb, ns); return ret_val; } @@ -444,7 +441,8 @@ static uint16_t bnep_setup_decode(struct bnep_setup_conn_req *req, static gboolean bnep_setup(GIOChannel *chan, GIOCondition cond, gpointer user_data) { - struct timeout *to = user_data; + struct network_adapter *na = user_data; + struct timeout *to = na->to; struct network_server *ns; uint8_t packet[BNEP_MTU]; struct bnep_setup_conn_req *req = (void *) packet; @@ -489,7 +487,7 @@ static gboolean bnep_setup(GIOChannel *chan, } ba2str(&sa.l2_bdaddr, address); - ns = server_find(&sa.l2_bdaddr, dst_role); + ns = find_server(na->servers, dst_role); if (!ns || ns->enable == FALSE) { error("Server unavailable: %s (0x%x)", address, dst_role); rsp = BNEP_CONN_NOT_ALLOWED; @@ -553,7 +551,8 @@ static gboolean timeout_cb(void *user_data) static void connect_event(GIOChannel *chan, int err, const bdaddr_t *src, const bdaddr_t *dst, gpointer user_data) { - struct timeout *to; + struct network_adapter *na; + struct timeout *to = na->to; if (err < 0) { error("accept(): %s(%d)", strerror(errno), errno); @@ -571,7 +570,7 @@ static void connect_event(GIOChannel *chan, int err, const bdaddr_t *src, to->id = g_timeout_add(SETUP_TIMEOUT, timeout_cb, to); to->watch = g_io_add_watch_full(chan, G_PRIORITY_DEFAULT, G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL, - bnep_setup, to, setup_destroy); + bnep_setup, na, setup_destroy); g_io_channel_unref(chan); return; @@ -580,20 +579,10 @@ static void connect_event(GIOChannel *chan, int err, const bdaddr_t *src, int server_init(DBusConnection *conn, const char *iface_prefix, gboolean secure) { - int lm; - - lm = secure ? L2CAP_LM_SECURE : 0; - security = secure; connection = dbus_connection_ref(conn); prefix = iface_prefix; - bnep_io = bt_l2cap_listen(BDADDR_ANY, BNEP_PSM, BNEP_MTU, lm, - connect_event, NULL); - if (!bnep_io) - return -1; - g_io_channel_set_close_on_unref(bnep_io, FALSE); - if (bridge_create(BNEP_SVC_GN) < 0) error("Can't create GN bridge"); @@ -602,12 +591,6 @@ int server_init(DBusConnection *conn, const char *iface_prefix, void server_exit() { - if (bnep_io != NULL) { - g_io_channel_close(bnep_io); - g_io_channel_unref(bnep_io); - bnep_io = NULL; - } - if (bridge_remove(BNEP_SVC_GN) < 0) error("Can't remove GN bridge"); @@ -617,6 +600,7 @@ void server_exit() static uint32_t register_server_record(struct network_server *ns) { + struct network_adapter *na = ns->na; sdp_record_t *record; record = server_record_new(ns->name, ns->id); @@ -625,7 +609,7 @@ static uint32_t register_server_record(struct network_server *ns) return 0; } - if (add_record_to_server(&ns->src, record) < 0) { + if (add_record_to_server(&na->src, record) < 0) { error("Failed to register service record"); sdp_record_free(record); return 0; @@ -636,24 +620,6 @@ static uint32_t register_server_record(struct network_server *ns) return record->handle; } -static DBusMessage *get_uuid(DBusConnection *conn, - DBusMessage *msg, void *data) -{ - struct network_server *ns = data; - DBusMessage *reply; - const char *uuid; - - reply = dbus_message_new_method_return(msg); - if (!reply) - return NULL; - - uuid = bnep_uuid(ns->id); - dbus_message_append_args(reply, - DBUS_TYPE_STRING, &uuid, - DBUS_TYPE_INVALID); - - return reply; -} static inline DBusMessage *failed(DBusMessage *msg, const char *description) { @@ -679,17 +645,6 @@ static DBusMessage *enable(DBusConnection *conn, ".AlreadyExist", "Server already enabled"); - if (bacmp(&ns->src, BDADDR_ANY) == 0) { - int dev_id; - - dev_id = hci_get_route(&ns->src); - if ((dev_id < 0) || (hci_devba(dev_id, &ns->src) < 0)) - return failed(msg, "Adapter not available"); - - /* Store the server info */ - server_store(ns->path); - } - reply = dbus_message_new_method_return(msg); if (!reply) return NULL; @@ -703,11 +658,6 @@ static DBusMessage *enable(DBusConnection *conn, ns->enable = TRUE; - store_property(&ns->src, ns->id, "enabled", "1"); - - g_dbus_emit_signal(conn, ns->path, NETWORK_SERVER_INTERFACE, - "Enabled", DBUS_TYPE_INVALID); - return reply; } @@ -743,16 +693,11 @@ static DBusMessage *disable(DBusConnection *conn, g_slist_foreach(ns->clients, (GFunc) kill_connection, NULL); - store_property(&ns->src, ns->id, "enabled", "0"); - - g_dbus_emit_signal(conn, ns->path, NETWORK_SERVER_INTERFACE, - "Disabled", DBUS_TYPE_INVALID); - return reply; } -static DBusMessage *is_enabled(DBusConnection *conn, DBusMessage *msg, - void *data) +static DBusMessage *set_name(DBusConnection *conn, DBusMessage *msg, + const char *name, void *data) { struct network_server *ns = data; DBusMessage *reply; @@ -761,28 +706,6 @@ static DBusMessage *is_enabled(DBusConnection *conn, DBusMessage *msg, if (!reply) return NULL; - dbus_message_append_args(reply, DBUS_TYPE_BOOLEAN, &ns->enable, - DBUS_TYPE_INVALID); - - return reply; -} - -static DBusMessage *set_name(DBusConnection *conn, - DBusMessage *msg, void *data) -{ - struct network_server *ns = data; - DBusMessage *reply; - const char *name; - - reply = dbus_message_new_method_return(msg); - if (!reply) - return NULL; - - if (!dbus_message_get_args(msg, NULL, - DBUS_TYPE_STRING, &name, - DBUS_TYPE_INVALID)) - return NULL; - if (!name || (strlen(name) == 0)) return invalid_arguments(msg, "Invalid name"); @@ -802,59 +725,10 @@ static DBusMessage *set_name(DBusConnection *conn, ns->record_id = handle; } - store_property(&ns->src, ns->id, "name", ns->name); - return reply; } -static DBusMessage *get_name(DBusConnection *conn, - DBusMessage *msg, void *data) -{ - struct network_server *ns = data; - char name[] = ""; - const char *pname = (ns->name ? ns->name : name); - DBusMessage *reply; - - reply = dbus_message_new_method_return(msg); - if (!reply) - return NULL; - - dbus_message_append_args(reply, - DBUS_TYPE_STRING, &pname, - DBUS_TYPE_INVALID); - - return reply; -} - -static DBusMessage *set_address_range(DBusConnection *conn, - DBusMessage *msg, void *data) -{ - return NULL; -} - -static DBusMessage *set_routing(DBusConnection *conn, DBusMessage *msg, - void *data) -{ - struct network_server *ns = data; - const char *iface; - - if (!dbus_message_get_args(msg, NULL, - DBUS_TYPE_STRING, &iface, - DBUS_TYPE_INVALID)) - return NULL; - - /* FIXME: Check if the interface is valid/UP */ - if (!iface || (strlen(iface) == 0)) - return invalid_arguments(msg, "Invalid interface"); - - if (ns->iface) - g_free(ns->iface); - ns->iface = g_strdup(iface); - - return dbus_message_new_method_return(msg); -} - -static DBusMessage *get_info(DBusConnection *conn, +static DBusMessage *get_properties(DBusConnection *conn, DBusMessage *msg, void *data) { struct network_server *ns = data; @@ -874,18 +748,74 @@ static DBusMessage *get_info(DBusConnection *conn, DBUS_TYPE_STRING_AS_STRING DBUS_TYPE_VARIANT_AS_STRING DBUS_DICT_ENTRY_END_CHAR_AS_STRING, &dict); - dbus_message_iter_append_dict_entry(&dict, "name", + dbus_message_iter_append_dict_entry(&dict, "Name", DBUS_TYPE_STRING, &ns->name); uuid = bnep_uuid(ns->id); - dbus_message_iter_append_dict_entry(&dict, "uuid", + dbus_message_iter_append_dict_entry(&dict, "Uuid", DBUS_TYPE_STRING, &uuid); + dbus_message_iter_append_dict_entry(&dict, "Enabled", + DBUS_TYPE_BOOLEAN, &ns->enable); + dbus_message_iter_close_container(&iter, &dict); return reply; } +static DBusMessage *set_property(DBusConnection *conn, + DBusMessage *msg, void *data) +{ + DBusMessageIter iter; + DBusMessageIter sub; + const char *property; + + if (!dbus_message_iter_init(msg, &iter)) + return invalid_arguments(msg, "Not a dict"); + + if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING) + return invalid_arguments(msg, "Key not a string"); + + dbus_message_iter_get_basic(&iter, &property); + dbus_message_iter_next(&iter); + + if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT) + return invalid_arguments(msg, "Value not a variant"); + dbus_message_iter_recurse(&iter, &sub); + + if (g_str_equal("Name", property)) { + const char *name; + + if (dbus_message_iter_get_arg_type(&sub) != DBUS_TYPE_STRING) + return invalid_arguments(msg, "Value not string"); + dbus_message_iter_get_basic(&sub, &name); + + return set_name(conn, msg, name, data); + } else if (g_str_equal("Enabled", property)) { + gboolean enabled; + + if (dbus_message_iter_get_arg_type(&sub) != DBUS_TYPE_BOOLEAN) + return invalid_arguments(msg, "Value not boolean"); + dbus_message_iter_get_basic(&sub, &enabled); + + return enabled ? enable(conn, msg, data) : + disable(conn, msg, data); + } + + return invalid_arguments(msg, "Property does not exist"); +} + +static void adapter_free(struct network_adapter *na) +{ + if (na->io != NULL) { + g_io_channel_close(na->io); + g_io_channel_unref(na->io); + } + + g_free(na->path); + g_free(na); +} + static void server_free(struct network_server *ns) { if (!ns) @@ -904,9 +834,6 @@ static void server_free(struct network_server *ns) if (ns->range) g_free(ns->range); - if (ns->path) - g_free(ns->path); - if (ns->clients) { g_slist_foreach(ns->clients, (GFunc) g_free, NULL); g_slist_free(ns->clients); @@ -915,183 +842,125 @@ static void server_free(struct network_server *ns) g_free(ns); } -static void server_unregister(void *data) +static void path_unregister(void *data) { struct network_server *ns = data; + struct network_adapter *na = ns->na; - info("Unregistered server path:%s", ns->path); - - servers = g_slist_remove(servers, ns); + na->servers = g_slist_remove(na->servers, ns); server_free(ns); + + info("Unregistered interface %s on path %s", + ns->iface, na->path); + + if (na->servers) + return; + + adapter_free(na); } static GDBusMethodTable server_methods[] = { - { "GetUUID", "", "s", get_uuid }, - { "Enable", "", "", enable }, - { "Disable", "", "", disable }, - { "IsEnabled", "", "b", is_enabled }, - { "SetName", "s", "", set_name }, - { "GetName", "", "s", get_name }, - { "SetAddressRange", "ss", "", set_address_range }, - { "SetRouting", "s", "", set_routing }, - { "GetInfo", "", "a{sv}",get_info }, + { "SetProperty", "sv", "", set_property }, + { "GetProperties", "", "a{sv}",get_properties }, { } }; static GDBusSignalTable server_signals[] = { - { "Enabled", "" }, - { "Disabled", "" }, + { "PropertyChanged", "sv" }, { } }; -int server_register(const char *path, bdaddr_t *src, uint16_t id) +static struct network_adapter *create_adapter(const char *path, bdaddr_t *src) { - struct network_server *ns; + struct network_adapter *na; + int lm; - if (!path) - return -EINVAL; + lm = security ? L2CAP_LM_SECURE : 0; - ns = g_new0(struct network_server, 1); + na = g_new0(struct network_adapter, 1); + na->path = g_strdup(path); + bacpy(&na->src, src); - if (!g_dbus_register_interface(connection, path, - NETWORK_SERVER_INTERFACE, - server_methods, server_signals, NULL, - ns, server_unregister)) { - error("D-Bus failed to register %s interface", - NETWORK_SERVER_INTERFACE); - server_free(ns); - return -1; + na->io = bt_l2cap_listen(src, BNEP_PSM, BNEP_MTU, lm, + connect_event, na); + if (!na->io) { + adapter_free(na); + return NULL; } - /* Setting a default name */ - if (id == BNEP_SVC_NAP) - ns->name = g_strdup("BlueZ NAP service"); - else if (id == BNEP_SVC_GN) - ns->name = g_strdup("BlueZ GN service"); - else - ns->name = g_strdup("BlueZ PANU service"); + g_io_channel_set_close_on_unref(na->io, FALSE); - ns->path = g_strdup(path); - ns->id = id; - bacpy(&ns->src, src); - - servers = g_slist_append(servers, ns); - - info("Registered server path:%s", path); - - return 0; + return na; } -int server_register_from_file(const char *path, const bdaddr_t *src, - uint16_t id, const char *filename) +int server_register(const char *path, bdaddr_t *src, uint16_t id) { + struct network_adapter *na; struct network_server *ns; - char *str; - if (!path) - return -EINVAL; - - ns = g_new0(struct network_server, 1); - - bacpy(&ns->src, src); - ns->path = g_strdup(path); - ns->id = id; - ns->name = textfile_get(filename, "name"); - if (!ns->name) { - /* Name is mandatory */ - server_free(ns); - return -1; + na = find_adapter(adapters, path); + if (!na) { + na = create_adapter(path, src); + if (!na) + return -EINVAL; + adapters = g_slist_append(adapters, na); } - ns->range = textfile_get(filename, "address_range"); - ns->iface = textfile_get(filename, "routing"); + ns = find_server(na->servers, id); + if (ns) + return 0; - str = textfile_get(filename, "enabled"); - if (str) { - if (strcmp("1", str) == 0) { - ns->record_id = register_server_record(ns); - ns->enable = TRUE; - } - g_free(str); + ns = g_new0(struct network_server, 1); + + switch (id) { + case BNEP_SVC_PANU: + ns->iface = g_strdup(NETWORK_PEER_INTERFACE); + ns->name = g_strdup("BlueZ PANU service"); + break; + case BNEP_SVC_GN: + ns->iface = g_strdup(NETWORK_HUB_INTERFACE); + ns->name = g_strdup("BlueZ GN service"); + break; + case BNEP_SVC_NAP: + ns->iface = g_strdup(NETWORK_ROUTER_INTERFACE); + ns->name = g_strdup("BlueZ NAP service"); + break; } - if (!g_dbus_register_interface(connection, path, - NETWORK_SERVER_INTERFACE, + if (!g_dbus_register_interface(connection, path, ns->iface, server_methods, server_signals, NULL, - ns, server_unregister)) { + ns, path_unregister)) { error("D-Bus failed to register %s interface", - NETWORK_SERVER_INTERFACE); + ns->iface); server_free(ns); return -1; } - servers = g_slist_append(servers, ns); + ns->id = id; + ns->na = na; + ns->record_id = register_server_record(ns); + ns->enable = TRUE; + na->servers = g_slist_append(na->servers, ns); - info("Registered server path:%s", path); + info("Registered interface %s on path %s", ns->iface, path); return 0; } -int server_store(const char *path) +int server_unregister(const char *path, uint16_t id) { + struct network_adapter *na; struct network_server *ns; - char filename[PATH_MAX + 1]; - char addr[18]; - GSList *l; - - l = g_slist_find_custom(servers, path, find_server); - if (!l) { - error("Unable to salve %s on storage", path); - return -ENOENT; - } - ns = l->data; - ba2str(&ns->src, addr); - if (ns->id == BNEP_SVC_NAP) - create_name(filename, PATH_MAX, STORAGEDIR, addr, "nap"); - else if (ns->id == BNEP_SVC_GN) - create_name(filename, PATH_MAX, STORAGEDIR, addr, "gn"); - else - create_name(filename, PATH_MAX, STORAGEDIR, addr, "panu"); - - create_file(filename, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); - - textfile_put(filename, "name", ns->name); - - if (ns->iface) - textfile_put(filename, "routing", ns->iface); + na = find_adapter(adapters, path); + if (!na) + return -EINVAL; - if (ns->range) - textfile_put(filename, "range", ns->range); + ns = find_server(na->servers, id); + if (!ns) + return -EINVAL; - textfile_put(filename, "enabled", ns->enable ? "1": "0"); + g_dbus_unregister_interface(connection, path, ns->iface); return 0; } - -int server_find_data(const char *path, const char *pattern) -{ - struct network_server *ns; - const char *uuid; - GSList *l; - - l = g_slist_find_custom(servers, path, find_server); - if (!l) - return -1; - - ns = l->data; - if (ns->name && strcasecmp(pattern, ns->name) == 0) - return 0; - - if (ns->iface && strcasecmp(pattern, ns->iface) == 0) - return 0; - - uuid = bnep_name(ns->id); - if (uuid && strcasecmp(pattern, uuid) == 0) - return 0; - - if (bnep_service_id(pattern) == ns->id) - return 0; - - return -1; -} diff --git a/network/server.h b/network/server.h index 6fb06b58..74ec86df 100644 --- a/network/server.h +++ b/network/server.h @@ -25,6 +25,7 @@ int server_init(DBusConnection *conn, const char *iface_prefix, gboolean secure); void server_exit(); int server_register(const char *path, bdaddr_t *src, uint16_t id); +int server_unregister(const char *path, uint16_t id); int server_register_from_file(const char *path, const bdaddr_t *src, uint16_t id, const char *filename); -- cgit