From edbb9a6396085fb857f4c35e5a5c931aca633b35 Mon Sep 17 00:00:00 2001 From: Johan Hedberg Date: Tue, 3 Jun 2008 16:26:42 +0000 Subject: Rework new agent logic --- hcid/adapter.c | 45 ++++++++++++++++++++++++++++++++++++++------- hcid/adapter.h | 1 + hcid/agent.c | 37 +++---------------------------------- hcid/agent.h | 3 +-- hcid/dbus-hci.c | 11 +++++++++++ 5 files changed, 54 insertions(+), 43 deletions(-) diff --git a/hcid/adapter.c b/hcid/adapter.c index 06082b92..c6756d21 100644 --- a/hcid/adapter.c +++ b/hcid/adapter.c @@ -69,6 +69,12 @@ #define NUM_ELEMENTS(table) (sizeof(table)/sizeof(const char *)) +#define IO_CAPABILITY_DISPLAYONLY 0x00 +#define IO_CAPABILITY_DISPLAYYESNO 0x01 +#define IO_CAPABILITY_KEYBOARDONLY 0x02 +#define IO_CAPABILITY_NOINPUTOUTPUT 0x03 +#define IO_CAPABILITY_INVALID 0xFF + struct mode_req { struct adapter *adapter; DBusConnection *conn; /* Connection reference */ @@ -276,7 +282,7 @@ static struct bonding_request_info *bonding_request_new(DBusConnection *conn, struct adapter *adapter, const char *address, const char *agent_path, - const char *capability) + uint8_t capability) { struct bonding_request_info *bonding; struct device *device; @@ -289,8 +295,7 @@ static struct bonding_request_info *bonding_request_new(DBusConnection *conn, if (agent_path) device->agent = agent_create(adapter, dbus_message_get_sender(msg), - agent_path, - capability, NULL, + agent_path, capability, (agent_remove_cb) device_agent_removed, device); } @@ -299,6 +304,7 @@ static struct bonding_request_info *bonding_request_new(DBusConnection *conn, bonding->conn = dbus_connection_ref(conn); bonding->msg = dbus_message_ref(msg); + bonding->adapter = adapter; str2ba(address, &bonding->bdaddr); @@ -2663,7 +2669,7 @@ static void create_bond_req_exit(void *user_data) static DBusMessage *create_bonding(DBusConnection *conn, DBusMessage *msg, const char *address, const char *agent_path, - const char *capability, void *data) + uint8_t capability, void *data) { char filename[PATH_MAX + 1]; char *str; @@ -2745,7 +2751,7 @@ static DBusHandlerResult adapter_create_bonding(DBusConnection *conn, return error_invalid_arguments(conn, msg, NULL); return send_message_and_unref(conn, - create_bonding(conn, msg, address, NULL, NULL, data)); + create_bonding(conn, msg, address, NULL, 0, data)); } static DBusHandlerResult adapter_cancel_bonding(DBusConnection *conn, @@ -3937,10 +3943,26 @@ static DBusMessage *create_device(DBusConnection *conn, return NULL; } +static uint8_t parse_io_capability(const char *capability) +{ + if (g_str_equal(capability, "")) + return IO_CAPABILITY_DISPLAYYESNO; + if (g_str_equal(capability, "DisplayOnly")) + return IO_CAPABILITY_DISPLAYONLY; + if (g_str_equal(capability, "DisplayYesNo")) + return IO_CAPABILITY_DISPLAYYESNO; + if (g_str_equal(capability, "KeyboardOnly")) + return IO_CAPABILITY_KEYBOARDONLY; + if (g_str_equal(capability, "NoInputOutput")) + return IO_CAPABILITY_NOINPUTOUTPUT; + return IO_CAPABILITY_INVALID; +} + static DBusMessage *create_paired_device(DBusConnection *conn, DBusMessage *msg, void *data) { const gchar *address, *agent_path, *capability; + uint8_t cap; if (dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &address, DBUS_TYPE_OBJECT_PATH, &agent_path, @@ -3951,7 +3973,11 @@ static DBusMessage *create_paired_device(DBusConnection *conn, if (check_address(address) < 0) return invalid_args(msg); - return create_bonding(conn, msg, address, agent_path, capability, + cap = parse_io_capability(capability); + if (cap == IO_CAPABILITY_INVALID) + return invalid_args(msg); + + return create_bonding(conn, msg, address, agent_path, cap, data); } @@ -4029,6 +4055,7 @@ static DBusMessage *register_agent(DBusConnection *conn, const char *path, *name, *capability; struct agent *agent; struct adapter *adapter = data; + uint8_t cap; if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_OBJECT_PATH, &path, DBUS_TYPE_STRING, &capability, DBUS_TYPE_INVALID)) @@ -4039,9 +4066,13 @@ static DBusMessage *register_agent(DBusConnection *conn, ERROR_INTERFACE ".AlreadyExists", "Agent already exists"); + cap = parse_io_capability(capability); + if (cap == IO_CAPABILITY_INVALID) + return invalid_args(msg); + name = dbus_message_get_sender(msg); - agent = agent_create(adapter, name, path, NULL, capability, + agent = agent_create(adapter, name, path, cap, (agent_remove_cb) agent_removed, adapter); if (!agent) return g_dbus_create_error(msg, diff --git a/hcid/adapter.h b/hcid/adapter.h index 17eed7bd..1666e659 100644 --- a/hcid/adapter.h +++ b/hcid/adapter.h @@ -55,6 +55,7 @@ struct remote_dev_info { struct bonding_request_info { DBusConnection *conn; DBusMessage *msg; + struct adapter *adapter; bdaddr_t bdaddr; GIOChannel *io; guint io_id; diff --git a/hcid/agent.c b/hcid/agent.c index 0791c769..2335f09c 100644 --- a/hcid/agent.c +++ b/hcid/agent.c @@ -63,13 +63,11 @@ typedef enum { struct agent { struct adapter *adapter; - char *addr; char *name; char *path; - char *capability; + uint8_t capability; struct agent_request *request; int exited; - guint timeout; agent_remove_cb remove_cb; void *remove_cb_data; guint listener_id; @@ -174,9 +172,6 @@ static void agent_free(struct agent *agent) agent_request_free(agent->request); } - if (agent->timeout) - g_source_remove(agent->timeout); - if (!agent->exited) { g_dbus_remove_watch(connection, agent->listener_id); agent_release(agent); @@ -184,26 +179,12 @@ static void agent_free(struct agent *agent) g_free(agent->name); g_free(agent->path); - g_free(agent->capability); - g_free(agent->addr); g_free(agent); } -static gboolean agent_timeout(struct agent *agent) -{ - debug("Agent at %s, %s timed out", agent->name, agent->path); - - agent->timeout = 0; - - agent_free(agent); - - return FALSE; -} - struct agent *agent_create(struct adapter *adapter, const char *name, - const char *path, const char *address, - const char *capability, + const char *path, uint8_t capability, agent_remove_cb cb, void *remove_cb_data) { struct agent *agent; @@ -216,16 +197,10 @@ struct agent *agent_create(struct adapter *adapter, const char *name, agent->adapter = adapter; agent->name = g_strdup(name); agent->path = g_strdup(path); - agent->capability = g_strdup(capability); + agent->capability = capability; agent->remove_cb = cb; agent->remove_cb_data = remove_cb_data; - if (address) { - agent->addr = g_strdup(address); - agent->timeout = g_timeout_add(AGENT_TIMEOUT, - (GSourceFunc) agent_timeout, agent); - } - agent->listener_id = g_dbus_add_disconnect_watch(connection, name, agent_exited, agent, NULL); @@ -341,9 +316,6 @@ done: agent->request = NULL; agent_request_free(req); - - if (agent->addr) - agent_free(agent); } int agent_authorize(struct agent *agent, @@ -461,9 +433,6 @@ done: dbus_pending_call_cancel(req->call); agent_request_free(req); - - if (agent->addr) - agent_free(agent); } int agent_request_pincode(struct agent *agent, struct device *device, diff --git a/hcid/agent.h b/hcid/agent.h index ad648178..22f79aa4 100644 --- a/hcid/agent.h +++ b/hcid/agent.h @@ -33,8 +33,7 @@ typedef void (*agent_pincode_cb) (struct agent *agent, DBusError *err, typedef void (*agent_remove_cb) (struct agent *agent, void *user_data); struct agent *agent_create(struct adapter *adapter, const char *name, - const char *path, const char *address, - const char *capability, + const char *path, uint8_t capability, agent_remove_cb cb, void *remove_cb_data); int agent_destroy(struct agent *agent, gboolean exited); diff --git a/hcid/dbus-hci.c b/hcid/dbus-hci.c index 679170ff..1b7c9cfa 100644 --- a/hcid/dbus-hci.c +++ b/hcid/dbus-hci.c @@ -63,6 +63,9 @@ static DBusConnection *connection = NULL; void bonding_request_free(struct bonding_request_info *bonding) { + struct device *device; + char address[18]; + if (!bonding) return; @@ -75,6 +78,14 @@ void bonding_request_free(struct bonding_request_info *bonding) if (bonding->io) g_io_channel_unref(bonding->io); + ba2str(&bonding->bdaddr, address); + + device = adapter_get_device(connection, bonding->adapter, address); + if (device && device->agent) { + agent_destroy(device->agent, FALSE); + device->agent = NULL; + } + g_free(bonding); } -- cgit