From 76041ebc6b7b6a9cb95040ec6a824c2fea75b2f1 Mon Sep 17 00:00:00 2001 From: Johan Hedberg Date: Tue, 25 Sep 2012 13:25:28 +0300 Subject: [PATCH] core: Add external profile registration callbacks --- src/manager.c | 9 ++++ src/profile.c | 125 ++++++++++++++++++++++++++++++++++++++++++++++++++ src/profile.h | 5 ++ 3 files changed, 139 insertions(+) diff --git a/src/manager.c b/src/manager.c index 15a2571cc..90e6e6bd7 100644 --- a/src/manager.c +++ b/src/manager.c @@ -28,6 +28,7 @@ #include #include +#include #include #include #include @@ -48,6 +49,8 @@ #include "dbus-common.h" #include "log.h" #include "adapter.h" +#include "device.h" +#include "profile.h" #include "error.h" #include "manager.h" @@ -176,6 +179,12 @@ static const GDBusMethodTable manager_methods[] = { GDBUS_ARGS({ "pattern", "s" }), GDBUS_ARGS({ "adapter", "o" }), find_adapter) }, + { GDBUS_METHOD("RegisterProfile", + GDBUS_ARGS({ "profile", "o"}, { "UUID", "s" }, + { "options", "a{sv}" }), + NULL, btd_profile_reg_ext) }, + { GDBUS_METHOD("UnregisterProfile", GDBUS_ARGS({ "profile", "o" }), + NULL, btd_profile_unreg_ext) }, { } }; diff --git a/src/profile.c b/src/profile.c index 5b40b1628..aa76a912b 100644 --- a/src/profile.c +++ b/src/profile.c @@ -31,11 +31,22 @@ #include #include +#include "uuid.h" +#include "error.h" #include "adapter.h" #include "device.h" #include "profile.h" +struct ext_profile { + struct btd_profile p; + char *name; + char *owner; + char *uuid; + char *path; +}; + static GSList *profiles = NULL; +static GSList *ext_profiles = NULL; void btd_profile_foreach(void (*func)(struct btd_profile *p, void *data), void *data) @@ -49,6 +60,14 @@ void btd_profile_foreach(void (*func)(struct btd_profile *p, void *data), func(profile, data); } + + for (l = ext_profiles; l != NULL; l = next) { + struct ext_profile *profile = l->data; + + next = g_slist_next(l); + + func(&profile->p, data); + } } int btd_profile_register(struct btd_profile *profile) @@ -61,3 +80,109 @@ void btd_profile_unregister(struct btd_profile *profile) { profiles = g_slist_remove(profiles, profile); } + +static struct ext_profile *find_ext_profile(const char *owner, + const char *path) +{ + GSList *l; + + for (l = ext_profiles; l != NULL; l = g_slist_next(l)) { + struct ext_profile *ext = l->data; + + if (!g_str_equal(ext->owner, owner)) + continue; + + if (g_str_equal(ext->path, path)) + return ext; + } + + return NULL; +} + +static struct ext_profile *create_ext(const char *owner, const char *path, + const char *uuid, + DBusMessageIter *opts) +{ + struct btd_profile *p; + struct ext_profile *ext; + + ext = g_new0(struct ext_profile, 1); + + ext->name = g_strdup_printf("%s-%s/%s", owner, path, uuid); + ext->owner = g_strdup(owner); + ext->path = g_strdup(path); + ext->uuid = g_strdup(uuid); + + p = &ext->p; + + p->name = ext->name; + + ext_profiles = g_slist_append(ext_profiles, ext); + + return ext; +} + +static void remove_ext(struct ext_profile *ext) +{ + ext_profiles = g_slist_remove(ext_profiles, ext); + + g_free(ext->name); + g_free(ext->owner); + g_free(ext->uuid); + g_free(ext->path); + + g_free(ext); +} + +DBusMessage *btd_profile_reg_ext(DBusConnection *conn, DBusMessage *msg, + void *user_data) +{ + const char *path, *sender, *uuid; + DBusMessageIter args, opts; + struct ext_profile *ext; + + sender = dbus_message_get_sender(msg); + + dbus_message_iter_init(msg, &args); + + dbus_message_iter_get_basic(&args, &path); + dbus_message_iter_next(&args); + + ext = find_ext_profile(sender, path); + if (ext) + return btd_error_already_exists(msg); + + dbus_message_iter_get_basic(&args, &uuid); + dbus_message_iter_next(&args); + + dbus_message_iter_recurse(&args, &opts); + if (dbus_message_iter_get_arg_type(&opts) != DBUS_TYPE_DICT_ENTRY) + return btd_error_invalid_args(msg); + + ext = create_ext(sender, path, uuid, &opts); + if (!ext) + return btd_error_invalid_args(msg); + + return dbus_message_new_method_return(msg); +} + +DBusMessage *btd_profile_unreg_ext(DBusConnection *conn, DBusMessage *msg, + void *user_data) +{ + const char *path, *sender; + struct ext_profile *ext; + + sender = dbus_message_get_sender(msg); + + if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_OBJECT_PATH, &path, + DBUS_TYPE_INVALID)) + return btd_error_invalid_args(msg); + + ext = find_ext_profile(sender, path); + if (!ext) + return btd_error_does_not_exist(msg); + + remove_ext(ext); + + return dbus_message_new_method_return(msg); +} diff --git a/src/profile.h b/src/profile.h index 0e73ef4eb..178e7bfc1 100644 --- a/src/profile.h +++ b/src/profile.h @@ -52,3 +52,8 @@ void btd_profile_foreach(void (*func)(struct btd_profile *p, void *data), int btd_profile_register(struct btd_profile *profile); void btd_profile_unregister(struct btd_profile *profile); + +DBusMessage *btd_profile_reg_ext(DBusConnection *conn, DBusMessage *msg, + void *user_data); +DBusMessage *btd_profile_unreg_ext(DBusConnection *conn, DBusMessage *msg, + void *user_data); -- 2.47.3