summaryrefslogtreecommitdiff
path: root/plugins
diff options
context:
space:
mode:
authorSzymon Janc <szymon.janc@tieto.com>2012-06-13 16:03:52 +0200
committerJohan Hedberg <johan.hedberg@intel.com>2012-06-13 17:54:40 +0300
commit4da87e3e2b9facfb92448b690c8593dd4b5a0277 (patch)
treef0a31185ec65b0532aedd0606cc34866f39e7222 /plugins
parent07b6738fb4dd29cb454f36a75ffe2af26eb529a2 (diff)
mgmtops: Handle EBUSY status from MGMT_OP_ADD_UUID commands
MGMT_OP_ADD_UUID may fail with EBUSY due to ongoing CoD update. In case of EBUSY error wait for Class Of Device changed event before adding more UUIDs.
Diffstat (limited to 'plugins')
-rw-r--r--plugins/mgmtops.c59
1 files changed, 50 insertions, 9 deletions
diff --git a/plugins/mgmtops.c b/plugins/mgmtops.c
index a196b1fe..4ce3ee4e 100644
--- a/plugins/mgmtops.c
+++ b/plugins/mgmtops.c
@@ -78,6 +78,7 @@ static struct controller_info {
uint8_t minor;
gboolean pending_powered;
+ gboolean pending_cod_change;
} *controllers = NULL;
static int mgmt_sock = -1;
@@ -1272,18 +1273,12 @@ static void read_local_oob_data_failed(int sk, uint16_t index)
oob_read_local_data_complete(adapter, NULL, NULL);
}
-static void mgmt_add_uuid_complete(int sk, uint16_t index, void *buf,
- size_t len)
+static void handle_pending_uuids(uint16_t index)
{
struct controller_info *info;
struct pending_uuid *pending;
- DBG("add_uuid complete");
-
- if (index > max_index) {
- error("Unexpected index %u in add_uuid_complete event", index);
- return;
- }
+ DBG("index %d", index);
info = &controllers[index];
@@ -1311,6 +1306,19 @@ static void mgmt_add_uuid_complete(int sk, uint16_t index, void *buf,
g_free(pending);
}
+static void mgmt_add_uuid_complete(int sk, uint16_t index, void *buf,
+ size_t len)
+{
+ DBG("index %d", index);
+
+ if (index > max_index) {
+ error("Unexpected index %u in add_uuid_complete event", index);
+ return;
+ }
+
+ handle_pending_uuids(index);
+}
+
static void mgmt_cmd_complete(int sk, uint16_t index, void *buf, size_t len)
{
struct mgmt_ev_cmd_complete *ev = buf;
@@ -1434,6 +1442,16 @@ static void mgmt_cmd_complete(int sk, uint16_t index, void *buf, size_t len)
}
}
+static void mgmt_add_uuid_busy(int sk, uint16_t index)
+{
+ struct controller_info *info;
+
+ DBG("index %d", index);
+
+ info = &controllers[index];
+ info->pending_cod_change = TRUE;
+}
+
static void mgmt_cmd_status(int sk, uint16_t index, void *buf, size_t len)
{
struct mgmt_ev_cmd_status *ev = buf;
@@ -1460,6 +1478,10 @@ static void mgmt_cmd_status(int sk, uint16_t index, void *buf, size_t len)
case MGMT_OP_READ_LOCAL_OOB_DATA:
read_local_oob_data_failed(sk, index);
break;
+ case MGMT_OP_ADD_UUID:
+ if (ev->status == MGMT_STATUS_BUSY)
+ mgmt_add_uuid_busy(sk, index);
+ break;
}
}
@@ -1709,6 +1731,25 @@ static void mgmt_new_ltk(int sk, uint16_t index, void *buf, size_t len)
bonding_complete(info, &ev->key.addr.bdaddr, 0);
}
+static void mgmt_cod_changed(int sk, uint16_t index)
+{
+ struct controller_info *info;
+
+ DBG("index %d", index);
+
+ if (index > max_index) {
+ error("Unexpected index %u in mgmt_cod_changed event", index);
+ return;
+ }
+
+ info = &controllers[index];
+
+ if (info->pending_cod_change) {
+ info->pending_cod_change = FALSE;
+ handle_pending_uuids(index);
+ }
+}
+
static gboolean mgmt_event(GIOChannel *io, GIOCondition cond, gpointer user_data)
{
char buf[MGMT_BUF_SIZE];
@@ -1772,7 +1813,7 @@ static gboolean mgmt_event(GIOChannel *io, GIOCondition cond, gpointer user_data
mgmt_new_settings(sk, index, buf + MGMT_HDR_SIZE, len);
break;
case MGMT_EV_CLASS_OF_DEV_CHANGED:
- DBG("hci%u Class of Device changed", index);
+ mgmt_cod_changed(sk, index);
break;
case MGMT_EV_NEW_LINK_KEY:
mgmt_new_link_key(sk, index, buf + MGMT_HDR_SIZE, len);