summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorVinayak Chettimada <vinayak.kariappa.chettimada@nordicsemi.no>2017-03-08 13:42:34 +0100
committerAnas Nashif <nashif@linux.intel.com>2017-03-08 15:51:18 +0000
commit85922c04458e23276e943335adc95684b3055b8e (patch)
tree7be6c941af9e9488a5aae1b081ba776341fb9d13
parent1408adeae1a2124c0d36adb905b9e269a8257be3 (diff)
Bluetooth: Controller: mayfly enable to supercede over disable
If mayfly enable is called before mayfly could be disabled, then enable shall supercede disabling, the mayfly will remain enabled. Any new mayfly enqueued by the caller that tried to disable mayfly will be chain for deferred executon under this condition. The BLE Controller's connection update procedure broke when mayfly implementation was updated to defer disabling until all queued mayfly where completed. Mayfly is disabled between ticker_stop and ticker_start calls to chain them so that ticker does not power off counter h/w if the ticker being stopped is last one. This commit fixes the connection update procedure which used the mayfly enable before mayfly disable could complete. Jira: ZEP-1839 Change-id: I07d34c90d193b5eca9762acd8b7272e8d7a78474 Signed-off-by: Vinayak Chettimada <vinayak.kariappa.chettimada@nordicsemi.no>
-rw-r--r--subsys/bluetooth/controller/util/mayfly.c33
1 files changed, 23 insertions, 10 deletions
diff --git a/subsys/bluetooth/controller/util/mayfly.c b/subsys/bluetooth/controller/util/mayfly.c
index 531627cd0..d97d79638 100644
--- a/subsys/bluetooth/controller/util/mayfly.c
+++ b/subsys/bluetooth/controller/util/mayfly.c
@@ -14,13 +14,10 @@
static struct {
void *head;
void *tail;
- union {
- uint32_t flags;
- struct {
- uint32_t disable_req : 1;
- uint32_t disable_ack : 1;
- };
- };
+ uint8_t enable_req;
+ uint8_t enable_ack;
+ uint8_t disable_req;
+ uint8_t disable_ack;
} mft[MAYFLY_CALLEE_COUNT][MAYFLY_CALLER_COUNT];
static void *mfl[MAYFLY_CALLEE_COUNT][MAYFLY_CALLER_COUNT][2];
@@ -45,6 +42,11 @@ void mayfly_init(void)
void mayfly_enable(uint8_t caller_id, uint8_t callee_id, uint8_t enable)
{
if (enable) {
+ if (mft[callee_id][caller_id].enable_req ==
+ mft[callee_id][caller_id].enable_ack) {
+ mft[callee_id][caller_id].enable_req++;
+ }
+
mayfly_enable_cb(caller_id, callee_id, enable);
} else {
if (mft[callee_id][caller_id].disable_req ==
@@ -63,7 +65,9 @@ uint32_t mayfly_enqueue(uint8_t caller_id, uint8_t callee_id, uint8_t chain,
uint8_t ack;
chain = chain || !mayfly_prio_is_equal(caller_id, callee_id) ||
- !mayfly_is_enabled(caller_id, callee_id);
+ !mayfly_is_enabled(caller_id, callee_id) ||
+ (mft[callee_id][caller_id].disable_req !=
+ mft[callee_id][caller_id].disable_ack);
/* shadow the ack */
ack = m->_ack;
@@ -110,8 +114,9 @@ uint32_t mayfly_enqueue(uint8_t caller_id, uint8_t callee_id, uint8_t chain,
void mayfly_run(uint8_t callee_id)
{
- uint8_t caller_id;
uint8_t disable = 0;
+ uint8_t enable = 0;
+ uint8_t caller_id;
/* iterate through each caller queue to this callee_id */
caller_id = MAYFLY_CALLER_COUNT;
@@ -180,9 +185,17 @@ void mayfly_run(uint8_t callee_id)
mft[callee_id][caller_id].disable_ack =
mft[callee_id][caller_id].disable_req;
}
+
+ if (mft[callee_id][caller_id].enable_req !=
+ mft[callee_id][caller_id].enable_ack) {
+ enable = 1;
+
+ mft[callee_id][caller_id].enable_ack =
+ mft[callee_id][caller_id].enable_req;
+ }
}
- if (disable) {
+ if (disable && !enable) {
mayfly_enable_cb(callee_id, callee_id, 0);
}
}