Merge pull request #110 from andrzej-kaczmarek/npl-dev

porting: More NPL changes/fixes
This commit is contained in:
Andrzej Kaczmarek
2018-05-24 13:49:43 +02:00
committed by GitHub
11 changed files with 180 additions and 56 deletions
+5 -1
View File
@@ -1088,6 +1088,8 @@ ble_ll_event_comp_pkts(struct ble_npl_event *ev)
void
ble_ll_task(void *arg)
{
struct ble_npl_event *ev;
/* Init ble phy */
ble_phy_init();
@@ -1100,7 +1102,9 @@ ble_ll_task(void *arg)
ble_ll_rand_start();
while (1) {
ble_npl_eventq_run(&g_ble_ll_data.ll_evq);
ev = ble_npl_eventq_get(&g_ble_ll_data.ll_evq, BLE_NPL_TIME_FOREVER);
assert(ev);
ble_npl_event_run(ev);
}
}
+13 -3
View File
@@ -27,6 +27,9 @@
#include "ble_hs_priv.h"
#include "ble_monitor_priv.h"
#include "nimble/nimble_npl.h"
#ifndef MYNEWT
#include "nimble/nimble_port.h"
#endif
#define BLE_HS_HCI_EVT_COUNT \
(MYNEWT_VAL(BLE_HCI_EVT_HI_BUF_COUNT) + \
@@ -674,13 +677,20 @@ ble_hs_init(void)
/* Configure the HCI transport to communicate with a host. */
ble_hci_trans_cfg_hs(ble_hs_hci_rx_evt, NULL, ble_hs_rx_data, NULL);
ble_hs_evq_set(ble_npl_eventq_dflt_get());
#ifdef MYNEWT
ble_hs_evq_set((struct ble_npl_eventq *)os_eventq_dflt_get());
#else
ble_hs_evq_set(nimble_port_get_dflt_eventq());
#endif
/* Enqueue the start event to the default event queue. Using the default
* queue ensures the event won't run until the end of main(). This allows
* the application to configure this package in the meantime.
*/
ble_npl_eventq_put(ble_npl_eventq_dflt_get(), &ble_hs_ev_start);
#ifdef MYNEWT
ble_npl_eventq_put((struct ble_npl_eventq *)os_eventq_dflt_get(), &ble_hs_ev_start);
#else
ble_npl_eventq_put(nimble_port_get_dflt_eventq(), &ble_hs_ev_start);
#endif
#if BLE_MONITOR
ble_monitor_new_index(0, (uint8_t[6]){ }, "nimble0");
+2 -4
View File
@@ -64,8 +64,6 @@ void *ble_npl_get_current_task_id(void);
* Event queue
*/
struct ble_npl_eventq *ble_npl_eventq_dflt_get(void);
void ble_npl_eventq_init(struct ble_npl_eventq *evq);
struct ble_npl_event *ble_npl_eventq_get(struct ble_npl_eventq *evq,
@@ -76,8 +74,6 @@ void ble_npl_eventq_put(struct ble_npl_eventq *evq, struct ble_npl_event *ev);
void ble_npl_eventq_remove(struct ble_npl_eventq *evq,
struct ble_npl_event *ev);
void ble_npl_eventq_run(struct ble_npl_eventq *evq);
void ble_npl_event_init(struct ble_npl_event *ev, ble_npl_event_fn *fn,
void *arg);
@@ -89,6 +85,8 @@ void ble_npl_event_set_arg(struct ble_npl_event *ev, void *arg);
bool ble_npl_eventq_is_empty(struct ble_npl_eventq *evq);
void ble_npl_event_run(struct ble_npl_event *ev);
/*
* Mutexes
*/
@@ -20,12 +20,18 @@
#ifndef _NIMBLE_PORT_H
#define _NIMBLE_PORT_H
#include "nimble/nimble_npl.h"
#ifdef __cplusplus
extern "C" {
#endif
void nimble_port_init(void);
void nimble_port_run(void);
struct ble_npl_eventq *nimble_port_get_dflt_eventq(void);
#if NIMBLE_CFG_CONTROLLER
void nimble_port_ll_task_func(void *arg);
#endif
+22
View File
@@ -25,6 +25,8 @@
#include "controller/ble_ll.h"
#endif
static struct ble_npl_eventq g_eventq_dflt;
void
nimble_port_init(void)
{
@@ -34,6 +36,9 @@ nimble_port_init(void)
void ble_hci_ram_init(void);
#endif
/* Initialize default event queue */
ble_npl_eventq_init(&g_eventq_dflt);
os_msys_init();
ble_hs_init();
@@ -49,6 +54,23 @@ nimble_port_init(void)
#endif
}
void
nimble_port_run(void)
{
struct ble_npl_event *ev;
while (1) {
ev = ble_npl_eventq_get(&g_eventq_dflt, BLE_NPL_TIME_FOREVER);
ble_npl_event_run(ev);
}
}
struct ble_npl_eventq *
nimble_port_get_dflt_eventq(void)
{
return &g_eventq_dflt;
}
#if NIMBLE_CFG_CONTROLLER
void
nimble_port_ll_task_func(void *arg)
+6 -7
View File
@@ -32,18 +32,17 @@ ble_npl_get_current_task_id(void)
return NULL;
}
struct ble_npl_eventq *
ble_npl_eventq_dflt_get(void)
{
return NULL;
}
void
ble_npl_eventq_init(struct ble_npl_eventq *evq)
{
}
struct ble_npl_event *
ble_npl_eventq_get(struct ble_npl_eventq *evq, ble_npl_time_t tmo)
{
}
void
ble_npl_eventq_put(struct ble_npl_eventq *evq, struct ble_npl_event *ev)
{
@@ -57,7 +56,7 @@ ble_npl_eventq_remove(struct ble_npl_eventq *evq,
}
void
ble_npl_eventq_run(struct ble_npl_eventq *evq)
ble_npl_event_run(struct ble_npl_event *ev)
{
}
@@ -85,14 +85,6 @@ ble_npl_get_current_task_id(void)
return xTaskGetCurrentTaskHandle();
}
struct ble_npl_eventq *npl_freertos_eventq_dflt_get(void);
static inline struct ble_npl_eventq *
ble_npl_eventq_dflt_get(void)
{
return npl_freertos_eventq_dflt_get();
}
static inline void
ble_npl_eventq_init(struct ble_npl_eventq *evq)
{
@@ -118,13 +110,8 @@ ble_npl_eventq_remove(struct ble_npl_eventq *evq, struct ble_npl_event *ev)
}
static inline void
ble_npl_eventq_run(struct ble_npl_eventq *evq)
ble_npl_event_run(struct ble_npl_event *ev)
{
struct ble_npl_event *ev;
ev = ble_npl_eventq_get(evq, BLE_NPL_TIME_FOREVER);
assert(ev->fn != NULL);
ev->fn(ev);
}
@@ -294,13 +281,15 @@ ble_npl_hw_set_isr(int irqn, uint32_t addr)
static inline uint32_t
ble_npl_hw_enter_critical(void)
{
return npl_freertos_hw_enter_critical();
vPortEnterCritical();
return 0;
}
static inline void
ble_npl_hw_exit_critical(uint32_t ctx)
{
npl_freertos_hw_exit_critical(ctx);
vPortExitCritical();
}
#ifdef __cplusplus
@@ -0,0 +1,35 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
#ifndef _NIMBLE_PORT_FREERTOS_H
#define _NIMBLE_PORT_FREERTOS_H
#include "nimble/nimble_npl.h"
#ifdef __cplusplus
extern "C" {
#endif
void nimble_port_freertos_init(TaskFunction_t host_task_fn);
#ifdef __cplusplus
}
#endif
#endif /* _NIMBLE_PORT_FREERTOS_H */
@@ -0,0 +1,51 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
#include <stddef.h>
#include "FreeRTOS.h"
#include "task.h"
#include "nimble/nimble_port.h"
#if NIMBLE_CFG_CONTROLLER
static TaskHandle_t ll_task_h;
#endif
static TaskHandle_t host_task_h;
void
nimble_port_freertos_init(TaskFunction_t host_task_fn)
{
#if NIMBLE_CFG_CONTROLLER
/*
* Create task where NimBLE LL will run. This one is required as LL has its
* own event queue and should have highest priority. The task function is
* provided by NimBLE and in case of FreeRTOS it does not need to be wrapped
* since it has compatible prototype.
*/
xTaskCreate(nimble_port_ll_task_func, "ll", configMINIMAL_STACK_SIZE + 400,
NULL, configMAX_PRIORITIES - 1, &ll_task_h);
#endif
/*
* Create task where NimBLE host will run. It is not strictly necessary to
* have separate task for NimBLE host, but since something needs to handle
* default queue it is just easier to make separate task which does this.
*/
xTaskCreate(host_task_fn, "ble", configMINIMAL_STACK_SIZE + 400,
NULL, tskIDLE_PRIORITY + 1, &host_task_h);
}
+33 -23
View File
@@ -29,18 +29,6 @@ in_isr(void)
return (SCB->ICSR & SCB_ICSR_VECTACTIVE_Msk) != 0;
}
static struct ble_npl_eventq dflt_evq;
struct ble_npl_eventq *
npl_freertos_eventq_dflt_get(void)
{
if (!dflt_evq.q) {
dflt_evq.q = xQueueCreate(32, sizeof(struct ble_npl_eventq *));
}
return &dflt_evq;
}
struct ble_npl_event *
npl_freertos_eventq_get(struct ble_npl_eventq *evq, ble_npl_time_t tmo)
{
@@ -94,6 +82,7 @@ npl_freertos_eventq_remove(struct ble_npl_eventq *evq,
BaseType_t ret;
int i;
int count;
BaseType_t woken, woken2;
if (!ev->queued) {
return;
@@ -106,22 +95,43 @@ npl_freertos_eventq_remove(struct ble_npl_eventq *evq,
* better use counting semaphore with os_queue to handle this in future.
*/
vPortEnterCritical();
if (in_isr()) {
woken = pdFALSE;
count = uxQueueMessagesWaiting(evq->q);
for (i = 0; i < count; i++) {
ret = xQueueReceive(evq->q, &tmp_ev, 0);
assert(ret == pdPASS);
count = uxQueueMessagesWaitingFromISR(evq->q);
for (i = 0; i < count; i++) {
ret = xQueueReceiveFromISR(evq->q, &tmp_ev, &woken2);
assert(ret == pdPASS);
woken |= woken2;
if (tmp_ev == ev) {
continue;
if (tmp_ev == ev) {
continue;
}
ret = xQueueSendToBackFromISR(evq->q, &tmp_ev, &woken2);
assert(ret == pdPASS);
woken |= woken2;
}
ret = xQueueSendToBack(evq->q, &tmp_ev, 0);
assert(ret == pdPASS);
}
portYIELD_FROM_ISR(woken);
} else {
vPortEnterCritical();
vPortExitCritical();
count = uxQueueMessagesWaiting(evq->q);
for (i = 0; i < count; i++) {
ret = xQueueReceive(evq->q, &tmp_ev, 0);
assert(ret == pdPASS);
if (tmp_ev == ev) {
continue;
}
ret = xQueueSendToBack(evq->q, &tmp_ev, 0);
assert(ret == pdPASS);
}
vPortExitCritical();
}
ev->queued = 0;
}
@@ -110,9 +110,9 @@ ble_npl_eventq_remove(struct ble_npl_eventq *evq,
}
static inline void
ble_npl_eventq_run(struct ble_npl_eventq *evq)
ble_npl_event_run(struct ble_npl_event *ev)
{
os_eventq_run(&evq->evq);
ev->ev.ev_cb(&ev->ev);
}
static inline bool