You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mynewt.apache.org by we...@apache.org on 2016/08/12 00:51:23 UTC

[01/10] incubator-mynewt-core git commit: MYNEWT_83: Use fixed buffer for reception.

Repository: incubator-mynewt-core
Updated Branches:
  refs/heads/develop ca1c44691 -> 5e3595d7b


MYNEWT_83: Use fixed buffer for reception.

On the nrf51, copying the fixed buffer was taking too long for certain
operations. The code changes associated with this commit are due to
this issue.


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/ea5736ed
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/ea5736ed
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/ea5736ed

Branch: refs/heads/develop
Commit: ea5736edb6914f1a56905fbce00ede5938aa7824
Parents: 7c8cca9
Author: William San Filippo <wi...@runtime.io>
Authored: Mon Jul 25 10:16:41 2016 -0700
Committer: William San Filippo <wi...@runtime.io>
Committed: Thu Aug 11 17:38:54 2016 -0700

----------------------------------------------------------------------
 net/nimble/controller/src/ble_ll.c           | 16 ++++-----
 net/nimble/controller/src/ble_ll_conn.c      | 41 +++++++++++++----------
 net/nimble/controller/src/ble_ll_conn_priv.h |  3 +-
 net/nimble/controller/src/ble_ll_resolv.c    | 25 +++++++++++---
 net/nimble/controller/src/ble_ll_scan.c      |  4 +--
 5 files changed, 57 insertions(+), 32 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/ea5736ed/net/nimble/controller/src/ble_ll.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll.c b/net/nimble/controller/src/ble_ll.c
index 96199d0..b8fcca5 100644
--- a/net/nimble/controller/src/ble_ll.c
+++ b/net/nimble/controller/src/ble_ll.c
@@ -801,23 +801,23 @@ ble_ll_rx_end(uint8_t *rxbuf, struct ble_mbuf_hdr *rxhdr)
         }
     }
 
-    /* Get an mbuf and copy data into it */
-    if (badpkt) {
-        rxpdu = NULL;
-    } else {
-        rxpdu = ble_phy_rxpdu_get(rxbuf, len + BLE_LL_PDU_HDR_LEN);
-    }
-
     /* Hand packet to the appropriate state machine (if crc ok) */
+    rxpdu = NULL;
     switch (BLE_MBUF_HDR_RX_STATE(rxhdr)) {
     case BLE_LL_STATE_ADV:
+        if (!badpkt) {
+            rxpdu = ble_phy_rxpdu_get(rxbuf, len + BLE_LL_PDU_HDR_LEN);
+        }
         rc = ble_ll_adv_rx_isr_end(pdu_type, rxpdu, crcok);
         break;
     case BLE_LL_STATE_SCANNING:
+        if (!badpkt) {
+            rxpdu = ble_phy_rxpdu_get(rxbuf, len + BLE_LL_PDU_HDR_LEN);
+        }
         rc = ble_ll_scan_rx_isr_end(rxpdu, crcok);
         break;
     case BLE_LL_STATE_INITIATING:
-        rc = ble_ll_init_rx_isr_end(rxpdu, crcok);
+        rc = ble_ll_init_rx_isr_end(rxbuf, crcok, rxhdr);
         break;
     default:
         rc = -1;

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/ea5736ed/net/nimble/controller/src/ble_ll_conn.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_conn.c b/net/nimble/controller/src/ble_ll_conn.c
index 77d62fc..bfbdf99 100644
--- a/net/nimble/controller/src/ble_ll_conn.c
+++ b/net/nimble/controller/src/ble_ll_conn.c
@@ -2195,7 +2195,8 @@ ble_ll_init_rx_pkt_in(uint8_t *rxbuf, struct ble_mbuf_hdr *ble_hdr)
  *       > 0: Do not disable PHY as that has already been done.
  */
 int
-ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
+ble_ll_init_rx_isr_end(uint8_t *rxbuf, uint8_t crcok,
+                       struct ble_mbuf_hdr *ble_hdr)
 {
     int rc;
     int resolved;
@@ -2208,24 +2209,18 @@ ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
     uint8_t *adv_addr;
     uint8_t *peer;
     uint8_t *init_addr;
-    uint8_t *rxbuf;
     uint8_t pyld_len;
     uint8_t inita_is_rpa;
     uint32_t endtime;
-    struct ble_mbuf_hdr *ble_hdr;
+    struct os_mbuf *rxpdu;
     struct ble_ll_conn_sm *connsm;
 
     /*
      * We have to restart receive if we cant hand up pdu. We return 0 so that
      * the phy does not get disabled.
      */
-    if (!rxpdu) {
-        ble_phy_disable();
-        ble_phy_rx();
-        return 0;
-    }
-
     rc = -1;
+    pyld_len = rxbuf[1] & BLE_ADV_PDU_HDR_LEN_MASK;
     if (!crcok) {
         goto init_rx_isr_exit;
     }
@@ -2234,10 +2229,7 @@ ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
     connsm = g_ble_ll_conn_create_sm;
 
     /* Only interested in ADV IND or ADV DIRECT IND */
-    rxbuf = rxpdu->om_data;
     pdu_type = rxbuf[0] & BLE_ADV_PDU_HDR_TYPE_MASK;
-    pyld_len = rxbuf[1] & BLE_ADV_PDU_HDR_LEN_MASK;
-
     inita_is_rpa = 0;
 
     switch (pdu_type) {
@@ -2285,7 +2277,6 @@ ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
         }
 
         index = -1;
-        ble_hdr = BLE_MBUF_HDR_PTR(rxpdu);
         peer = adv_addr;
         peer_addr_type = addr_type;
 
@@ -2303,7 +2294,7 @@ ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
                 resolved = 1;
             } else {
                 if (chk_wl) {
-                    return -1;
+                    goto init_rx_isr_exit;
                 }
             }
         }
@@ -2312,12 +2303,12 @@ ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
         /* Check filter policy */
         if (chk_wl) {
             if (!ble_ll_whitelist_match(peer, peer_addr_type, resolved)) {
-                return -1;
+                goto init_rx_isr_exit;
             }
         } else {
             /* Must match the connection address */
             if (!ble_ll_conn_is_peer_adv(addr_type, adv_addr, index)) {
-                return -1;
+                goto init_rx_isr_exit;
             }
         }
         ble_hdr->rxinfo.flags |= BLE_MBUF_HDR_F_DEVMATCH;
@@ -2330,7 +2321,7 @@ ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
             if ((index < 0) ||
                 !ble_ll_resolv_rpa(init_addr,
                                    g_ble_ll_resolv_list[index].rl_local_irk)) {
-                return -1;
+                goto init_rx_isr_exit;
             }
         }
 
@@ -2344,6 +2335,8 @@ ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
             if (!rc) {
                 CONN_F_CONN_REQ_TXD(connsm) = 1;
                 STATS_INC(ble_ll_conn_stats, conn_req_txd);
+            } else {
+                ble_ll_sched_rmv_elem(&connsm->conn_sch);
             }
         } else {
             /* Count # of times we could not set schedule */
@@ -2352,9 +2345,23 @@ ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
     }
 
 init_rx_isr_exit:
+    /*
+     * We have to restart receive if we cant hand up pdu. We return 0 so that
+     * the phy does not get disabled.
+     */
+    rxpdu = ble_phy_rxpdu_get(rxbuf, pyld_len + BLE_LL_PDU_HDR_LEN);
+    if (rxpdu == NULL) {
+        ble_phy_disable();
+        ble_phy_rx();
+        rc = 0;
+    } else {
+        ble_ll_rx_pdu_in(rxpdu);
+    }
+
     if (rc) {
         ble_ll_state_set(BLE_LL_STATE_STANDBY);
     }
+
     return rc;
 }
 

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/ea5736ed/net/nimble/controller/src/ble_ll_conn_priv.h
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_conn_priv.h b/net/nimble/controller/src/ble_ll_conn_priv.h
index 575b353..fc06e5f 100644
--- a/net/nimble/controller/src/ble_ll_conn_priv.h
+++ b/net/nimble/controller/src/ble_ll_conn_priv.h
@@ -113,7 +113,8 @@ int ble_ll_conn_rx_isr_start(struct ble_mbuf_hdr *rxhdr, uint32_t aa);
 int ble_ll_conn_rx_isr_end(uint8_t *rxbuf, struct ble_mbuf_hdr *rxhdr);
 void ble_ll_conn_rx_data_pdu(struct os_mbuf *rxpdu, struct ble_mbuf_hdr *hdr);
 void ble_ll_init_rx_pkt_in(uint8_t *rxbuf, struct ble_mbuf_hdr *ble_hdr);
-int ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok);
+int ble_ll_init_rx_isr_end(uint8_t *rxbuf, uint8_t crcok,
+                           struct ble_mbuf_hdr *ble_hdr);
 void ble_ll_conn_wfr_timer_exp(void);
 int ble_ll_conn_is_lru(struct ble_ll_conn_sm *s1, struct ble_ll_conn_sm *s2);
 uint32_t ble_ll_conn_get_ce_end_time(void);

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/ea5736ed/net/nimble/controller/src/ble_ll_resolv.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_resolv.c b/net/nimble/controller/src/ble_ll_resolv.c
index 4d91685..b4d58b0 100644
--- a/net/nimble/controller/src/ble_ll_resolv.c
+++ b/net/nimble/controller/src/ble_ll_resolv.c
@@ -340,6 +340,9 @@ ble_ll_resolv_gen_priv_addr(struct ble_ll_resolv_entry *rl, int local,
 {
     uint8_t *irk;
     uint8_t *prand;
+    uint32_t *irk32;
+    uint32_t *key32;
+    uint32_t *pt32;
     struct ble_encryption_block ecb;
 
     assert(rl != NULL);
@@ -356,13 +359,27 @@ ble_ll_resolv_gen_priv_addr(struct ble_ll_resolv_entry *rl, int local,
         irk = rl->rl_peer_irk;
     }
 
-    memcpy(ecb.key, irk, BLE_ENC_BLOCK_SIZE);
-    memset(ecb.plain_text, 0, BLE_ENC_BLOCK_SIZE);
-    swap_buf(&ecb.plain_text[13], prand, 3);
+    irk32 = (uint32_t *)irk;
+    key32 = (uint32_t *)&ecb.key[0];
+    key32[0] = irk32[0];
+    key32[1] = irk32[1];
+    key32[2] = irk32[2];
+    key32[3] = irk32[3];
+    pt32 = (uint32_t *)&ecb.plain_text[0];
+    pt32[0] = 0;
+    pt32[1] = 0;
+    pt32[2] = 0;
+    ecb.plain_text[12] = 0;
+    ecb.plain_text[13] = prand[2];
+    ecb.plain_text[14] = prand[1];
+    ecb.plain_text[15] = prand[0];
 
     /* Calculate hash */
     ble_hw_encrypt_block(&ecb);
-    swap_buf(addr, ecb.cipher_text + 13, 3);
+
+    addr[0] = ecb.cipher_text[15];
+    addr[1] = ecb.cipher_text[14];
+    addr[2] = ecb.cipher_text[13];
 }
 
 /**

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/ea5736ed/net/nimble/controller/src/ble_ll_scan.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_scan.c b/net/nimble/controller/src/ble_ll_scan.c
index f252784..0fc4e79 100644
--- a/net/nimble/controller/src/ble_ll_scan.c
+++ b/net/nimble/controller/src/ble_ll_scan.c
@@ -989,7 +989,7 @@ ble_ll_scan_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
 
     /* If whitelist enabled, check to see if device is in the white list */
     if (chk_wl && !ble_ll_whitelist_match(peer, peer_addr_type, resolved)) {
-        return -1;
+        goto scan_rx_isr_exit;
     }
     ble_hdr->rxinfo.flags |= BLE_MBUF_HDR_F_DEVMATCH;
 
@@ -997,7 +997,7 @@ ble_ll_scan_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok)
     if (chk_send_req) {
         /* Dont send scan request if we have sent one to this advertiser */
         if (ble_ll_scan_have_rxd_scan_rsp(peer, peer_addr_type)) {
-            return -1;
+            goto scan_rx_isr_exit;
         }
 
         /* Better not be a scan response pending */


[03/10] incubator-mynewt-core git commit: Fix error in comment regarding how to calculate pin index from the port and port pin number

Posted by we...@apache.org.
Fix error in comment regarding how to calculate pin index from the port and port pin number


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/bbad7a2a
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/bbad7a2a
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/bbad7a2a

Branch: refs/heads/develop
Commit: bbad7a2a957bbfd2d6c25f6bc5381d39b2da75e8
Parents: ca1c446
Author: William San Filippo <wi...@runtime.io>
Authored: Tue Jul 19 20:19:58 2016 -0700
Committer: William San Filippo <wi...@runtime.io>
Committed: Thu Aug 11 17:38:54 2016 -0700

----------------------------------------------------------------------
 hw/mcu/stm/stm32f4xx/src/hal_gpio.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/bbad7a2a/hw/mcu/stm/stm32f4xx/src/hal_gpio.c
----------------------------------------------------------------------
diff --git a/hw/mcu/stm/stm32f4xx/src/hal_gpio.c b/hw/mcu/stm/stm32f4xx/src/hal_gpio.c
index 56b457e..f5707dd 100644
--- a/hw/mcu/stm/stm32f4xx/src/hal_gpio.c
+++ b/hw/mcu/stm/stm32f4xx/src/hal_gpio.c
@@ -59,7 +59,7 @@
  *          - Multiply by 16.
  *          - Add port pin number.
  *
- *      Ex: PD11 = (4 * 16) + 11 = 75.
+ *      Ex: PE11 = (4 * 16) + 11 = 75.
  *          PA0 = (0 * 16) + 0 = 0
  */
 #define GPIO_INDEX(pin)     ((pin) & 0x0F)


[08/10] incubator-mynewt-core git commit: Fix incorrect handling of multiple connections and starting encrypted links with all of them

Posted by we...@apache.org.
Fix incorrect handling of multiple connections and starting encrypted links with all of them


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/22fe6f2e
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/22fe6f2e
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/22fe6f2e

Branch: refs/heads/develop
Commit: 22fe6f2ed1eef48e6e18779c220e5ab7e5279a7c
Parents: 50d00eb
Author: William San Filippo <wi...@runtime.io>
Authored: Tue Aug 9 15:49:07 2016 -0700
Committer: William San Filippo <wi...@runtime.io>
Committed: Thu Aug 11 17:49:45 2016 -0700

----------------------------------------------------------------------
 apps/bletest/src/main.c | 16 ++++++++++++----
 1 file changed, 12 insertions(+), 4 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/22fe6f2e/apps/bletest/src/main.c
----------------------------------------------------------------------
diff --git a/apps/bletest/src/main.c b/apps/bletest/src/main.c
index 5dd0cde..bfe8d50 100755
--- a/apps/bletest/src/main.c
+++ b/apps/bletest/src/main.c
@@ -659,6 +659,8 @@ bletest_execute_advertiser(void)
     int i;
 #if (BLETEST_CONCURRENT_CONN_TEST == 1)
     int j;
+    uint16_t mask;
+    uint16_t reply_handle;
 #endif
     int rc;
     uint16_t handle;
@@ -730,10 +732,16 @@ bletest_execute_advertiser(void)
     if ((int32_t)(os_time_get() - g_next_os_time) >= 0) {
 #if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1)
         /* Do we need to send a LTK reply? */
-        if (g_bletest_ltk_reply_handle) {
-            //bletest_send_ltk_req_neg_reply(g_bletest_ltk_reply_handle);
-            bletest_send_ltk_req_reply(g_bletest_ltk_reply_handle);
-            g_bletest_ltk_reply_handle = 0;
+        mask = 1;
+        reply_handle = 1;
+        while (g_bletest_ltk_reply_handle && mask) {
+            if (g_bletest_ltk_reply_handle & mask) {
+                bletest_send_ltk_req_reply(reply_handle);
+                //bletest_send_ltk_req_neg_reply(reply_handle);
+                g_bletest_ltk_reply_handle &= ~mask;
+            }
+            ++reply_handle;
+            mask <<= 1;
         }
 #endif
         if (g_bletest_current_conns) {


[04/10] incubator-mynewt-core git commit: MYNEWT-83: Use a fixed buffer for reception for controller stack

Posted by we...@apache.org.
MYNEWT-83: Use a fixed buffer for reception for controller stack

The nimble stack was using mbufs for reception and now uses a
static buffer. The reason behind the change is that we wanted
to be able to receive a frame even though no mbufs were available.
This would allow transmit packets to receive ACKs and thus free
up transmit buffers waiting on connection queues.

There were a number of code changes associated with the phy API.
Implemented a more efficient copy routine to copy words from
the static rx buffer into mbufs. Note that this is not yet done
for transmit frames as we are not sure we could guarantee that
the data pointer is aligned.


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/580f5b6d
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/580f5b6d
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/580f5b6d

Branch: refs/heads/develop
Commit: 580f5b6dd8c56c4fe3e0b4df287c25506a8ec048
Parents: bbad7a2
Author: William San Filippo <wi...@runtime.io>
Authored: Wed Jul 20 04:19:57 2016 -0700
Committer: William San Filippo <wi...@runtime.io>
Committed: Thu Aug 11 17:38:54 2016 -0700

----------------------------------------------------------------------
 .../controller/include/controller/ble_ll.h      |  11 +-
 .../controller/include/controller/ble_ll_scan.h |   2 +-
 .../controller/include/controller/ble_phy.h     |   7 +
 net/nimble/controller/src/ble_ll.c              |  64 ++----
 net/nimble/controller/src/ble_ll_conn.c         |  77 +++----
 net/nimble/controller/src/ble_ll_conn_priv.h    |   2 +-
 net/nimble/controller/src/ble_ll_scan.c         |   6 +-
 net/nimble/controller/src/ble_ll_sched.c        |  14 +-
 net/nimble/drivers/nrf51/src/ble_phy.c          | 215 ++++++++++++------
 net/nimble/drivers/nrf52/src/ble_phy.c          | 217 +++++++++++++------
 net/nimble/include/nimble/nimble_opt.h          |   4 +-
 11 files changed, 383 insertions(+), 236 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/controller/include/controller/ble_ll.h
----------------------------------------------------------------------
diff --git a/net/nimble/controller/include/controller/ble_ll.h b/net/nimble/controller/include/controller/ble_ll.h
index 2be8425..51d725c 100644
--- a/net/nimble/controller/include/controller/ble_ll.h
+++ b/net/nimble/controller/include/controller/ble_ll.h
@@ -313,12 +313,13 @@ int ble_ll_is_our_devaddr(uint8_t *addr, int addr_type);
 void ble_ll_acl_data_in(struct os_mbuf *txpkt);
 
 /*--- PHY interfaces ---*/
+struct ble_mbuf_hdr;
+
 /* Called by the PHY when a packet has started */
-int ble_ll_rx_start(struct os_mbuf *rxpdu, uint8_t chan);
+int ble_ll_rx_start(uint8_t *rxbuf, uint8_t chan, struct ble_mbuf_hdr *hdr);
 
 /* Called by the PHY when a packet reception ends */
-struct ble_mbuf_hdr;
-int ble_ll_rx_end(struct os_mbuf *rxpdu, struct ble_mbuf_hdr *ble_hdr);
+int ble_ll_rx_end(uint8_t *rxbuf, struct ble_mbuf_hdr *rxhdr);
 
 /*--- Controller API ---*/
 void ble_ll_mbuf_init(struct os_mbuf *m, uint8_t pdulen, uint8_t hdr);
@@ -332,6 +333,9 @@ uint8_t ble_ll_state_get(void);
 /* Send an event to LL task */
 void ble_ll_event_send(struct os_event *ev);
 
+/* Hand received pdu's to LL task  */
+void ble_ll_rx_pdu_in(struct os_mbuf *rxpdu);
+
 /* Set random address */
 int ble_ll_set_random_addr(uint8_t *addr);
 
@@ -383,6 +387,7 @@ int ble_ll_rand_start(void);
 #define BLE_LL_LOG_ID_CONN_END          (30)
 #define BLE_LL_LOG_ID_ADV_TXBEG         (50)
 #define BLE_LL_LOG_ID_ADV_TXDONE        (60)
+#define BLE_LL_LOG_ID_SCHED             (80)
 
 #ifdef BLE_LL_LOG
 void ble_ll_log(uint8_t id, uint8_t arg8, uint16_t arg16, uint32_t arg32);

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/controller/include/controller/ble_ll_scan.h
----------------------------------------------------------------------
diff --git a/net/nimble/controller/include/controller/ble_ll_scan.h b/net/nimble/controller/include/controller/ble_ll_scan.h
index 7dafcee..3b935f4 100644
--- a/net/nimble/controller/include/controller/ble_ll_scan.h
+++ b/net/nimble/controller/include/controller/ble_ll_scan.h
@@ -96,7 +96,7 @@ void ble_ll_scan_init(void);
 void ble_ll_scan_reset(void);
 
 /* Called when Link Layer starts to receive a PDU and is in scanning state */
-int ble_ll_scan_rx_isr_start(uint8_t pdu_type, struct os_mbuf *rxpdu);
+int ble_ll_scan_rx_isr_start(uint8_t pdu_type, uint8_t *rxflags);
 
 /* Called when Link Layer has finished receiving a PDU while scanning */
 int ble_ll_scan_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok);

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/controller/include/controller/ble_phy.h
----------------------------------------------------------------------
diff --git a/net/nimble/controller/include/controller/ble_phy.h b/net/nimble/controller/include/controller/ble_phy.h
index 1333c19..74f349a 100644
--- a/net/nimble/controller/include/controller/ble_phy.h
+++ b/net/nimble/controller/include/controller/ble_phy.h
@@ -97,6 +97,13 @@ int ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans);
 /* Place the PHY into receive mode */
 int ble_phy_rx(void);
 
+/*
+ * Retrieve the received PDU from the PHY. This returns an mbuf with
+ * the most recently received PDU in it. It also contains the ble_hdr
+ * as well
+ */
+struct os_mbuf *ble_phy_rxpdu_get(uint8_t *dptr, uint16_t mblen);
+
 /* Get an RSSI reading */
 int ble_phy_rssi_get(void);
 

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/controller/src/ble_ll.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll.c b/net/nimble/controller/src/ble_ll.c
index 1a4f558..96199d0 100644
--- a/net/nimble/controller/src/ble_ll.c
+++ b/net/nimble/controller/src/ble_ll.c
@@ -666,25 +666,21 @@ ble_ll_acl_data_in(struct os_mbuf *txpkt)
  *   > 0: Continue to receive frame and go from rx to tx when done
  */
 int
-ble_ll_rx_start(struct os_mbuf *rxpdu, uint8_t chan)
+ble_ll_rx_start(uint8_t *rxbuf, uint8_t chan, struct ble_mbuf_hdr *rxhdr)
 {
     int rc;
     uint8_t pdu_type;
-    uint8_t *rxbuf;
-    struct ble_mbuf_hdr *ble_hdr;
 
-    ble_ll_log(BLE_LL_LOG_ID_RX_START, chan, 0, (uint32_t)rxpdu);
+    ble_ll_log(BLE_LL_LOG_ID_RX_START, chan, 0, rxhdr->beg_cputime);
 
     /* Check channel type */
-    rxbuf = rxpdu->om_data;
     if (chan < BLE_PHY_NUM_DATA_CHANS) {
         /*
          * Data channel pdu. We should be in CONNECTION state with an
          * ongoing connection
          */
         if (g_ble_ll_data.ll_state == BLE_LL_STATE_CONNECTION) {
-            ble_hdr = BLE_MBUF_HDR_PTR(rxpdu);
-            rc = ble_ll_conn_rx_isr_start(ble_hdr, ble_phy_access_addr_get());
+            rc = ble_ll_conn_rx_isr_start(rxhdr, ble_phy_access_addr_get());
         } else {
             STATS_INC(ble_ll_stats, bad_ll_state);
             rc = 0;
@@ -708,7 +704,7 @@ ble_ll_rx_start(struct os_mbuf *rxpdu, uint8_t chan)
         }
         break;
     case BLE_LL_STATE_SCANNING:
-        rc = ble_ll_scan_rx_isr_start(pdu_type, rxpdu);
+        rc = ble_ll_scan_rx_isr_start(pdu_type, &rxhdr->rxinfo.flags);
         break;
     case BLE_LL_STATE_CONNECTION:
         /* Should not occur */
@@ -730,8 +726,8 @@ ble_ll_rx_start(struct os_mbuf *rxpdu, uint8_t chan)
  *
  * NOTE: Called from interrupt context!
  *
- * @param rxpdu Pointer to received PDU
- *        ble_hdr Pointer to BLE header of received mbuf
+ * @param rxbuf Pointer to received PDU data
+ *        rxhdr Pointer to BLE header of received mbuf
  *
  * @return int
  *       < 0: Disable the phy after reception.
@@ -739,7 +735,7 @@ ble_ll_rx_start(struct os_mbuf *rxpdu, uint8_t chan)
  *       > 0: Do not disable PHY as that has already been done.
  */
 int
-ble_ll_rx_end(struct os_mbuf *rxpdu, struct ble_mbuf_hdr *ble_hdr)
+ble_ll_rx_end(uint8_t *rxbuf, struct ble_mbuf_hdr *rxhdr)
 {
     int rc;
     int badpkt;
@@ -747,40 +743,23 @@ ble_ll_rx_end(struct os_mbuf *rxpdu, struct ble_mbuf_hdr *ble_hdr)
     uint8_t len;
     uint8_t chan;
     uint8_t crcok;
-    uint16_t mblen;
-    uint8_t *rxbuf;
-
-    /* Set the rx buffer pointer to the start of the received data */
-    rxbuf = rxpdu->om_data;
+    struct os_mbuf *rxpdu;
 
     /* Get channel and CRC status from BLE header */
-    chan = ble_hdr->rxinfo.channel;
-    crcok = BLE_MBUF_HDR_CRC_OK(ble_hdr);
+    chan = rxhdr->rxinfo.channel;
+    crcok = BLE_MBUF_HDR_CRC_OK(rxhdr);
 
     ble_ll_log(BLE_LL_LOG_ID_RX_END, rxbuf[0],
-               ((uint16_t)ble_hdr->rxinfo.flags << 8) | rxbuf[1],
-               (BLE_MBUF_HDR_PTR(rxpdu))->beg_cputime);
+               ((uint16_t)rxhdr->rxinfo.flags << 8) | rxbuf[1],
+               rxhdr->beg_cputime);
 
     /* Check channel type */
     if (chan < BLE_PHY_NUM_DATA_CHANS) {
-        /* Set length in the received PDU */
-        mblen = rxbuf[1] + BLE_LL_PDU_HDR_LEN;
-        OS_MBUF_PKTHDR(rxpdu)->omp_len = mblen;
-        rxpdu->om_len = mblen;
-
-        /*
-         * NOTE: this looks a bit odd, and it is, but for now we place the
-         * received PDU on the Link Layer task before calling the rx end
-         * function. We do this to guarantee connection event end ordering
-         * and receive PDU processing.
-         */
-        ble_ll_rx_pdu_in(rxpdu);
-
         /*
          * Data channel pdu. We should be in CONNECTION state with an
          * ongoing connection.
          */
-        rc = ble_ll_conn_rx_isr_end(rxpdu);
+        rc = ble_ll_conn_rx_isr_end(rxbuf, rxhdr);
         return rc;
     }
 
@@ -788,14 +767,9 @@ ble_ll_rx_end(struct os_mbuf *rxpdu, struct ble_mbuf_hdr *ble_hdr)
     pdu_type = rxbuf[0] & BLE_ADV_PDU_HDR_TYPE_MASK;
     len = rxbuf[1] & BLE_ADV_PDU_HDR_LEN_MASK;
 
-    /* Setup the mbuf lengths */
-    mblen = len + BLE_LL_PDU_HDR_LEN;
-    OS_MBUF_PKTHDR(rxpdu)->omp_len = mblen;
-    rxpdu->om_len = mblen;
-
     /* If the CRC checks, make sure lengths check! */
+    badpkt = 0;
     if (crcok) {
-        badpkt = 0;
         switch (pdu_type) {
         case BLE_ADV_PDU_TYPE_SCAN_REQ:
         case BLE_ADV_PDU_TYPE_ADV_DIRECT_IND:
@@ -824,14 +798,18 @@ ble_ll_rx_end(struct os_mbuf *rxpdu, struct ble_mbuf_hdr *ble_hdr)
         /* If this is a malformed packet, just kill it here */
         if (badpkt) {
             STATS_INC(ble_ll_stats, rx_adv_malformed_pkts);
-            os_mbuf_free_chain(rxpdu);
-            rxpdu = NULL;
         }
     }
 
+    /* Get an mbuf and copy data into it */
+    if (badpkt) {
+        rxpdu = NULL;
+    } else {
+        rxpdu = ble_phy_rxpdu_get(rxbuf, len + BLE_LL_PDU_HDR_LEN);
+    }
 
     /* Hand packet to the appropriate state machine (if crc ok) */
-    switch (BLE_MBUF_HDR_RX_STATE(ble_hdr)) {
+    switch (BLE_MBUF_HDR_RX_STATE(rxhdr)) {
     case BLE_LL_STATE_ADV:
         rc = ble_ll_adv_rx_isr_end(pdu_type, rxpdu, crcok);
         break;

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/controller/src/ble_ll_conn.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_conn.c b/net/nimble/controller/src/ble_ll_conn.c
index cb0f89b..77d62fc 100644
--- a/net/nimble/controller/src/ble_ll_conn.c
+++ b/net/nimble/controller/src/ble_ll_conn.c
@@ -216,13 +216,13 @@ STATS_NAME_END(ble_ll_conn_stats)
  * Called to determine if the received PDU is an empty PDU or not.
  */
 static int
-ble_ll_conn_is_empty_pdu(struct os_mbuf *rxpdu)
+ble_ll_conn_is_empty_pdu(uint8_t *rxbuf)
 {
     int rc;
     uint8_t llid;
 
-    llid = rxpdu->om_data[0] & BLE_LL_DATA_HDR_LLID_MASK;
-    if ((llid == BLE_LL_LLID_DATA_FRAG) && (rxpdu->om_data[1] == 0)) {
+    llid = rxbuf[0] & BLE_LL_DATA_HDR_LLID_MASK;
+    if ((llid == BLE_LL_LLID_DATA_FRAG) && (rxbuf[1] == 0)) {
         rc = 1;
     } else {
         rc = 0;
@@ -285,7 +285,7 @@ ble_ll_conn_get_ce_end_time(void)
  *  standby and set the current state machine pointer to NULL.
  */
 static void
-ble_ll_conn_current_sm_over(void)
+ble_ll_conn_current_sm_over(struct ble_ll_conn_sm *connsm)
 {
     /* Disable the PHY */
     ble_phy_disable();
@@ -298,6 +298,15 @@ ble_ll_conn_current_sm_over(void)
 
     /* Set current LL connection to NULL */
     g_ble_ll_conn_cur_sm = NULL;
+
+    /*
+     * NOTE: the connection state machine may be NULL if we are calling
+     * this when we are ending the connection. In that case, there is no
+     * need to post to the LL the connection event end event
+     */
+    if (connsm) {
+        ble_ll_event_send(&connsm->conn_ev_end);
+    }
 }
 
 /**
@@ -571,11 +580,8 @@ ble_ll_conn_wfr_timer_exp(void)
     struct ble_ll_conn_sm *connsm;
 
     connsm = g_ble_ll_conn_cur_sm;
-    ble_ll_conn_current_sm_over();
-    if (connsm) {
-        ble_ll_event_send(&connsm->conn_ev_end);
-        STATS_INC(ble_ll_conn_stats, wfr_expirations);
-    }
+    ble_ll_conn_current_sm_over(connsm);
+    STATS_INC(ble_ll_conn_stats, wfr_expirations);
 }
 
 /**
@@ -592,10 +598,8 @@ ble_ll_conn_wait_txend(void *arg)
 {
     struct ble_ll_conn_sm *connsm;
 
-    ble_ll_conn_current_sm_over();
-
     connsm = (struct ble_ll_conn_sm *)arg;
-    ble_ll_event_send(&connsm->conn_ev_end);
+    ble_ll_conn_current_sm_over(connsm);
 }
 
 #if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1)
@@ -629,8 +633,7 @@ ble_ll_conn_txend_encrypt(void *arg)
 
     connsm = (struct ble_ll_conn_sm *)arg;
     CONN_F_ENCRYPTED(connsm) = 1;
-    ble_ll_conn_current_sm_over();
-    ble_ll_event_send(&connsm->conn_ev_end);
+    ble_ll_conn_current_sm_over(connsm);
 }
 
 static void
@@ -640,8 +643,7 @@ ble_ll_conn_rxend_unencrypt(void *arg)
 
     connsm = (struct ble_ll_conn_sm *)arg;
     CONN_F_ENCRYPTED(connsm) = 0;
-    ble_ll_conn_current_sm_over();
-    ble_ll_event_send(&connsm->conn_ev_end);
+    ble_ll_conn_current_sm_over(connsm);
 }
 
 static void
@@ -2375,7 +2377,7 @@ ble_ll_conn_timeout(struct ble_ll_conn_sm *connsm, uint8_t ble_err)
     was_current = 0;
     OS_ENTER_CRITICAL(sr);
     if (g_ble_ll_conn_cur_sm == connsm) {
-        ble_ll_conn_current_sm_over();
+        ble_ll_conn_current_sm_over(NULL);
         was_current = 1;
     }
     OS_EXIT_CRITICAL(sr);
@@ -2447,7 +2449,6 @@ ble_ll_conn_rx_isr_start(struct ble_mbuf_hdr *rxhdr, uint32_t aa)
             connsm->anchor_point = connsm->last_anchor_point;
         }
     }
-
     return 1;
 }
 
@@ -2599,7 +2600,7 @@ conn_rx_data_pdu_end:
  *       > 0: Do not disable PHY as that has already been done.
  */
 int
-ble_ll_conn_rx_isr_end(struct os_mbuf *rxpdu)
+ble_ll_conn_rx_isr_end(uint8_t *rxbuf, struct ble_mbuf_hdr *rxhdr)
 {
     int rc;
     int is_ctrl;
@@ -2615,7 +2616,7 @@ ble_ll_conn_rx_isr_end(struct os_mbuf *rxpdu)
     uint32_t endtime;
     struct os_mbuf *txpdu;
     struct ble_ll_conn_sm *connsm;
-    struct ble_mbuf_hdr *rxhdr;
+    struct os_mbuf *rxpdu;
     struct ble_mbuf_hdr *txhdr;
 
     /*
@@ -2630,9 +2631,8 @@ ble_ll_conn_rx_isr_end(struct os_mbuf *rxpdu)
     }
 
     /* Set the handle in the ble mbuf header */
-    rxhdr = BLE_MBUF_HDR_PTR(rxpdu);
-    hdr_byte = rxpdu->om_data[0];
-    rx_pyld_len = rxpdu->om_data[1];
+    hdr_byte = rxbuf[0];
+    rx_pyld_len = rxbuf[1];
 
     /*
      * Check the packet CRC. A connection event can continue even if the
@@ -2659,15 +2659,13 @@ ble_ll_conn_rx_isr_end(struct os_mbuf *rxpdu)
         /* Reset consecutively received bad crcs (since this one was good!) */
         connsm->cons_rxd_bad_crc = 0;
 
-        /* Check for valid LLID before proceeding. */
+        /*
+         * Check for valid LLID before proceeding. We have seen some weird
+         * things with the PHY where the CRC is OK but we dont have a valid
+         * LLID. This should really never happen but if it does we will just
+         * bail. An error stat will get incremented at the LL.
+         */
         if ((hdr_byte & BLE_LL_DATA_HDR_LLID_MASK) == 0) {
-            /*
-             * XXX: for now, just exit since we dont trust the length
-             * and may erroneously adjust anchor. Once we fix the anchor
-             * point issue we need to decide what to do on bad llid. Note
-             * that an error stat gets counted at the LL
-             */
-            reply = 0;
             goto conn_exit;
         }
 
@@ -2683,7 +2681,7 @@ ble_ll_conn_rx_isr_end(struct os_mbuf *rxpdu)
         if ((hdr_sn && conn_nesn) || (!hdr_sn && !conn_nesn)) {
             connsm->next_exp_seqnum ^= 1;
 #if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1)
-            if (CONN_F_ENCRYPTED(connsm) && !ble_ll_conn_is_empty_pdu(rxpdu)) {
+            if (CONN_F_ENCRYPTED(connsm) && !ble_ll_conn_is_empty_pdu(rxbuf)) {
                 ++connsm->enc_data.rx_pkt_cntr;
             }
 #endif
@@ -2776,13 +2774,13 @@ chk_rx_terminate_ind:
         is_ctrl = 0;
         if ((hdr_byte & BLE_LL_DATA_HDR_LLID_MASK) == BLE_LL_LLID_CTRL) {
             is_ctrl = 1;
-            opcode = rxpdu->om_data[2];
+            opcode = rxbuf[2];
         }
 
         /* If we received a terminate IND, we must set some flags */
         if (is_ctrl && (opcode == BLE_LL_CTRL_TERMINATE_IND)) {
             connsm->csmflags.cfbit.terminate_ind_rxd = 1;
-            connsm->rxd_disconnect_reason = rxpdu->om_data[3];
+            connsm->rxd_disconnect_reason = rxbuf[3];
             reply = 1;
         } else if (connsm->conn_role == BLE_LL_CONN_ROLE_MASTER) {
             reply = CONN_F_LAST_TXD_MD(connsm) || (hdr_byte & BLE_LL_DATA_HDR_MD_MASK);
@@ -2808,12 +2806,15 @@ chk_rx_terminate_ind:
     }
 
 conn_exit:
+    /* Copy the received pdu and hand it up */
+    rxpdu = ble_phy_rxpdu_get(rxbuf, rxbuf[1] + BLE_LL_PDU_HDR_LEN);
+    if (rxpdu) {
+        ble_ll_rx_pdu_in(rxpdu);
+    }
+
     /* Send link layer a connection end event if over */
     if (rc) {
-        ble_ll_conn_current_sm_over();
-        if (connsm) {
-            ble_ll_event_send(&connsm->conn_ev_end);
-        }
+        ble_ll_conn_current_sm_over(connsm);
     }
 
     return rc;

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/controller/src/ble_ll_conn_priv.h
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_conn_priv.h b/net/nimble/controller/src/ble_ll_conn_priv.h
index b855b22..575b353 100644
--- a/net/nimble/controller/src/ble_ll_conn_priv.h
+++ b/net/nimble/controller/src/ble_ll_conn_priv.h
@@ -110,7 +110,7 @@ void ble_ll_conn_event_end(void *arg);
 void ble_ll_conn_tx_pkt_in(struct os_mbuf *om, uint16_t handle, uint16_t len);
 void ble_ll_conn_spvn_timeout(void *arg);
 int ble_ll_conn_rx_isr_start(struct ble_mbuf_hdr *rxhdr, uint32_t aa);
-int ble_ll_conn_rx_isr_end(struct os_mbuf *rxpdu);
+int ble_ll_conn_rx_isr_end(uint8_t *rxbuf, struct ble_mbuf_hdr *rxhdr);
 void ble_ll_conn_rx_data_pdu(struct os_mbuf *rxpdu, struct ble_mbuf_hdr *hdr);
 void ble_ll_init_rx_pkt_in(uint8_t *rxbuf, struct ble_mbuf_hdr *ble_hdr);
 int ble_ll_init_rx_isr_end(struct os_mbuf *rxpdu, uint8_t crcok);

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/controller/src/ble_ll_scan.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_scan.c b/net/nimble/controller/src/ble_ll_scan.c
index 64c3990..f252784 100644
--- a/net/nimble/controller/src/ble_ll_scan.c
+++ b/net/nimble/controller/src/ble_ll_scan.c
@@ -838,11 +838,10 @@ ble_ll_scan_event_proc(void *arg)
  *  1: we may send a response to this frame.
  */
 int
-ble_ll_scan_rx_isr_start(uint8_t pdu_type, struct os_mbuf *rxpdu)
+ble_ll_scan_rx_isr_start(uint8_t pdu_type, uint8_t *rxflags)
 {
     int rc;
     struct ble_ll_scan_sm *scansm;
-    struct ble_mbuf_hdr *ble_hdr;
 
     rc = 0;
     scansm = &g_ble_ll_scan_sm;
@@ -864,8 +863,7 @@ ble_ll_scan_rx_isr_start(uint8_t pdu_type, struct os_mbuf *rxpdu)
          */
         if (scansm->scan_rsp_pending) {
             if (pdu_type == BLE_ADV_PDU_TYPE_SCAN_RSP) {
-                ble_hdr = BLE_MBUF_HDR_PTR(rxpdu);
-                ble_hdr->rxinfo.flags |= BLE_MBUF_HDR_F_SCAN_RSP_CHK;
+                *rxflags |= BLE_MBUF_HDR_F_SCAN_RSP_CHK;
             } else {
                 ble_ll_scan_req_backoff(scansm, 0);
             }

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/controller/src/ble_ll_sched.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_sched.c b/net/nimble/controller/src/ble_ll_sched.c
index 5b79217..90cb510 100644
--- a/net/nimble/controller/src/ble_ll_sched.c
+++ b/net/nimble/controller/src/ble_ll_sched.c
@@ -32,6 +32,10 @@
 /* XXX: this is temporary. Not sure what I want to do here */
 struct cpu_timer g_ble_ll_sched_timer;
 
+#if (BLE_LL_SCHED_DEBUG == 1)
+int32_t g_ble_ll_sched_max_late;
+#endif
+
 /* XXX: TODO:
  *  1) Add some accounting to the schedule code to see how late we are
  *  (min/max?)
@@ -645,6 +649,7 @@ ble_ll_sched_execute_item(struct ble_ll_sched_item *sch)
         } else {
             STATS_INC(ble_ll_stats, sched_state_conn_errs);
             ble_ll_conn_event_halt();
+            return -1;
         }
     }
 
@@ -663,12 +668,19 @@ ble_ll_sched_execute_item(struct ble_ll_sched_item *sch)
 void
 ble_ll_sched_run(void *arg)
 {
+    int32_t dt;
     struct ble_ll_sched_item *sch;
 
     /* Look through schedule queue */
     while ((sch = TAILQ_FIRST(&g_ble_ll_sched_q)) != NULL) {
         /* Make sure we have passed the start time of the first event */
-        if ((int32_t)(cputime_get32() - sch->start_time) >= 0) {
+        dt = (int32_t)(cputime_get32() - sch->start_time);
+        if (dt >= 0) {
+#if (BLE_LL_SCHED_DEBUG == 1)
+            if (dt > g_ble_ll_sched_max_late) {
+                g_ble_ll_sched_max_late = dt;
+            }
+#endif
             /* Remove schedule item and execute the callback */
             TAILQ_REMOVE(&g_ble_ll_sched_q, sch, link);
             sch->enqueued = 0;

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/drivers/nrf51/src/ble_phy.c
----------------------------------------------------------------------
diff --git a/net/nimble/drivers/nrf51/src/ble_phy.c b/net/nimble/drivers/nrf51/src/ble_phy.c
index 0c05011..15a2da7 100644
--- a/net/nimble/drivers/nrf51/src/ble_phy.c
+++ b/net/nimble/drivers/nrf51/src/ble_phy.c
@@ -38,7 +38,7 @@
 /*
  * XXX: Maximum possible transmit time is 1 msec for a 60ppm crystal
  * and 16ms for a 30ppm crystal! We need to limit PDU size based on
- * crystal accuracy
+ * crystal accuracy. Look at this in the spec.
  */
 
 /* XXX: private header file? */
@@ -82,9 +82,10 @@ struct ble_phy_obj
     uint8_t phy_encrypted;
     uint8_t phy_privacy;
     uint8_t phy_tx_pyld_len;
+    uint8_t *rxdptr;
     uint32_t phy_aar_scratch;
     uint32_t phy_access_address;
-    struct os_mbuf *rxpdu;
+    struct ble_mbuf_hdr rxhdr;
     void *txend_arg;
     ble_phy_tx_end_func txend_cb;
 };
@@ -92,7 +93,8 @@ struct ble_phy_obj g_ble_phy_data;
 
 /* XXX: if 27 byte packets desired we can make this smaller */
 /* Global transmit/receive buffer */
-static uint32_t g_ble_phy_txrx_buf[(BLE_PHY_MAX_PDU_LEN + 3) / 4];
+static uint32_t g_ble_phy_tx_buf[(BLE_PHY_MAX_PDU_LEN + 3) / 4];
+static uint32_t g_ble_phy_rx_buf[(BLE_PHY_MAX_PDU_LEN + 3) / 4];
 
 #if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1)
 /* Make sure word-aligned for faster copies */
@@ -183,33 +185,104 @@ struct nrf_ccm_data g_nrf_ccm_data;
 #endif
 
 /**
- * ble phy rxpdu get
+ * Copies the data from the phy receive buffer into a mbuf chain.
  *
- * Gets a mbuf for PDU reception.
  *
- * @return struct os_mbuf* Pointer to retrieved mbuf or NULL if none available
+ * @param dptr Pointer to receive buffer
+ * @param len Length of receive buffer to copy.
+ *
+ * @return struct os_mbuf* Pointer to mbuf. NULL if no mbuf available.
  */
-static struct os_mbuf *
-ble_phy_rxpdu_get(void)
+struct os_mbuf *
+ble_phy_rxpdu_get(uint8_t *dptr, uint16_t len)
 {
+    uint16_t rem_bytes;
+    uint16_t mb_bytes;
+    uint16_t copylen;
+    uint32_t *dst;
+    uint32_t *src;
     struct os_mbuf *m;
+    struct os_mbuf *n;
+    struct os_mbuf *p;
+    struct ble_mbuf_hdr *ble_hdr;
+    struct os_mbuf_pkthdr *pkthdr;
+
+    /* Better be aligned */
+    assert(((uint32_t)dptr & 3) == 0);
+
+    p = os_msys_get_pkthdr(len, sizeof(struct ble_mbuf_hdr));
+    if (!p) {
+        STATS_INC(ble_phy_stats, no_bufs);
+        return NULL;
+    }
+
+    /*
+     * Fill in the mbuf pkthdr first. NOTE: first mbuf in chain will have data
+     * pre-pended to it so we adjust m_data by a word.
+     */
+    p->om_data += 4;
+    dst = (uint32_t *)(p->om_data);
+    src = (uint32_t *)dptr;
+
+    rem_bytes = len;
+    mb_bytes = (p->om_omp->omp_databuf_len - p->om_pkthdr_len - 4);
+    copylen = min(mb_bytes, rem_bytes);
+    copylen &= 0xFFFC;
+    rem_bytes -= copylen;
+    mb_bytes -= copylen;
+    p->om_len = copylen;
+    while (copylen > 0) {
+        *dst = *src;
+        ++dst;
+        ++src;
+        copylen -= 4;
+    }
 
-    m = g_ble_phy_data.rxpdu;
-    if (m == NULL) {
-        m = os_msys_get_pkthdr(BLE_MBUF_PAYLOAD_SIZE, sizeof(struct ble_mbuf_hdr));
-        if (!m) {
+    /* Copy remaining bytes */
+    m = p;
+    while (rem_bytes > 0) {
+        /* If there are enough bytes in the mbuf, copy them and leave */
+        if (rem_bytes <= mb_bytes) {
+            memcpy(m->om_data + m->om_len, src, rem_bytes);
+            m->om_len += rem_bytes;
+            break;
+        }
+
+        n = os_msys_get(rem_bytes, 0);
+        if (!n) {
+            os_mbuf_free_chain(p);
             STATS_INC(ble_phy_stats, no_bufs);
-        } else {
-            /*
-             * NOTE: we add two bytes to the data pointer as we will prepend
-             * two bytes if we hand this received pdu up to host.
-             */
-            m->om_data += 2;
-            g_ble_phy_data.rxpdu = m;
+            return NULL;
+        }
+
+        /* Chain new mbuf to existing chain */
+        SLIST_NEXT(m, om_next) = n;
+        m = n;
+
+        mb_bytes = m->om_omp->omp_databuf_len;
+        copylen = min(mb_bytes, rem_bytes);
+        copylen &= 0xFFFC;
+        rem_bytes -= copylen;
+        mb_bytes -= copylen;
+        m->om_len = copylen;
+        dst = (uint32_t *)m->om_data;
+        while (copylen > 0) {
+            *dst = *src;
+            ++dst;
+            ++src;
+            copylen -= 4;
         }
     }
 
-    return m;
+    /* Set packet length */
+    pkthdr = OS_MBUF_PKTHDR(p);
+    pkthdr->omp_len = len;
+
+    /* Copy ble header */
+    ble_hdr = BLE_MBUF_HDR_PTR(p);
+    memcpy(ble_hdr, &g_ble_phy_data.rxhdr, sizeof(struct ble_mbuf_hdr));
+
+    return p;
 }
 
 /**
@@ -241,11 +314,16 @@ nrf_wait_disabled(void)
 static void
 ble_phy_rx_xcvr_setup(void)
 {
+    uint8_t *dptr;
+
+    dptr = (uint8_t *)&g_ble_phy_rx_buf[0];
+
 #if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1)
     if (g_ble_phy_data.phy_encrypted) {
+        dptr += 3;
         NRF_RADIO->PACKETPTR = (uint32_t)&g_ble_phy_enc_buf[0];
         NRF_CCM->INPTR = (uint32_t)&g_ble_phy_enc_buf[0];
-        NRF_CCM->OUTPTR = (uint32_t)g_ble_phy_data.rxpdu->om_data;
+        NRF_CCM->OUTPTR = (uint32_t)dptr;
         NRF_CCM->SCRATCHPTR = (uint32_t)&g_nrf_encrypt_scratchpad[0];
         NRF_CCM->MODE = CCM_MODE_MODE_Decryption;
         NRF_CCM->CNFPTR = (uint32_t)&g_nrf_ccm_data;
@@ -254,20 +332,22 @@ ble_phy_rx_xcvr_setup(void)
         NRF_CCM->EVENTS_ENDCRYPT = 0;
         NRF_PPI->CHENSET = PPI_CHEN_CH24_Msk | PPI_CHEN_CH25_Msk;
     } else {
-        NRF_RADIO->PACKETPTR = (uint32_t)g_ble_phy_data.rxpdu->om_data;
+        NRF_RADIO->PACKETPTR = (uint32_t)dptr;
     }
 #else
-    NRF_RADIO->PACKETPTR = (uint32_t)g_ble_phy_data.rxpdu->om_data;
+    NRF_RADIO->PACKETPTR = (uint32_t)dptr;
 #endif
 
 #if (BLE_LL_CFG_FEAT_LL_PRIVACY == 1)
     if (g_ble_phy_data.phy_privacy) {
+        dptr += 3;
+        NRF_RADIO->PACKETPTR = (uint32_t)dptr;
         NRF_RADIO->PCNF0 = (6 << RADIO_PCNF0_LFLEN_Pos) |
                            (2 << RADIO_PCNF0_S1LEN_Pos) |
                            (NRF_S0_LEN << RADIO_PCNF0_S0LEN_Pos);
         NRF_AAR->ENABLE = AAR_ENABLE_ENABLE_Enabled;
         NRF_AAR->IRKPTR = (uint32_t)&g_nrf_irk_list[0];
-        NRF_AAR->ADDRPTR = (uint32_t)g_ble_phy_data.rxpdu->om_data;
+        NRF_AAR->ADDRPTR = (uint32_t)dptr;
         NRF_AAR->SCRATCHPTR = (uint32_t)&g_ble_phy_data.phy_aar_scratch;
         NRF_AAR->EVENTS_END = 0;
         NRF_AAR->EVENTS_RESOLVED = 0;
@@ -289,6 +369,7 @@ ble_phy_rx_xcvr_setup(void)
     /* Reset the rx started flag. Used for the wait for response */
     g_ble_phy_data.phy_rx_started = 0;
     g_ble_phy_data.phy_state = BLE_PHY_STATE_RX;
+    g_ble_phy_data.rxdptr = dptr;
 
     /* I want to know when 1st byte received (after address) */
     NRF_RADIO->BCC = 8; /* in bits */
@@ -313,16 +394,28 @@ ble_phy_rx_xcvr_setup(void)
 static void
 ble_phy_tx_end_isr(void)
 {
+    uint8_t was_encrypted;
     uint8_t transition;
     uint8_t txlen;
     uint32_t wfr_time;
+    uint32_t txstart;
+
+    /*
+     * Read captured tx start time. This is not the actual transmit start
+     * time but it is the time at which the address event occurred
+     * (after transmission of access address)
+     */
+    txstart = NRF_TIMER0->CC[1];
+
+    /* If this transmission was encrypted we need to remember it */
+    was_encrypted = g_ble_phy_data.phy_encrypted;
 
     /* Better be in TX state! */
     assert(g_ble_phy_data.phy_state == BLE_PHY_STATE_TX);
 
     /* Log the event */
-    ble_ll_log(BLE_LL_LOG_ID_PHY_TXEND, (g_ble_phy_txrx_buf[0] >> 8) & 0xFF,
-               g_ble_phy_data.phy_encrypted, NRF_TIMER0->CC[1]);
+    ble_ll_log(BLE_LL_LOG_ID_PHY_TXEND, (g_ble_phy_tx_buf[0] >> 8) & 0xFF,
+               was_encrypted, txstart);
 
     /* Clear events and clear interrupt on disabled event */
     NRF_RADIO->EVENTS_DISABLED = 0;
@@ -335,7 +428,7 @@ ble_phy_tx_end_isr(void)
      * XXX: not sure what to do. We had a HW error during transmission.
      * For now I just count a stat but continue on like all is good.
      */
-    if (g_ble_phy_data.phy_encrypted) {
+    if (was_encrypted) {
         if (NRF_CCM->EVENTS_ERROR) {
             STATS_INC(ble_phy_stats, tx_hw_err);
             NRF_CCM->EVENTS_ERROR = 0;
@@ -343,26 +436,25 @@ ble_phy_tx_end_isr(void)
     }
 #endif
 
+    /* Call transmit end callback */
+    if (g_ble_phy_data.txend_cb) {
+        g_ble_phy_data.txend_cb(g_ble_phy_data.txend_arg);
+    }
+
     transition = g_ble_phy_data.phy_transition;
     if (transition == BLE_PHY_TRANSITION_TX_RX) {
         /* Packet pointer needs to be reset. */
-        if (g_ble_phy_data.rxpdu != NULL) {
-            ble_phy_rx_xcvr_setup();
-        } else {
-            /* Disable the phy */
-            STATS_INC(ble_phy_stats, no_bufs);
-            ble_phy_disable();
-        }
+        ble_phy_rx_xcvr_setup();
 
         /*
          * Enable the wait for response timer. Note that cc #1 on
          * timer 0 contains the transmit start time
          */
         txlen = g_ble_phy_data.phy_tx_pyld_len;
-        if (txlen && g_ble_phy_data.phy_encrypted) {
+        if (txlen && was_encrypted) {
             txlen += BLE_LL_DATA_MIC_LEN;
         }
-        wfr_time = NRF_TIMER0->CC[1] - BLE_TX_LEN_USECS_M(NRF_RX_START_OFFSET);
+        wfr_time = txstart - BLE_TX_LEN_USECS_M(NRF_RX_START_OFFSET);
         wfr_time += BLE_TX_DUR_USECS_M(txlen);
         wfr_time += cputime_usecs_to_ticks(BLE_LL_WFR_USECS);
         ble_ll_wfr_enable(wfr_time);
@@ -371,22 +463,14 @@ ble_phy_tx_end_isr(void)
         NRF_PPI->CHENCLR = PPI_CHEN_CH20_Msk;
         assert(transition == BLE_PHY_TRANSITION_NONE);
     }
-
-    /* Call transmit end callback */
-    if (g_ble_phy_data.txend_cb) {
-        g_ble_phy_data.txend_cb(g_ble_phy_data.txend_arg);
-    }
 }
 
 static void
 ble_phy_rx_end_isr(void)
 {
     int rc;
-#if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1)
     uint8_t *dptr;
-#endif
     uint8_t crcok;
-    struct os_mbuf *rxpdu;
     struct ble_mbuf_hdr *ble_hdr;
 
     /* Clear events and clear interrupt */
@@ -397,12 +481,12 @@ ble_phy_rx_end_isr(void)
     NRF_PPI->CHENCLR = PPI_CHEN_CH21_Msk;
 
     /* Set RSSI and CRC status flag in header */
-    ble_hdr = BLE_MBUF_HDR_PTR(g_ble_phy_data.rxpdu);
+    ble_hdr = &g_ble_phy_data.rxhdr;
     assert(NRF_RADIO->EVENTS_RSSIEND != 0);
     ble_hdr->rxinfo.rssi = -1 * NRF_RADIO->RSSISAMPLE;
-#if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1)
-    dptr = g_ble_phy_data.rxpdu->om_data;
-#endif
+
+    dptr = g_ble_phy_data.rxdptr;
+
     /* Count PHY crc errors and valid packets */
     crcok = (uint8_t)NRF_RADIO->CRCSTATUS;
     if (!crcok) {
@@ -441,10 +525,6 @@ ble_phy_rx_end_isr(void)
 #endif
     }
 
-    /* Call Link Layer receive payload function */
-    rxpdu = g_ble_phy_data.rxpdu;
-    g_ble_phy_data.rxpdu = NULL;
-
 #if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1) || (BLE_LL_CFG_FEAT_LL_PRIVACY == 1)
     if (g_ble_phy_data.phy_encrypted || g_ble_phy_data.phy_privacy) {
         /*
@@ -454,10 +534,10 @@ ble_phy_rx_end_isr(void)
          */
         dptr[2] = dptr[1];
         dptr[1] = dptr[0];
-        rxpdu->om_data += 1;
+        ++dptr;
     }
 #endif
-    rc = ble_ll_rx_end(rxpdu, ble_hdr);
+    rc = ble_ll_rx_end(dptr, ble_hdr);
     if (rc < 0) {
         ble_phy_disable();
     }
@@ -474,8 +554,6 @@ ble_phy_rx_start_isr(void)
     NRF_RADIO->EVENTS_ADDRESS = 0;
     NRF_RADIO->INTENCLR = RADIO_INTENCLR_ADDRESS_Msk;
 
-    assert(g_ble_phy_data.rxpdu != NULL);
-
     /* Wait to get 1st byte of frame */
     while (1) {
         state = NRF_RADIO->STATE;
@@ -495,7 +573,7 @@ ble_phy_rx_start_isr(void)
     }
 
     /* Initialize flags, channel and state in ble header at rx start */
-    ble_hdr = BLE_MBUF_HDR_PTR(g_ble_phy_data.rxpdu);
+    ble_hdr = &g_ble_phy_data.rxhdr;
     ble_hdr->rxinfo.flags = ble_ll_state_get();
     ble_hdr->rxinfo.channel = g_ble_phy_data.phy_chan;
     ble_hdr->rxinfo.handle = 0;
@@ -503,7 +581,8 @@ ble_phy_rx_start_isr(void)
         BLE_TX_LEN_USECS_M(NRF_RX_START_OFFSET);
 
     /* Call Link Layer receive start function */
-    rc = ble_ll_rx_start(g_ble_phy_data.rxpdu, g_ble_phy_data.phy_chan);
+    rc = ble_ll_rx_start(g_ble_phy_data.rxdptr, g_ble_phy_data.phy_chan,
+                         &g_ble_phy_data.rxhdr);
     if (rc >= 0) {
         /* Set rx started flag and enable rx end ISR */
         g_ble_phy_data.phy_rx_started = 1;
@@ -672,11 +751,6 @@ ble_phy_rx(void)
         return BLE_PHY_ERR_RADIO_STATE;
     }
 
-    /* If no pdu, get one */
-    if (ble_phy_rxpdu_get() == NULL) {
-        return BLE_PHY_ERR_NO_BUFS;
-    }
-
     /* Make sure all interrupts are disabled */
     NRF_RADIO->INTENCLR = NRF_RADIO_IRQ_MASK_ALL;
 
@@ -855,7 +929,7 @@ ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans)
 
         NRF_CCM->SHORTS = 1;
         NRF_CCM->INPTR = (uint32_t)&g_ble_phy_enc_buf[0];
-        NRF_CCM->OUTPTR = (uint32_t)&g_ble_phy_txrx_buf[0];
+        NRF_CCM->OUTPTR = (uint32_t)&g_ble_phy_tx_buf[0];
         NRF_CCM->SCRATCHPTR = (uint32_t)&g_nrf_encrypt_scratchpad[0];
         NRF_CCM->EVENTS_ERROR = 0;
         NRF_CCM->MODE = CCM_MODE_MODE_Encryption;
@@ -872,7 +946,7 @@ ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans)
         NRF_AAR->IRKPTR = (uint32_t)&g_nrf_irk_list[0];
 #endif
         /* RAM representation has S0 and LENGTH fields (2 bytes) */
-        dptr = (uint8_t *)&g_ble_phy_txrx_buf[0];
+        dptr = (uint8_t *)&g_ble_phy_tx_buf[0];
         dptr[0] = ble_hdr->txinfo.hdr_byte;
         dptr[1] = payload_len;
         dptr += 2;
@@ -887,13 +961,13 @@ ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans)
 #endif
 
     /* RAM representation has S0 and LENGTH fields (2 bytes) */
-    dptr = (uint8_t *)&g_ble_phy_txrx_buf[0];
+    dptr = (uint8_t *)&g_ble_phy_tx_buf[0];
     dptr[0] = ble_hdr->txinfo.hdr_byte;
     dptr[1] = payload_len;
     dptr += 2;
 #endif
 
-    NRF_RADIO->PACKETPTR = (uint32_t)&g_ble_phy_txrx_buf[0];
+    NRF_RADIO->PACKETPTR = (uint32_t)&g_ble_phy_tx_buf[0];
 
     /* Clear the ready, end and disabled events */
     NRF_RADIO->EVENTS_READY = 0;
@@ -903,13 +977,10 @@ ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans)
     /* Enable shortcuts for transmit start/end. */
     shortcuts = RADIO_SHORTS_END_DISABLE_Msk | RADIO_SHORTS_READY_START_Msk;
     if (end_trans == BLE_PHY_TRANSITION_TX_RX) {
-        /* If we are going into receive after this, try to get a buffer. */
-        if (ble_phy_rxpdu_get()) {
-            shortcuts |= RADIO_SHORTS_DISABLED_RXEN_Msk;
-        }
+        shortcuts |= RADIO_SHORTS_DISABLED_RXEN_Msk;
     }
-    NRF_RADIO->INTENSET = RADIO_INTENSET_DISABLED_Msk;
     NRF_RADIO->SHORTS = shortcuts;
+    NRF_RADIO->INTENSET = RADIO_INTENSET_DISABLED_Msk;
 
     /* Set transmitted payload length */
     g_ble_phy_data.phy_tx_pyld_len = payload_len;

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/drivers/nrf52/src/ble_phy.c
----------------------------------------------------------------------
diff --git a/net/nimble/drivers/nrf52/src/ble_phy.c b/net/nimble/drivers/nrf52/src/ble_phy.c
index 541ece9..8ffab96 100644
--- a/net/nimble/drivers/nrf52/src/ble_phy.c
+++ b/net/nimble/drivers/nrf52/src/ble_phy.c
@@ -39,7 +39,7 @@
 /*
  * XXX: Maximum possible transmit time is 1 msec for a 60ppm crystal
  * and 16ms for a 30ppm crystal! We need to limit PDU size based on
- * crystal accuracy
+ * crystal accuracy. Look at this in the spec.
  */
 
 /* XXX: private header file? */
@@ -79,7 +79,7 @@ struct ble_phy_obj
     uint8_t phy_tx_pyld_len;
     uint32_t phy_aar_scratch;
     uint32_t phy_access_address;
-    struct os_mbuf *rxpdu;
+    struct ble_mbuf_hdr rxhdr;
     void *txend_arg;
     ble_phy_tx_end_func txend_cb;
 };
@@ -87,7 +87,8 @@ struct ble_phy_obj g_ble_phy_data;
 
 /* XXX: if 27 byte packets desired we can make this smaller */
 /* Global transmit/receive buffer */
-static uint32_t g_ble_phy_txrx_buf[(BLE_PHY_MAX_PDU_LEN + 3) / 4];
+static uint32_t g_ble_phy_tx_buf[(BLE_PHY_MAX_PDU_LEN + 3) / 4];
+static uint32_t g_ble_phy_rx_buf[(BLE_PHY_MAX_PDU_LEN + 3) / 4];
 
 #if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1)
 /* Make sure word-aligned for faster copies */
@@ -185,33 +186,104 @@ struct nrf_ccm_data g_nrf_ccm_data;
 #endif
 
 /**
- * ble phy rxpdu get
+ * Copies the data from the phy receive buffer into a mbuf chain.
  *
- * Gets a mbuf for PDU reception.
  *
- * @return struct os_mbuf* Pointer to retrieved mbuf or NULL if none available
+ * @param dptr Pointer to receive buffer
+ * @param len Length of receive buffer to copy.
+ *
+ * @return struct os_mbuf* Pointer to mbuf. NULL if no mbuf available.
  */
-static struct os_mbuf *
-ble_phy_rxpdu_get(void)
+struct os_mbuf *
+ble_phy_rxpdu_get(uint8_t *dptr, uint16_t len)
 {
+    uint16_t rem_bytes;
+    uint16_t mb_bytes;
+    uint16_t copylen;
+    uint32_t *dst;
+    uint32_t *src;
     struct os_mbuf *m;
+    struct os_mbuf *n;
+    struct os_mbuf *p;
+    struct ble_mbuf_hdr *ble_hdr;
+    struct os_mbuf_pkthdr *pkthdr;
 
-    m = g_ble_phy_data.rxpdu;
-    if (m == NULL) {
-        m = os_msys_get_pkthdr(BLE_MBUF_PAYLOAD_SIZE, sizeof(struct ble_mbuf_hdr));
-        if (!m) {
+    /* Better be aligned */
+    assert(((uint32_t)dptr & 3) == 0);
+
+    p = os_msys_get_pkthdr(len, sizeof(struct ble_mbuf_hdr));
+    if (!p) {
+        STATS_INC(ble_phy_stats, no_bufs);
+        return NULL;
+    }
+
+    /*
+     * Fill in the mbuf pkthdr first. NOTE: first mbuf in chain will have data
+     * pre-pended to it so we adjust m_data by a word.
+     */
+    p->om_data += 4;
+    dst = (uint32_t *)(p->om_data);
+    src = (uint32_t *)dptr;
+
+    rem_bytes = len;
+    mb_bytes = (p->om_omp->omp_databuf_len - p->om_pkthdr_len - 4);
+    copylen = min(mb_bytes, rem_bytes);
+    copylen &= 0xFFFC;
+    rem_bytes -= copylen;
+    mb_bytes -= copylen;
+    p->om_len = copylen;
+    while (copylen > 0) {
+        *dst = *src;
+        ++dst;
+        ++src;
+        copylen -= 4;
+    }
+
+    /* Copy remaining bytes */
+    m = p;
+    while (rem_bytes > 0) {
+        /* If there are enough bytes in the mbuf, copy them and leave */
+        if (rem_bytes <= mb_bytes) {
+            memcpy(m->om_data + m->om_len, src, rem_bytes);
+            m->om_len += rem_bytes;
+            break;
+        }
+
+        n = os_msys_get(rem_bytes, 0);
+        if (!n) {
+            os_mbuf_free_chain(p);
             STATS_INC(ble_phy_stats, no_bufs);
-        } else {
-            /*
-             * NOTE: we add two bytes to the data pointer as we will prepend
-             * two bytes if we hand this received pdu up to host.
-             */
-            m->om_data += 2;
-            g_ble_phy_data.rxpdu = m;
+            return NULL;
+        }
+
+        /* Chain new mbuf to existing chain */
+        SLIST_NEXT(m, om_next) = n;
+        m = n;
+
+        mb_bytes = m->om_omp->omp_databuf_len;
+        copylen = min(mb_bytes, rem_bytes);
+        copylen &= 0xFFFC;
+        rem_bytes -= copylen;
+        mb_bytes -= copylen;
+        m->om_len = copylen;
+        dst = (uint32_t *)m->om_data;
+        while (copylen > 0) {
+            *dst = *src;
+            ++dst;
+            ++src;
+            copylen -= 4;
         }
     }
 
-    return m;
+    /* Set packet length */
+    pkthdr = OS_MBUF_PKTHDR(p);
+    pkthdr->omp_len = len;
+
+    /* Copy ble header */
+    ble_hdr = BLE_MBUF_HDR_PTR(p);
+    memcpy(ble_hdr, &g_ble_phy_data.rxhdr, sizeof(struct ble_mbuf_hdr));
+
+    return p;
 }
 
 /**
@@ -243,11 +315,16 @@ nrf_wait_disabled(void)
 static void
 ble_phy_rx_xcvr_setup(void)
 {
+    uint8_t *dptr;
+
+    dptr = (uint8_t *)&g_ble_phy_rx_buf[0];
+    dptr += 3;
+
 #if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1)
     if (g_ble_phy_data.phy_encrypted) {
         NRF_RADIO->PACKETPTR = (uint32_t)&g_ble_phy_enc_buf[0];
         NRF_CCM->INPTR = (uint32_t)&g_ble_phy_enc_buf[0];
-        NRF_CCM->OUTPTR = (uint32_t)g_ble_phy_data.rxpdu->om_data;
+        NRF_CCM->OUTPTR = (uint32_t)dptr;
         NRF_CCM->SCRATCHPTR = (uint32_t)&g_nrf_encrypt_scratchpad[0];
         NRF_CCM->MODE = CCM_MODE_LENGTH_Msk | CCM_MODE_MODE_Decryption;
         NRF_CCM->CNFPTR = (uint32_t)&g_nrf_ccm_data;
@@ -256,17 +333,17 @@ ble_phy_rx_xcvr_setup(void)
         NRF_CCM->EVENTS_ENDCRYPT = 0;
         NRF_PPI->CHENSET = PPI_CHEN_CH24_Msk | PPI_CHEN_CH25_Msk;
     } else {
-        NRF_RADIO->PACKETPTR = (uint32_t)g_ble_phy_data.rxpdu->om_data;
+        NRF_RADIO->PACKETPTR = (uint32_t)dptr;
     }
 #else
-    NRF_RADIO->PACKETPTR = (uint32_t)g_ble_phy_data.rxpdu->om_data;
+    NRF_RADIO->PACKETPTR = (uint32_t)dptr;
 #endif
 
 #if (BLE_LL_CFG_FEAT_LL_PRIVACY == 1)
     if (g_ble_phy_data.phy_privacy) {
         NRF_AAR->ENABLE = AAR_ENABLE_ENABLE_Enabled;
         NRF_AAR->IRKPTR = (uint32_t)&g_nrf_irk_list[0];
-        NRF_AAR->ADDRPTR = (uint32_t)g_ble_phy_data.rxpdu->om_data;
+        NRF_AAR->ADDRPTR = (uint32_t)dptr;
         NRF_AAR->SCRATCHPTR = (uint32_t)&g_ble_phy_data.phy_aar_scratch;
         NRF_AAR->EVENTS_END = 0;
         NRF_AAR->EVENTS_RESOLVED = 0;
@@ -308,16 +385,28 @@ ble_phy_rx_xcvr_setup(void)
 static void
 ble_phy_tx_end_isr(void)
 {
+    uint8_t was_encrypted;
     uint8_t transition;
     uint8_t txlen;
     uint32_t wfr_time;
+    uint32_t txstart;
+
+    /*
+     * Read captured tx start time. This is not the actual transmit start
+     * time but it is the time at which the address event occurred
+     * (after transmission of access address)
+     */
+    txstart = NRF_TIMER0->CC[1];
+
+    /* If this transmission was encrypted we need to remember it */
+    was_encrypted = g_ble_phy_data.phy_encrypted;
 
     /* Better be in TX state! */
     assert(g_ble_phy_data.phy_state == BLE_PHY_STATE_TX);
 
     /* Log the event */
-    ble_ll_log(BLE_LL_LOG_ID_PHY_TXEND, (g_ble_phy_txrx_buf[0] >> 8) & 0xFF,
-               g_ble_phy_data.phy_encrypted, NRF_TIMER0->CC[1]);
+    ble_ll_log(BLE_LL_LOG_ID_PHY_TXEND, (g_ble_phy_tx_buf[0] >> 8) & 0xFF,
+               was_encrypted, txstart);
 
     /* Clear events and clear interrupt on disabled event */
     NRF_RADIO->EVENTS_DISABLED = 0;
@@ -330,7 +419,7 @@ ble_phy_tx_end_isr(void)
      * XXX: not sure what to do. We had a HW error during transmission.
      * For now I just count a stat but continue on like all is good.
      */
-    if (g_ble_phy_data.phy_encrypted) {
+    if (was_encrypted) {
         if (NRF_CCM->EVENTS_ERROR) {
             STATS_INC(ble_phy_stats, tx_hw_err);
             NRF_CCM->EVENTS_ERROR = 0;
@@ -338,26 +427,25 @@ ble_phy_tx_end_isr(void)
     }
 #endif
 
+    /* Call transmit end callback */
+    if (g_ble_phy_data.txend_cb) {
+        g_ble_phy_data.txend_cb(g_ble_phy_data.txend_arg);
+    }
+
     transition = g_ble_phy_data.phy_transition;
     if (transition == BLE_PHY_TRANSITION_TX_RX) {
         /* Packet pointer needs to be reset. */
-        if (g_ble_phy_data.rxpdu != NULL) {
-            ble_phy_rx_xcvr_setup();
-        } else {
-            /* Disable the phy */
-            STATS_INC(ble_phy_stats, no_bufs);
-            ble_phy_disable();
-        }
+        ble_phy_rx_xcvr_setup();
 
         /*
          * Enable the wait for response timer. Note that cc #1 on
          * timer 0 contains the transmit start time
          */
         txlen = g_ble_phy_data.phy_tx_pyld_len;
-        if (txlen && g_ble_phy_data.phy_encrypted) {
+        if (txlen && was_encrypted) {
             txlen += BLE_LL_DATA_MIC_LEN;
         }
-        wfr_time = NRF_TIMER0->CC[1] - BLE_TX_LEN_USECS_M(NRF_RX_START_OFFSET);
+        wfr_time = txstart - BLE_TX_LEN_USECS_M(NRF_RX_START_OFFSET);
         wfr_time += BLE_TX_DUR_USECS_M(txlen);
         wfr_time += cputime_usecs_to_ticks(BLE_LL_WFR_USECS);
         ble_ll_wfr_enable(wfr_time);
@@ -366,11 +454,6 @@ ble_phy_tx_end_isr(void)
         NRF_PPI->CHENCLR = PPI_CHEN_CH20_Msk;
         assert(transition == BLE_PHY_TRANSITION_NONE);
     }
-
-    /* Call transmit end callback */
-    if (g_ble_phy_data.txend_cb) {
-        g_ble_phy_data.txend_cb(g_ble_phy_data.txend_arg);
-    }
 }
 
 static void
@@ -379,7 +462,6 @@ ble_phy_rx_end_isr(void)
     int rc;
     uint8_t *dptr;
     uint8_t crcok;
-    struct os_mbuf *rxpdu;
     struct ble_mbuf_hdr *ble_hdr;
 
     /* Clear events and clear interrupt */
@@ -390,11 +472,12 @@ ble_phy_rx_end_isr(void)
     NRF_PPI->CHENCLR = PPI_CHEN_CH21_Msk;
 
     /* Set RSSI and CRC status flag in header */
-    ble_hdr = BLE_MBUF_HDR_PTR(g_ble_phy_data.rxpdu);
+    ble_hdr = &g_ble_phy_data.rxhdr;
     assert(NRF_RADIO->EVENTS_RSSIEND != 0);
     ble_hdr->rxinfo.rssi = -1 * NRF_RADIO->RSSISAMPLE;
 
-    dptr = g_ble_phy_data.rxpdu->om_data;
+    dptr = (uint8_t *)&g_ble_phy_rx_buf[0];
+    dptr += 3;
 
     /* Count PHY crc errors and valid packets */
     crcok = (uint8_t)NRF_RADIO->CRCSTATUS;
@@ -434,10 +517,6 @@ ble_phy_rx_end_isr(void)
 #endif
     }
 
-    /* Call Link Layer receive payload function */
-    rxpdu = g_ble_phy_data.rxpdu;
-    g_ble_phy_data.rxpdu = NULL;
-
     /*
      * XXX: This is a horrible ugly hack to deal with the RAM S1 byte
      * that is not sent over the air but is present here. Simply move the
@@ -445,9 +524,7 @@ ble_phy_rx_end_isr(void)
      */
     dptr[2] = dptr[1];
     dptr[1] = dptr[0];
-    rxpdu->om_data += 1;
-
-    rc = ble_ll_rx_end(rxpdu, ble_hdr);
+    rc = ble_ll_rx_end(dptr + 1, ble_hdr);
     if (rc < 0) {
         ble_phy_disable();
     }
@@ -464,8 +541,6 @@ ble_phy_rx_start_isr(void)
     NRF_RADIO->EVENTS_ADDRESS = 0;
     NRF_RADIO->INTENCLR = RADIO_INTENCLR_ADDRESS_Msk;
 
-    assert(g_ble_phy_data.rxpdu != NULL);
-
     /* Wait to get 1st byte of frame */
     while (1) {
         state = NRF_RADIO->STATE;
@@ -485,7 +560,7 @@ ble_phy_rx_start_isr(void)
     }
 
     /* Initialize flags, channel and state in ble header at rx start */
-    ble_hdr = BLE_MBUF_HDR_PTR(g_ble_phy_data.rxpdu);
+    ble_hdr = &g_ble_phy_data.rxhdr;
     ble_hdr->rxinfo.flags = ble_ll_state_get();
     ble_hdr->rxinfo.channel = g_ble_phy_data.phy_chan;
     ble_hdr->rxinfo.handle = 0;
@@ -493,7 +568,9 @@ ble_phy_rx_start_isr(void)
         BLE_TX_LEN_USECS_M(NRF_RX_START_OFFSET);
 
     /* Call Link Layer receive start function */
-    rc = ble_ll_rx_start(g_ble_phy_data.rxpdu, g_ble_phy_data.phy_chan);
+    rc = ble_ll_rx_start((uint8_t *)&g_ble_phy_rx_buf[0] + 3,
+                         g_ble_phy_data.phy_chan,
+                         &g_ble_phy_data.rxhdr);
     if (rc >= 0) {
         /* Set rx started flag and enable rx end ISR */
         g_ble_phy_data.phy_rx_started = 1;
@@ -589,6 +666,7 @@ ble_phy_init(void)
                        RADIO_PCNF0_S1INCL_Msk                       |
                        (NRF_S0_LEN << RADIO_PCNF0_S0LEN_Pos)        |
                        (RADIO_PCNF0_PLEN_8bit << RADIO_PCNF0_PLEN_Pos);
+
     /* XXX: should maxlen be 251 for encryption? */
     NRF_RADIO->PCNF1 = NRF_MAXLEN |
                        (RADIO_PCNF1_ENDIAN_Little <<  RADIO_PCNF1_ENDIAN_Pos) |
@@ -664,11 +742,6 @@ ble_phy_rx(void)
         return BLE_PHY_ERR_RADIO_STATE;
     }
 
-    /* If no pdu, get one */
-    if (ble_phy_rxpdu_get() == NULL) {
-        return BLE_PHY_ERR_NO_BUFS;
-    }
-
     /* Make sure all interrupts are disabled */
     NRF_RADIO->INTENCLR = NRF_RADIO_IRQ_MASK_ALL;
 
@@ -809,6 +882,7 @@ ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans)
 {
     int rc;
     uint8_t *dptr;
+    uint8_t *pktptr;
     uint8_t payload_len;
     uint32_t state;
     uint32_t shortcuts;
@@ -829,9 +903,11 @@ ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans)
 #if (BLE_LL_CFG_FEAT_LE_ENCRYPTION == 1)
     if (g_ble_phy_data.phy_encrypted) {
         dptr = (uint8_t *)&g_ble_phy_enc_buf[0];
+        ++dptr;
+        pktptr = (uint8_t *)&g_ble_phy_tx_buf[0];
         NRF_CCM->SHORTS = 1;
-        NRF_CCM->INPTR = (uint32_t)&g_ble_phy_enc_buf[0];
-        NRF_CCM->OUTPTR = (uint32_t)&g_ble_phy_txrx_buf[0];
+        NRF_CCM->INPTR = (uint32_t)dptr;
+        NRF_CCM->OUTPTR = (uint32_t)pktptr;
         NRF_CCM->SCRATCHPTR = (uint32_t)&g_nrf_encrypt_scratchpad[0];
         NRF_CCM->EVENTS_ERROR = 0;
         NRF_CCM->MODE = CCM_MODE_LENGTH_Msk;
@@ -843,13 +919,17 @@ ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans)
         NRF_PPI->CHENCLR = PPI_CHEN_CH23_Msk;
         NRF_AAR->IRKPTR = (uint32_t)&g_nrf_irk_list[0];
 #endif
-        dptr = (uint8_t *)&g_ble_phy_txrx_buf[0];
+        dptr = (uint8_t *)&g_ble_phy_tx_buf[0];
+        ++dptr;
+        pktptr = dptr;
     }
 #else
 #if (BLE_LL_CFG_FEAT_LL_PRIVACY == 1)
     NRF_PPI->CHENCLR = PPI_CHEN_CH23_Msk;
 #endif
-    dptr = (uint8_t *)&g_ble_phy_txrx_buf[0];
+    dptr = (uint8_t *)&g_ble_phy_tx_buf[0];
+    ++dptr;
+    pktptr = dptr;
 #endif
 
     /* RAM representation has S0, LENGTH and S1 fields. (3 bytes) */
@@ -857,7 +937,7 @@ ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans)
     dptr[1] = payload_len;
     dptr[2] = 0;
     dptr += 3;
-    NRF_RADIO->PACKETPTR = (uint32_t)&g_ble_phy_txrx_buf[0];
+    NRF_RADIO->PACKETPTR = (uint32_t)pktptr;
 
     /* Clear the ready, end and disabled events */
     NRF_RADIO->EVENTS_READY = 0;
@@ -867,13 +947,10 @@ ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans)
     /* Enable shortcuts for transmit start/end. */
     shortcuts = RADIO_SHORTS_END_DISABLE_Msk | RADIO_SHORTS_READY_START_Msk;
     if (end_trans == BLE_PHY_TRANSITION_TX_RX) {
-        /* If we are going into receive after this, try to get a buffer. */
-        if (ble_phy_rxpdu_get()) {
-            shortcuts |= RADIO_SHORTS_DISABLED_RXEN_Msk;
-        }
+        shortcuts |= RADIO_SHORTS_DISABLED_RXEN_Msk;
     }
-    NRF_RADIO->INTENSET = RADIO_INTENSET_DISABLED_Msk;
     NRF_RADIO->SHORTS = shortcuts;
+    NRF_RADIO->INTENSET = RADIO_INTENSET_DISABLED_Msk;
 
     /* Set transmitted payload length */
     g_ble_phy_data.phy_tx_pyld_len = payload_len;

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/580f5b6d/net/nimble/include/nimble/nimble_opt.h
----------------------------------------------------------------------
diff --git a/net/nimble/include/nimble/nimble_opt.h b/net/nimble/include/nimble/nimble_opt.h
index 319c08d..2fd8228 100644
--- a/net/nimble/include/nimble/nimble_opt.h
+++ b/net/nimble/include/nimble/nimble_opt.h
@@ -355,9 +355,7 @@
 #endif
 
 /*
- * This option allows a controller to send/receive LE pings. Currently,
- * this feature is not implemented by the controller so turning it on or off
- * has no effect.
+ * This option allows a controller to send/receive LE pings.
  */
 #ifndef BLE_LL_CFG_FEAT_LE_PING
 #define  BLE_LL_CFG_FEAT_LE_PING                (1)


[09/10] incubator-mynewt-core git commit: MYNEWT-358: nrf51 cannot connect to directed advertisers w/privacy

Posted by we...@apache.org.
MYNEWT-358: nrf51 cannot connect to directed advertisers w/privacy

In order to fix this issue I have added the local RPA to the resolving list and
modified the code so that the RPA timer is a true LL timer that will be used
to regenerate local RPAs at the specified timeout. This allows the local RPA
to be generated early and not during an IFS interval


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/726a600c
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/726a600c
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/726a600c

Branch: refs/heads/develop
Commit: 726a600cd594f7c6ae6092a3df58d469178806aa
Parents: a955c2f
Author: William San Filippo <wi...@runtime.io>
Authored: Thu Aug 11 14:19:56 2016 -0700
Committer: William San Filippo <wi...@runtime.io>
Committed: Thu Aug 11 17:49:46 2016 -0700

----------------------------------------------------------------------
 .../include/controller/ble_ll_resolv.h          |   7 +-
 net/nimble/controller/src/ble_ll_adv.c          |  17 +++
 net/nimble/controller/src/ble_ll_conn.c         |   1 +
 net/nimble/controller/src/ble_ll_resolv.c       | 150 +++++++++++++++----
 net/nimble/controller/src/ble_ll_scan.c         |   2 +-
 5 files changed, 142 insertions(+), 35 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/726a600c/net/nimble/controller/include/controller/ble_ll_resolv.h
----------------------------------------------------------------------
diff --git a/net/nimble/controller/include/controller/ble_ll_resolv.h b/net/nimble/controller/include/controller/ble_ll_resolv.h
index 251543b..6c63c79 100644
--- a/net/nimble/controller/include/controller/ble_ll_resolv.h
+++ b/net/nimble/controller/include/controller/ble_ll_resolv.h
@@ -23,15 +23,18 @@
 /*
  * An entry in the resolving list.
  *      The identity address is stored in little endian format.
+ *      The local rpa is stored in little endian format.
  *      The IRKs are stored in big endian format.
  */
 struct ble_ll_resolv_entry
 {
-    uint8_t rl_reserved;
     uint8_t rl_addr_type;
-    uint8_t rl_identity_addr[BLE_DEV_ADDR_LEN];
+    uint8_t rl_local_rpa_set;
+    uint16_t rl_reserved;
     uint8_t rl_local_irk[16];
     uint8_t rl_peer_irk[16];
+    uint8_t rl_identity_addr[BLE_DEV_ADDR_LEN];
+    uint8_t rl_local_rpa[BLE_DEV_ADDR_LEN];
 };
 
 extern struct ble_ll_resolv_entry g_ble_ll_resolv_list[];

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/726a600c/net/nimble/controller/src/ble_ll_adv.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_adv.c b/net/nimble/controller/src/ble_ll_adv.c
index 1f43a5d..0c6df3b 100644
--- a/net/nimble/controller/src/ble_ll_adv.c
+++ b/net/nimble/controller/src/ble_ll_adv.c
@@ -121,6 +121,23 @@ struct ble_ll_adv_sm g_ble_ll_adv_sm;
 
 
 #if (BLE_LL_CFG_FEAT_LL_PRIVACY == 1)
+/**
+ * Called to change advertisers ADVA and INITA (for directed advertisements)
+ * as an advertiser needs to adhere to the resolvable private address generation
+ * timer.
+ *
+ * NOTE: the resolvable private address code uses its own timer to regenerate
+ * local resolvable private addresses. The advertising code uses its own
+ * timer to reset the INITA (for directed advertisements). This code also sets
+ * the appropriate txadd and rxadd bits that will go into the advertisement.
+ *
+ * Another thing to note: it is possible that an IRK is all zeroes in the
+ * resolving list. That is why we need to check if the generated address is
+ * in fact a RPA as a resolving list entry with all zeroes will use the
+ * identity address (which may be a private address or public).
+ *
+ * @param advsm
+ */
 void
 ble_ll_adv_chk_rpa_timeout(struct ble_ll_adv_sm *advsm)
 {

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/726a600c/net/nimble/controller/src/ble_ll_conn.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_conn.c b/net/nimble/controller/src/ble_ll_conn.c
index bfbdf99..fb95367 100644
--- a/net/nimble/controller/src/ble_ll_conn.c
+++ b/net/nimble/controller/src/ble_ll_conn.c
@@ -1904,6 +1904,7 @@ ble_ll_conn_event_end(void *arg)
      * The way this works is that whenever the timer expires it just gets reset
      * and we send the autheticated payload timeout event. Note that this timer
      * should run even when encryption is paused.
+     * XXX: what should be here? Was there code here that got deleted?
      */
 #endif
 

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/726a600c/net/nimble/controller/src/ble_ll_resolv.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_resolv.c b/net/nimble/controller/src/ble_ll_resolv.c
index b4d58b0..903c95f 100644
--- a/net/nimble/controller/src/ble_ll_resolv.c
+++ b/net/nimble/controller/src/ble_ll_resolv.c
@@ -31,12 +31,15 @@
 #include "ble_ll_conn_priv.h"
 
 #if (BLE_LL_CFG_FEAT_LL_PRIVACY == 1)
-
-/* Flag denoting whether or not address translation is enabled. */
-uint8_t g_ble_ll_addr_res_enabled;
-uint8_t g_ble_ll_resolv_list_size;
-uint8_t g_ble_ll_resolv_list_cnt;
-uint32_t g_ble_ll_resolv_rpa_tmo;
+struct ble_ll_resolv_data
+{
+    uint8_t addr_res_enabled;
+    uint8_t rl_size;
+    uint8_t rl_cnt;
+    uint32_t rpa_tmo;
+    struct os_callout_func rpa_timer;
+};
+struct ble_ll_resolv_data g_ble_ll_resolv_data;
 
 struct ble_ll_resolv_entry g_ble_ll_resolv_list[NIMBLE_OPT_LL_RESOLV_LIST_SIZE];
 
@@ -53,9 +56,9 @@ ble_ll_resolv_list_chg_allowed(void)
 {
     int rc;
 
-    if (g_ble_ll_addr_res_enabled && (ble_ll_adv_enabled()  ||
-                                      ble_ll_scan_enabled() ||
-                                      g_ble_ll_conn_create_sm)) {
+    if (g_ble_ll_resolv_data.addr_res_enabled &&
+            (ble_ll_adv_enabled() || ble_ll_scan_enabled() ||
+             g_ble_ll_conn_create_sm)) {
         rc = 0;
     } else {
         rc = 1;
@@ -64,6 +67,32 @@ ble_ll_resolv_list_chg_allowed(void)
 }
 
 /**
+ * Called when the Resolvable private address timer expires. This timer
+ * is used to regenerate local RPA's in the resolving list.
+ *
+ * @param arg
+ */
+void
+ble_ll_resolv_rpa_timer_cb(void *arg)
+{
+    int i;
+    os_sr_t sr;
+    struct ble_ll_resolv_entry *rl;
+
+    rl = &g_ble_ll_resolv_list[0];
+    for (i = 0; i < g_ble_ll_resolv_data.rl_cnt; ++i) {
+        OS_ENTER_CRITICAL(sr);
+        rl->rl_local_rpa_set = 0;
+        ble_ll_resolv_gen_priv_addr(rl, 1, rl->rl_local_rpa);
+        rl->rl_local_rpa_set = 1;
+        OS_EXIT_CRITICAL(sr);
+        ++rl;
+    }
+    os_callout_reset(&g_ble_ll_resolv_data.rpa_timer.cf_c,
+                     (int32_t)g_ble_ll_resolv_data.rpa_tmo);
+}
+
+/**
  * Called to determine if the IRK is all zero.
  *
  * @param irk
@@ -102,7 +131,7 @@ ble_ll_resolv_list_clr(void)
     }
 
     /* Sets total on list to 0. Clears HW resolve list */
-    g_ble_ll_resolv_list_cnt = 0;
+    g_ble_ll_resolv_data.rl_cnt = 0;
     ble_hw_resolv_list_clear();
 
     return BLE_ERR_SUCCESS;
@@ -119,7 +148,7 @@ ble_ll_resolv_list_clr(void)
 int
 ble_ll_resolv_list_read_size(uint8_t *rspbuf, uint8_t *rsplen)
 {
-    rspbuf[0] = g_ble_ll_resolv_list_size;
+    rspbuf[0] = g_ble_ll_resolv_data.rl_size;
     *rsplen = 1;
     return BLE_ERR_SUCCESS;
 }
@@ -141,7 +170,7 @@ ble_ll_is_on_resolv_list(uint8_t *addr, uint8_t addr_type)
     struct ble_ll_resolv_entry *rl;
 
     rl = &g_ble_ll_resolv_list[0];
-    for (i = 0; i < g_ble_ll_resolv_list_cnt; ++i) {
+    for (i = 0; i < g_ble_ll_resolv_data.rl_cnt; ++i) {
         if ((rl->rl_addr_type == addr_type) &&
             (!memcmp(&rl->rl_identity_addr[0], addr, BLE_DEV_ADDR_LEN))) {
             return i + 1;
@@ -167,7 +196,7 @@ ble_ll_resolv_list_find(uint8_t *addr, uint8_t addr_type)
     struct ble_ll_resolv_entry *rl;
 
     rl = &g_ble_ll_resolv_list[0];
-    for (i = 0; i < g_ble_ll_resolv_list_cnt; ++i) {
+    for (i = 0; i < g_ble_ll_resolv_data.rl_cnt; ++i) {
         if ((rl->rl_addr_type == addr_type) &&
             (!memcmp(&rl->rl_identity_addr[0], addr, BLE_DEV_ADDR_LEN))) {
             return rl;
@@ -197,7 +226,7 @@ ble_ll_resolv_list_add(uint8_t *cmdbuf)
     }
 
     /* Check if we have any open entries */
-    if (g_ble_ll_resolv_list_cnt >= g_ble_ll_resolv_list_size) {
+    if (g_ble_ll_resolv_data.rl_cnt >= g_ble_ll_resolv_data.rl_size) {
         return BLE_ERR_MEM_CAPACITY;
     }
 
@@ -206,14 +235,23 @@ ble_ll_resolv_list_add(uint8_t *cmdbuf)
 
     rc = BLE_ERR_SUCCESS;
     if (!ble_ll_is_on_resolv_list(ident_addr, addr_type)) {
-        rl = &g_ble_ll_resolv_list[g_ble_ll_resolv_list_cnt];
+        rl = &g_ble_ll_resolv_list[g_ble_ll_resolv_data.rl_cnt];
         rl->rl_addr_type = addr_type;
+        rl->rl_local_rpa_set = 0;
         memcpy(&rl->rl_identity_addr[0], ident_addr, BLE_DEV_ADDR_LEN);
         swap_buf(rl->rl_peer_irk, cmdbuf + 7, 16);
         swap_buf(rl->rl_local_irk, cmdbuf + 23, 16);
-        ++g_ble_ll_resolv_list_cnt;
 
+        /*
+         * Add peer IRK to HW resolving list. If we can add it, also
+         * generate a local RPA now to save time later.
+         */
         rc = ble_hw_resolv_list_add(rl->rl_peer_irk);
+        if (!rc) {
+            ble_ll_resolv_gen_priv_addr(rl, 1, rl->rl_local_rpa);
+            rl->rl_local_rpa_set = 1;
+        }
+        ++g_ble_ll_resolv_data.rl_cnt;
     }
 
     return rc;
@@ -243,11 +281,11 @@ ble_ll_resolv_list_rmv(uint8_t *cmdbuf)
 
     /* Remove from IRK records */
     position = ble_ll_is_on_resolv_list(ident_addr, addr_type);
-    if (position && (position < g_ble_ll_resolv_list_cnt)) {
+    if (position && (position < g_ble_ll_resolv_data.rl_cnt)) {
         memmove(&g_ble_ll_resolv_list[position - 1],
                 &g_ble_ll_resolv_list[position],
-                g_ble_ll_resolv_list_cnt - position);
-        --g_ble_ll_resolv_list_cnt;
+                g_ble_ll_resolv_data.rl_cnt - position);
+        --g_ble_ll_resolv_data.rl_cnt;
 
         /* Remove from HW list */
         ble_hw_resolv_list_rmv(position - 1);
@@ -267,13 +305,29 @@ int
 ble_ll_resolv_enable_cmd(uint8_t *cmdbuf)
 {
     int rc;
+    int32_t tmo;
+    uint8_t enabled;
 
     if (ble_ll_adv_enabled() || ble_ll_scan_enabled() ||
         g_ble_ll_conn_create_sm) {
         rc = BLE_ERR_CMD_DISALLOWED;
     } else {
-        g_ble_ll_addr_res_enabled = cmdbuf[0];
-        rc = BLE_ERR_SUCCESS;
+        enabled = cmdbuf[0];
+        if (enabled <= 1) {
+            /* If we change state, we need to disable/enable the RPA timer */
+            if ((enabled ^ g_ble_ll_resolv_data.addr_res_enabled) != 0) {
+                if (enabled) {
+                    tmo = (int32_t)g_ble_ll_resolv_data.rpa_tmo;
+                    os_callout_reset(&g_ble_ll_resolv_data.rpa_timer.cf_c, tmo);
+                } else {
+                    os_callout_stop(&g_ble_ll_resolv_data.rpa_timer.cf_c);
+                }
+                g_ble_ll_resolv_data.addr_res_enabled = enabled;
+            }
+            rc = BLE_ERR_SUCCESS;
+        } else {
+            rc = BLE_ERR_INV_HCI_CMD_PARMS;
+        }
     }
 
     return rc;
@@ -306,7 +360,11 @@ ble_ll_resolv_set_rpa_tmo(uint8_t *cmdbuf)
 
     tmo_secs = le16toh(cmdbuf);
     if ((tmo_secs > 0) && (tmo_secs <= 0xA1B8)) {
-        g_ble_ll_resolv_rpa_tmo = tmo_secs * OS_TICKS_PER_SEC;
+        g_ble_ll_resolv_data.rpa_tmo = tmo_secs * OS_TICKS_PER_SEC;
+        if (g_ble_ll_resolv_data.addr_res_enabled) {
+            os_callout_reset(&g_ble_ll_resolv_data.rpa_timer.cf_c,
+                             (int32_t)g_ble_ll_resolv_data.rpa_tmo);
+        }
     } else {
         rc = BLE_ERR_INV_HCI_CMD_PARMS;
     }
@@ -323,12 +381,11 @@ ble_ll_resolv_set_rpa_tmo(uint8_t *cmdbuf)
 uint32_t
 ble_ll_resolv_get_rpa_tmo(void)
 {
-    return g_ble_ll_resolv_rpa_tmo;
+    return g_ble_ll_resolv_data.rpa_tmo;
 }
 
 /**
- * Called the generate a resolvable private address
- *
+ * Called to generate a resolvable private address
  *
  * @param rl
  * @param local
@@ -348,6 +405,12 @@ ble_ll_resolv_gen_priv_addr(struct ble_ll_resolv_entry *rl, int local,
     assert(rl != NULL);
     assert(addr != NULL);
 
+    /* If the local rpa has already been generated, just copy it */
+    if (local && rl->rl_local_rpa_set) {
+        memcpy(addr, rl->rl_local_rpa, BLE_DEV_ADDR_LEN);
+        return;
+    }
+
     /* Get prand */
     prand = addr + 3;
     ble_ll_rand_prand_get(prand);
@@ -427,11 +490,29 @@ int
 ble_ll_resolv_rpa(uint8_t *rpa, uint8_t *irk)
 {
     int rc;
+    uint32_t *irk32;
+    uint32_t *key32;
+    uint32_t *pt32;
     struct ble_encryption_block ecb;
 
-    memcpy(ecb.key, irk, BLE_ENC_BLOCK_SIZE);
-    memset(ecb.plain_text, 0, BLE_ENC_BLOCK_SIZE);
-    swap_buf(&ecb.plain_text[13], rpa + 3, 3);
+    irk32 = (uint32_t *)irk;
+    key32 = (uint32_t *)&ecb.key[0];
+
+    key32[0] = irk32[0];
+    key32[1] = irk32[1];
+    key32[2] = irk32[2];
+    key32[3] = irk32[3];
+
+    pt32 = (uint32_t *)&ecb.plain_text[0];
+    pt32[0] = 0;
+    pt32[1] = 0;
+    pt32[2] = 0;
+    pt32[3] = 0;
+
+    ecb.plain_text[15] = rpa[3];
+    ecb.plain_text[14] = rpa[4];
+    ecb.plain_text[13] = rpa[5];
+
     ble_hw_encrypt_block(&ecb);
     if ((ecb.cipher_text[15] == rpa[0]) && (ecb.cipher_text[14] == rpa[1]) &&
         (ecb.cipher_text[13] == rpa[2])) {
@@ -451,7 +532,7 @@ ble_ll_resolv_rpa(uint8_t *rpa, uint8_t *irk)
 uint8_t
 ble_ll_resolv_enabled(void)
 {
-    return g_ble_ll_addr_res_enabled;
+    return g_ble_ll_resolv_data.addr_res_enabled;
 }
 
 /**
@@ -460,7 +541,8 @@ ble_ll_resolv_enabled(void)
 void
 ble_ll_resolv_list_reset(void)
 {
-    g_ble_ll_addr_res_enabled = 0;
+    g_ble_ll_resolv_data.addr_res_enabled = 0;
+    os_callout_stop(&g_ble_ll_resolv_data.rpa_timer.cf_c);
     ble_ll_resolv_list_clr();
     ble_ll_resolv_init();
 }
@@ -471,14 +553,18 @@ ble_ll_resolv_init(void)
     uint8_t hw_size;
 
     /* Default is 15 minutes */
-    g_ble_ll_resolv_rpa_tmo = 15 * 60 * OS_TICKS_PER_SEC;
+    g_ble_ll_resolv_data.rpa_tmo = 15 * 60 * OS_TICKS_PER_SEC;
 
     hw_size = ble_hw_resolv_list_size();
     if (hw_size > NIMBLE_OPT_LL_RESOLV_LIST_SIZE) {
         hw_size = NIMBLE_OPT_LL_RESOLV_LIST_SIZE;
     }
-    g_ble_ll_resolv_list_size = hw_size;
+    g_ble_ll_resolv_data.rl_size = hw_size;
 
+    os_callout_func_init(&g_ble_ll_resolv_data.rpa_timer,
+                         &g_ble_ll_data.ll_evq,
+                         ble_ll_resolv_rpa_timer_cb,
+                         NULL);
 }
 
 #endif  /* if BLE_LL_CFG_FEAT_LL_PRIVACY == 1 */

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/726a600c/net/nimble/controller/src/ble_ll_scan.c
----------------------------------------------------------------------
diff --git a/net/nimble/controller/src/ble_ll_scan.c b/net/nimble/controller/src/ble_ll_scan.c
index 0fc4e79..29193dc 100644
--- a/net/nimble/controller/src/ble_ll_scan.c
+++ b/net/nimble/controller/src/ble_ll_scan.c
@@ -448,7 +448,7 @@ ble_ll_hci_send_adv_report(uint8_t pdu_type, uint8_t txadd, uint8_t *rxbuf,
                  * are 2 greater than the unresolved ones in the spec, so
                  * we just add 2 here.
                  */
-                addr_type += 2;
+                addr_type = g_ble_ll_resolv_list[index].rl_addr_type + 2;
             } else{
                 adv_addr = rxbuf;
             }


[07/10] incubator-mynewt-core git commit: BLE apps - Update for latest HCI transport changes

Posted by we...@apache.org.
BLE apps - Update for latest HCI transport changes


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/50d00eb8
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/50d00eb8
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/50d00eb8

Branch: refs/heads/develop
Commit: 50d00eb80ba1bc21986753480c282ecc17e08e38
Parents: 70f4ec7
Author: Christopher Collins <cc...@apache.org>
Authored: Thu Aug 4 16:31:33 2016 -0700
Committer: William San Filippo <wi...@runtime.io>
Committed: Thu Aug 11 17:49:45 2016 -0700

----------------------------------------------------------------------
 apps/bleprph/src/main.c | 3 ---
 apps/bletest/src/main.c | 2 ++
 2 files changed, 2 insertions(+), 3 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/50d00eb8/apps/bleprph/src/main.c
----------------------------------------------------------------------
diff --git a/apps/bleprph/src/main.c b/apps/bleprph/src/main.c
index d2ded46..b08b077 100755
--- a/apps/bleprph/src/main.c
+++ b/apps/bleprph/src/main.c
@@ -426,9 +426,6 @@ main(void)
     rc = ble_hs_init(&bleprph_evq, &cfg);
     assert(rc == 0);
 
-    rc = ble_hci_ram_init(&ble_hci_ram_cfg_dflt);
-    assert(rc == 0);
-
     nmgr_task_init(NEWTMGR_TASK_PRIO, newtmgr_stack, NEWTMGR_TASK_STACK_SIZE);
     imgmgr_module_init();
 

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/50d00eb8/apps/bletest/src/main.c
----------------------------------------------------------------------
diff --git a/apps/bletest/src/main.c b/apps/bletest/src/main.c
index 94def1f..5dd0cde 100755
--- a/apps/bletest/src/main.c
+++ b/apps/bletest/src/main.c
@@ -44,6 +44,8 @@
 #include "controller/ble_ll_conn.h"
 #include "controller/ble_ll_scan.h"
 #include "controller/ble_ll_adv.h"
+
+/* RAM HCI transport. */
 #include "transport/ram/ble_hci_ram.h"
 
 /* RAM HCI transport. */


[06/10] incubator-mynewt-core git commit: Fix incorrect handling of multiple connections and starting encrypted links with all of them

Posted by we...@apache.org.
Fix incorrect handling of multiple connections and starting encrypted links with all of them


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/a955c2f9
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/a955c2f9
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/a955c2f9

Branch: refs/heads/develop
Commit: a955c2f9ec9b88293ccbffddc46dfa14e0b6d778
Parents: 22fe6f2
Author: William San Filippo <wi...@runtime.io>
Authored: Tue Aug 9 15:51:01 2016 -0700
Committer: William San Filippo <wi...@runtime.io>
Committed: Thu Aug 11 17:49:45 2016 -0700

----------------------------------------------------------------------
 apps/bletest/src/bletest_hci.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/a955c2f9/apps/bletest/src/bletest_hci.c
----------------------------------------------------------------------
diff --git a/apps/bletest/src/bletest_hci.c b/apps/bletest/src/bletest_hci.c
index 64d0270..354b568 100755
--- a/apps/bletest/src/bletest_hci.c
+++ b/apps/bletest/src/bletest_hci.c
@@ -63,7 +63,7 @@ bletest_send_conn_update(uint16_t handle)
 void
 bletest_ltk_req_reply(uint16_t handle)
 {
-    g_bletest_ltk_reply_handle = handle;
+    g_bletest_ltk_reply_handle |= (1 << (handle-1));
 }
 
 int


[10/10] incubator-mynewt-core git commit: Use new acl data tx routine

Posted by we...@apache.org.
Use new acl data tx routine


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/5e3595d7
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/5e3595d7
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/5e3595d7

Branch: refs/heads/develop
Commit: 5e3595d7b597bce180edeb96355379384eec3aeb
Parents: 726a600
Author: William San Filippo <wi...@runtime.io>
Authored: Thu Aug 11 15:49:05 2016 -0700
Committer: William San Filippo <wi...@runtime.io>
Committed: Thu Aug 11 17:49:46 2016 -0700

----------------------------------------------------------------------
 apps/bletest/src/main.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/5e3595d7/apps/bletest/src/main.c
----------------------------------------------------------------------
diff --git a/apps/bletest/src/main.c b/apps/bletest/src/main.c
index bfe8d50..b6468a8 100755
--- a/apps/bletest/src/main.c
+++ b/apps/bletest/src/main.c
@@ -781,7 +781,7 @@ bletest_execute_advertiser(void)
 
                         /* Add length */
                         OS_MBUF_PKTHDR(om)->omp_len = om->om_len;
-                        ble_hci_trans_hs_acl_data_send(om);
+                        ble_hci_trans_hs_acl_tx(om);
 
                         /* Increment last handle used */
                         ++g_last_handle_used;


[02/10] incubator-mynewt-core git commit: MYNEWT-83: use fixed buffer for reception. Get native arch building

Posted by we...@apache.org.
MYNEWT-83: use fixed buffer for reception. Get native arch building


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/7c8cca9f
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/7c8cca9f
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/7c8cca9f

Branch: refs/heads/develop
Commit: 7c8cca9f88ebf86717b2941c4484065ffb2a2438
Parents: 580f5b6
Author: William San Filippo <wi...@runtime.io>
Authored: Mon Jul 25 10:06:41 2016 -0700
Committer: William San Filippo <wi...@runtime.io>
Committed: Thu Aug 11 17:38:54 2016 -0700

----------------------------------------------------------------------
 net/nimble/drivers/native/src/ble_phy.c | 184 +++++++++++++++++++++------
 1 file changed, 142 insertions(+), 42 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/7c8cca9f/net/nimble/drivers/native/src/ble_phy.c
----------------------------------------------------------------------
diff --git a/net/nimble/drivers/native/src/ble_phy.c b/net/nimble/drivers/native/src/ble_phy.c
index e2c9f25..4eb5d97 100644
--- a/net/nimble/drivers/native/src/ble_phy.c
+++ b/net/nimble/drivers/native/src/ble_phy.c
@@ -18,24 +18,32 @@
  */
 
 #include <stdint.h>
+#include <string.h>
 #include <assert.h>
 #include "os/os.h"
-#include "nimble/ble.h"             /* XXX: needed for ble mbuf header.*/
+#include "ble/xcvr.h"
+#include "nimble/ble.h"
+#include "nimble/nimble_opt.h"
 #include "controller/ble_phy.h"
 #include "controller/ble_ll.h"
 
 /* BLE PHY data structure */
 struct ble_phy_obj
 {
+    uint8_t phy_stats_initialized;
     int8_t  phy_txpwr_dbm;
     uint8_t phy_chan;
     uint8_t phy_state;
     uint8_t phy_transition;
     uint8_t phy_rx_started;
+    uint8_t phy_encrypted;
     uint8_t phy_privacy;
+    uint8_t phy_tx_pyld_len;
+    uint32_t phy_aar_scratch;
     uint32_t phy_access_address;
-    struct os_mbuf *rxpdu;
+    struct ble_mbuf_hdr rxhdr;
     void *txend_arg;
+    uint8_t *rxdptr;
     ble_phy_tx_end_func txend_cb;
 };
 struct ble_phy_obj g_ble_phy_data;
@@ -75,6 +83,42 @@ static struct xcvr_data g_xcvr_data;
 #define BLE_XCVR_TX_PWR_MAX_DBM     (30)
 #define BLE_XCVR_TX_PWR_MIN_DBM     (-20)
 
+/* Statistics */
+STATS_SECT_START(ble_phy_stats)
+    STATS_SECT_ENTRY(phy_isrs)
+    STATS_SECT_ENTRY(tx_good)
+    STATS_SECT_ENTRY(tx_fail)
+    STATS_SECT_ENTRY(tx_late)
+    STATS_SECT_ENTRY(tx_bytes)
+    STATS_SECT_ENTRY(rx_starts)
+    STATS_SECT_ENTRY(rx_aborts)
+    STATS_SECT_ENTRY(rx_valid)
+    STATS_SECT_ENTRY(rx_crc_err)
+    STATS_SECT_ENTRY(rx_late)
+    STATS_SECT_ENTRY(no_bufs)
+    STATS_SECT_ENTRY(radio_state_errs)
+    STATS_SECT_ENTRY(rx_hw_err)
+    STATS_SECT_ENTRY(tx_hw_err)
+STATS_SECT_END
+STATS_SECT_DECL(ble_phy_stats) ble_phy_stats;
+
+STATS_NAME_START(ble_phy_stats)
+    STATS_NAME(ble_phy_stats, phy_isrs)
+    STATS_NAME(ble_phy_stats, tx_good)
+    STATS_NAME(ble_phy_stats, tx_fail)
+    STATS_NAME(ble_phy_stats, tx_late)
+    STATS_NAME(ble_phy_stats, tx_bytes)
+    STATS_NAME(ble_phy_stats, rx_starts)
+    STATS_NAME(ble_phy_stats, rx_aborts)
+    STATS_NAME(ble_phy_stats, rx_valid)
+    STATS_NAME(ble_phy_stats, rx_crc_err)
+    STATS_NAME(ble_phy_stats, rx_late)
+    STATS_NAME(ble_phy_stats, no_bufs)
+    STATS_NAME(ble_phy_stats, radio_state_errs)
+    STATS_NAME(ble_phy_stats, rx_hw_err)
+    STATS_NAME(ble_phy_stats, tx_hw_err)
+STATS_NAME_END(ble_phy_stats)
+
 /* XXX: TODO:
 
  * 1) Test the following to make sure it works: suppose an event is already
@@ -95,28 +139,104 @@ ble_xcvr_clear_irq(uint32_t mask)
 }
 
 /**
- * ble phy rxpdu get
+ * Copies the data from the phy receive buffer into a mbuf chain.
+ *
  *
- * Gets a mbuf for PDU reception.
+ * @param dptr Pointer to receive buffer
+ * @param len Length of receive buffer to copy.
  *
- * @return struct os_mbuf* Pointer to retrieved mbuf or NULL if none available
+ * @return struct os_mbuf* Pointer to mbuf. NULL if no mbuf available.
  */
-static struct os_mbuf *
-ble_phy_rxpdu_get(void)
+struct os_mbuf *
+ble_phy_rxpdu_get(uint8_t *dptr, uint16_t len)
 {
+    uint16_t rem_bytes;
+    uint16_t mb_bytes;
+    uint16_t copylen;
+    uint32_t *dst;
+    uint32_t *src;
     struct os_mbuf *m;
+    struct os_mbuf *n;
+    struct os_mbuf *p;
+    struct ble_mbuf_hdr *ble_hdr;
+    struct os_mbuf_pkthdr *pkthdr;
 
-    m = g_ble_phy_data.rxpdu;
-    if (m == NULL) {
-        m = os_msys_get_pkthdr(BLE_MBUF_PAYLOAD_SIZE, sizeof(struct ble_mbuf_hdr));
-        if (!m) {
-            ++g_ble_phy_stats.no_bufs;
-        } else {
-            g_ble_phy_data.rxpdu = m;
+    /* Better be aligned */
+    assert(((uint32_t)dptr & 3) == 0);
+
+    p = os_msys_get_pkthdr(len, sizeof(struct ble_mbuf_hdr));
+    if (!p) {
+        STATS_INC(ble_phy_stats, no_bufs);
+        return NULL;
+    }
+
+    /*
+     * Fill in the mbuf pkthdr first. NOTE: first mbuf in chain will have data
+     * pre-pended to it so we adjust m_data by a word.
+     */
+    p->om_data += 4;
+    dst = (uint32_t *)(p->om_data);
+    src = (uint32_t *)dptr;
+
+    rem_bytes = len;
+    mb_bytes = (p->om_omp->omp_databuf_len - p->om_pkthdr_len - 4);
+    copylen = min(mb_bytes, rem_bytes);
+    copylen &= 0xFFFC;
+    rem_bytes -= copylen;
+    mb_bytes -= copylen;
+    p->om_len = copylen;
+    while (copylen > 0) {
+        *dst = *src;
+        ++dst;
+        ++src;
+        copylen -= 4;
+    }
+
+    /* Copy remaining bytes */
+    m = p;
+    while (rem_bytes > 0) {
+        /* If there are enough bytes in the mbuf, copy them and leave */
+        if (rem_bytes <= mb_bytes) {
+            memcpy(m->om_data + m->om_len, src, rem_bytes);
+            m->om_len += rem_bytes;
+            break;
+        }
+
+        n = os_msys_get(rem_bytes, 0);
+        if (!n) {
+            os_mbuf_free_chain(p);
+            STATS_INC(ble_phy_stats, no_bufs);
+            return NULL;
+        }
+
+        /* Chain new mbuf to existing chain */
+        SLIST_NEXT(m, om_next) = n;
+        m = n;
+
+        mb_bytes = m->om_omp->omp_databuf_len;
+        copylen = min(mb_bytes, rem_bytes);
+        copylen &= 0xFFFC;
+        rem_bytes -= copylen;
+        mb_bytes -= copylen;
+        m->om_len = copylen;
+        dst = (uint32_t *)m->om_data;
+        while (copylen > 0) {
+            *dst = *src;
+            ++dst;
+            ++src;
+            copylen -= 4;
         }
     }
 
-    return m;
+    /* Set packet length */
+    pkthdr = OS_MBUF_PKTHDR(p);
+    pkthdr->omp_len = len;
+
+    /* Copy ble header */
+    ble_hdr = BLE_MBUF_HDR_PTR(p);
+    memcpy(ble_hdr, &g_ble_phy_data.rxhdr, sizeof(struct ble_mbuf_hdr));
+
+    return p;
 }
 
 void
@@ -126,7 +246,6 @@ ble_phy_isr(void)
     uint8_t crcok;
     uint8_t transition;
     uint32_t irq_en;
-    struct os_mbuf *rxpdu;
     struct ble_mbuf_hdr *ble_hdr;
 
     /* Check for disabled event. This only happens for transmits now */
@@ -139,14 +258,9 @@ ble_phy_isr(void)
 
         transition = g_ble_phy_data.phy_transition;
         if (transition == BLE_PHY_TRANSITION_TX_RX) {
-            /* Packet pointer needs to be reset. */
-            if (g_ble_phy_data.rxpdu != NULL) {
-                g_ble_phy_data.phy_state = BLE_PHY_STATE_RX;
-            } else {
-                /* Disable the phy */
-                /* XXX: count no bufs? */
-                ble_phy_disable();
-            }
+            /* Disable the phy */
+            /* XXX: count no bufs? */
+            ble_phy_disable();
         } else {
             /* Better not be going from rx to tx! */
             assert(transition == BLE_PHY_TRANSITION_NONE);
@@ -158,11 +272,9 @@ ble_phy_isr(void)
 
         ble_xcvr_clear_irq(BLE_XCVR_IRQ_F_RX_START);
 
-        /* Better have a PDU! */
-        assert(g_ble_phy_data.rxpdu != NULL);
-
         /* Call Link Layer receive start function */
-        rc = ble_ll_rx_start(g_ble_phy_data.rxpdu, g_ble_phy_data.phy_chan);
+        rc = ble_ll_rx_start(g_ble_phy_data.rxdptr, g_ble_phy_data.phy_chan,
+                             &g_ble_phy_data.rxhdr);
         if (rc >= 0) {
             /* XXX: set rx end enable isr */
         } else {
@@ -182,7 +294,7 @@ ble_phy_isr(void)
         ble_xcvr_clear_irq(BLE_XCVR_IRQ_F_RX_END);
 
         /* Construct BLE header before handing up */
-        ble_hdr = BLE_MBUF_HDR_PTR(g_ble_phy_data.rxpdu);
+        ble_hdr = &g_ble_phy_data.rxhdr;
         ble_hdr->rxinfo.flags = 0;
         ble_hdr->rxinfo.rssi = -77;    /* XXX: dummy rssi */
         ble_hdr->rxinfo.channel = g_ble_phy_data.phy_chan;
@@ -197,9 +309,7 @@ ble_phy_isr(void)
         }
 
         /* Call Link Layer receive payload function */
-        rxpdu = g_ble_phy_data.rxpdu;
-        g_ble_phy_data.rxpdu = NULL;
-        rc = ble_ll_rx_end(rxpdu, ble_hdr);
+        rc = ble_ll_rx_end(g_ble_phy_data.rxdptr, ble_hdr);
         if (rc < 0) {
             /* Disable the PHY. */
             ble_phy_disable();
@@ -239,11 +349,6 @@ ble_phy_rx(void)
         return BLE_PHY_ERR_RADIO_STATE;
     }
 
-    /* If no pdu, get one */
-    if (ble_phy_rxpdu_get() == NULL) {
-        return BLE_PHY_ERR_NO_BUFS;
-    }
-
     g_ble_phy_data.phy_state = BLE_PHY_STATE_RX;
 
     return 0;
@@ -348,11 +453,6 @@ ble_phy_tx(struct os_mbuf *txpdu, uint8_t end_trans)
     }
 
 
-    /* Enable shortcuts for transmit start/end. */
-    if (end_trans == BLE_PHY_TRANSITION_TX_RX) {
-        ble_phy_rxpdu_get();
-    }
-
     /* Set the PHY transition */
     g_ble_phy_data.phy_transition = end_trans;
 


[05/10] incubator-mynewt-core git commit: Update sample BLE apps to use transports.

Posted by we...@apache.org.
Update sample BLE apps to use transports.


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/70f4ec7a
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/70f4ec7a
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/70f4ec7a

Branch: refs/heads/develop
Commit: 70f4ec7a1f2d3942100d66fa0e8023af8a66203c
Parents: ea5736e
Author: Christopher Collins <cc...@apache.org>
Authored: Wed Aug 3 19:43:50 2016 -0700
Committer: William San Filippo <wi...@runtime.io>
Committed: Thu Aug 11 17:45:48 2016 -0700

----------------------------------------------------------------------
 apps/blecent/src/main.c | 2 +-
 apps/bleprph/src/main.c | 3 +++
 apps/bletest/src/main.c | 1 +
 3 files changed, 5 insertions(+), 1 deletion(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/70f4ec7a/apps/blecent/src/main.c
----------------------------------------------------------------------
diff --git a/apps/blecent/src/main.c b/apps/blecent/src/main.c
index d5f47e6..384338a 100755
--- a/apps/blecent/src/main.c
+++ b/apps/blecent/src/main.c
@@ -184,7 +184,7 @@ blecent_read_write_subscribe(const struct peer *peer)
 
     value[0] = 99;
     value[1] = 100;
-    rc = ble_gattc_write_flat(peer->conn_handle, chr->chr.val_handle, 
+    rc = ble_gattc_write_flat(peer->conn_handle, chr->chr.val_handle,
                               value, sizeof value, blecent_on_write, NULL);
     if (rc != 0) {
         BLECENT_LOG(ERROR, "Error: Failed to write characteristic; rc=%d\n",

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/70f4ec7a/apps/bleprph/src/main.c
----------------------------------------------------------------------
diff --git a/apps/bleprph/src/main.c b/apps/bleprph/src/main.c
index b08b077..d2ded46 100755
--- a/apps/bleprph/src/main.c
+++ b/apps/bleprph/src/main.c
@@ -426,6 +426,9 @@ main(void)
     rc = ble_hs_init(&bleprph_evq, &cfg);
     assert(rc == 0);
 
+    rc = ble_hci_ram_init(&ble_hci_ram_cfg_dflt);
+    assert(rc == 0);
+
     nmgr_task_init(NEWTMGR_TASK_PRIO, newtmgr_stack, NEWTMGR_TASK_STACK_SIZE);
     imgmgr_module_init();
 

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/70f4ec7a/apps/bletest/src/main.c
----------------------------------------------------------------------
diff --git a/apps/bletest/src/main.c b/apps/bletest/src/main.c
index c2635dd..94def1f 100755
--- a/apps/bletest/src/main.c
+++ b/apps/bletest/src/main.c
@@ -44,6 +44,7 @@
 #include "controller/ble_ll_conn.h"
 #include "controller/ble_ll_scan.h"
 #include "controller/ble_ll_adv.h"
+#include "transport/ram/ble_hci_ram.h"
 
 /* RAM HCI transport. */
 #include "transport/ram/ble_hci_ram.h"