You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mynewt.apache.org by cc...@apache.org on 2016/06/15 02:27:28 UTC

[06/50] [abbrv] incubator-mynewt-core git commit: BLE Host - Fix privacy+pairing bug.

BLE Host - Fix privacy+pairing bug.

We were still not using the correct address types and adresses in the
cryptographic functions when privacy was in effect.  All crypto
functions now use:
    * identity address type
    * effective address (RPA if privacy in use; else identity addr).


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/eb177946
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/eb177946
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/eb177946

Branch: refs/heads/develop
Commit: eb177946f0fa7b80eaf67fda60639c1fe88a1efd
Parents: be5a985
Author: Christopher Collins <cc...@apache.org>
Authored: Wed Jun 8 05:50:16 2016 +0800
Committer: Christopher Collins <cc...@apache.org>
Committed: Tue Jun 14 19:23:34 2016 -0700

----------------------------------------------------------------------
 net/nimble/host/src/ble_gap.c          |   2 +-
 net/nimble/host/src/ble_hs_conn.c      | 111 ++++++++++++++++++++--------
 net/nimble/host/src/ble_hs_conn_priv.h |  14 +++-
 net/nimble/host/src/ble_sm.c           |  30 +++++---
 net/nimble/host/src/ble_sm_alg.c       |   3 +
 net/nimble/host/src/ble_sm_lgcy.c      |   2 +-
 net/nimble/host/src/ble_sm_priv.h      |   3 +-
 net/nimble/host/src/ble_sm_sc.c        |  66 ++++++++++++-----
 8 files changed, 164 insertions(+), 67 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/eb177946/net/nimble/host/src/ble_gap.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_gap.c b/net/nimble/host/src/ble_gap.c
index 795b2ec..a54042f 100644
--- a/net/nimble/host/src/ble_gap.c
+++ b/net/nimble/host/src/ble_gap.c
@@ -917,7 +917,7 @@ ble_gap_rx_conn_complete(struct hci_le_conn_complete *evt)
     }
 
     memcpy(conn->our_rpa_addr, evt->local_rpa, 6);
-    memcpy(conn->peer_rpa_addr, evt->local_rpa, 6);
+    memcpy(conn->peer_rpa_addr, evt->peer_rpa, 6);
 
     ble_gap_conn_to_snapshot(conn, &snap);
 

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/eb177946/net/nimble/host/src/ble_hs_conn.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_hs_conn.c b/net/nimble/host/src/ble_hs_conn.c
index 84081b4..07550ec 100644
--- a/net/nimble/host/src/ble_hs_conn.c
+++ b/net/nimble/host/src/ble_hs_conn.c
@@ -316,52 +316,101 @@ ble_hs_conn_first(void)
 }
 
 void
-ble_hs_conn_peer_effective_addr(struct ble_hs_conn *conn, uint8_t *out_addr)
+ble_hs_conn_addrs(struct ble_hs_conn *conn,
+                  uint8_t *out_our_effective_addr_type,
+                  uint8_t **out_our_effective_addr,
+                  uint8_t *out_our_identity_addr_type,
+                  uint8_t **out_our_identity_addr,
+                  uint8_t *out_peer_effective_addr_type,
+                  uint8_t **out_peer_effective_addr,
+                  uint8_t *out_peer_identity_addr_type,
+                  uint8_t **out_peer_identity_addr)
 {
+
+    uint8_t peer_effective_addr_type;
+    uint8_t peer_identity_addr_type;
+    uint8_t our_effective_addr_type;
+    uint8_t our_identity_addr_type;
+    uint8_t *peer_effective_addr;
+    uint8_t *peer_identity_addr;
+    uint8_t *our_effective_addr;
+    uint8_t *our_identity_addr;
+
+    /* Determine our address information. */
+    our_identity_addr =
+        bls_hs_priv_get_local_identity_addr(&our_identity_addr_type);
+    if (memcmp(conn->our_rpa_addr, ble_hs_conn_null_addr, 6) == 0) {
+        our_effective_addr_type = our_identity_addr_type;
+        our_effective_addr = our_identity_addr;
+    } else {
+        switch (our_identity_addr_type) {
+        case BLE_ADDR_TYPE_PUBLIC:
+            our_effective_addr_type = BLE_ADDR_TYPE_RPA_PUB_DEFAULT;
+            break;
+
+        case BLE_ADDR_TYPE_RANDOM:
+            our_effective_addr_type = BLE_ADDR_TYPE_RPA_RND_DEFAULT;
+            break;
+
+        default:
+            BLE_HS_DBG_ASSERT(0);
+        }
+
+        our_effective_addr = conn->our_rpa_addr;
+    }
+
+    /* Determine peer address information. */
+    peer_effective_addr_type = conn->bhc_addr_type;
+    peer_identity_addr = conn->bhc_addr;
     switch (conn->bhc_addr_type) {
     case BLE_ADDR_TYPE_PUBLIC:
+        peer_identity_addr_type = BLE_ADDR_TYPE_PUBLIC;
+        peer_effective_addr = conn->bhc_addr;
+        break;
+
     case BLE_ADDR_TYPE_RANDOM:
-        memcpy(out_addr, conn->bhc_addr, 6);
+        peer_identity_addr_type = BLE_ADDR_TYPE_RANDOM;
+        peer_effective_addr = conn->bhc_addr;
         break;
 
     case BLE_ADDR_TYPE_RPA_PUB_DEFAULT:
+        peer_identity_addr_type = BLE_ADDR_TYPE_PUBLIC;
+        peer_effective_addr = conn->peer_rpa_addr;
+        break;
+
     case BLE_ADDR_TYPE_RPA_RND_DEFAULT:
-        memcpy(out_addr, conn->peer_rpa_addr, 6);
+        peer_identity_addr_type = BLE_ADDR_TYPE_RANDOM;
+        peer_effective_addr = conn->peer_rpa_addr;
         break;
 
     default:
         BLE_HS_DBG_ASSERT(0);
         break;
     }
-}
 
-void
-ble_hs_conn_our_effective_addr(struct ble_hs_conn *conn,
-                               uint8_t *out_addr_type, uint8_t *out_addr)
-{
-    uint8_t ident_addr_type;
-    uint8_t *ident_addr;
-
-    ident_addr = bls_hs_priv_get_local_identity_addr(&ident_addr_type);
-
-    if (memcmp(conn->our_rpa_addr, ble_hs_conn_null_addr, 6) == 0) {
-        *out_addr_type = ident_addr_type;
-        memcpy(out_addr, ident_addr, 6);
-    } else {
-        switch (ident_addr_type) {
-        case BLE_ADDR_TYPE_PUBLIC:
-            *out_addr_type = BLE_ADDR_TYPE_RPA_PUB_DEFAULT;
-            break;
-
-        case BLE_ADDR_TYPE_RANDOM:
-            *out_addr_type = BLE_ADDR_TYPE_RPA_RND_DEFAULT;
-            break;
-
-        default:
-            BLE_HS_DBG_ASSERT(0);
-        }
-
-        memcpy(out_addr, conn->our_rpa_addr, 6);
+    if (out_our_effective_addr_type != NULL) {
+        *out_our_effective_addr_type = our_effective_addr_type;
+    }
+    if (out_our_effective_addr != NULL) {
+        *out_our_effective_addr = our_effective_addr;
+    }
+    if (out_our_identity_addr_type != NULL) {
+        *out_our_identity_addr_type = our_identity_addr_type;
+    }
+    if (out_our_identity_addr != NULL) {
+        *out_our_identity_addr = our_identity_addr;
+    }
+    if (out_peer_effective_addr_type != NULL) {
+        *out_peer_effective_addr_type = peer_effective_addr_type;
+    }
+    if (out_peer_effective_addr != NULL) {
+        *out_peer_effective_addr = peer_effective_addr;
+    }
+    if (out_peer_identity_addr_type != NULL) {
+        *out_peer_identity_addr_type = peer_identity_addr_type;
+    }
+    if (out_peer_identity_addr != NULL) {
+        *out_peer_identity_addr = peer_identity_addr;
     }
 }
 

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/eb177946/net/nimble/host/src/ble_hs_conn_priv.h
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_hs_conn_priv.h b/net/nimble/host/src/ble_hs_conn_priv.h
index 9e3fbf2..1ef4829 100644
--- a/net/nimble/host/src/ble_hs_conn_priv.h
+++ b/net/nimble/host/src/ble_hs_conn_priv.h
@@ -75,10 +75,16 @@ struct ble_l2cap_chan *ble_hs_conn_chan_find(struct ble_hs_conn *conn,
                                              uint16_t cid);
 int ble_hs_conn_chan_insert(struct ble_hs_conn *conn,
                             struct ble_l2cap_chan *chan);
-void ble_hs_conn_peer_effective_addr(struct ble_hs_conn *conn,
-                                     uint8_t *out_addr);
-void ble_hs_conn_our_effective_addr(struct ble_hs_conn *conn,
-                                    uint8_t *out_addr_type, uint8_t *out_addr);
+void ble_hs_conn_addrs(struct ble_hs_conn *conn,
+                       uint8_t *our_effective_addr_type,
+                       uint8_t **our_effective_addr,
+                       uint8_t *our_identity_addr_type,
+                       uint8_t **our_identity_addr,
+                       uint8_t *peer_effective_addr_type,
+                       uint8_t **peer_effective_addr,
+                       uint8_t *peer_identity_addr_type,
+                       uint8_t **peer_identity_addr);
+
 int ble_hs_conn_init(void);
 
 #endif

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/eb177946/net/nimble/host/src/ble_sm.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_sm.c b/net/nimble/host/src/ble_sm.c
index 58cd22a..0f179d2 100644
--- a/net/nimble/host/src/ble_sm.c
+++ b/net/nimble/host/src/ble_sm.c
@@ -516,29 +516,39 @@ ble_sm_peer_addr(struct ble_sm_proc *proc,
 }
 
 int
-ble_sm_addrs(struct ble_sm_proc *proc, uint8_t *out_iat, uint8_t *out_ia,
+ble_sm_ia_ra(struct ble_sm_proc *proc,
+             uint8_t *out_iat, uint8_t *out_ia,
              uint8_t *out_rat, uint8_t *out_ra)
 {
     struct ble_hs_conn *conn;
-    uint8_t our_addr_type;
+    uint8_t *peer_effective_addr;
+    uint8_t *our_effective_addr;
+    uint8_t peer_id_addr_type;
+    uint8_t our_id_addr_type;
 
     conn = ble_hs_conn_find(proc->conn_handle);
     if (conn == NULL) {
         return BLE_HS_ENOTCONN;
     }
 
+    ble_hs_conn_addrs(conn,
+                      NULL, &our_effective_addr,
+                      &our_id_addr_type, NULL,
+                      NULL, &peer_effective_addr,
+                      &peer_id_addr_type, NULL);
+
     if (proc->flags & BLE_SM_PROC_F_INITIATOR) {
-        ble_hs_conn_our_effective_addr(conn, &our_addr_type, out_ia);
-        *out_iat = ble_hs_misc_addr_type_to_ident(our_addr_type);
+        *out_iat = our_id_addr_type;
+        memcpy(out_ia, our_effective_addr, 6);
 
-        ble_hs_conn_peer_effective_addr(conn, out_ra);
-        *out_rat = ble_hs_misc_addr_type_to_ident(conn->bhc_addr_type);
+        *out_rat = peer_id_addr_type;
+        memcpy(out_ra, peer_effective_addr, 6);
     } else {
-        ble_hs_conn_our_effective_addr(conn, &our_addr_type, out_ra);
-        *out_rat = ble_hs_misc_addr_type_to_ident(our_addr_type);
+        *out_iat = peer_id_addr_type;
+        memcpy(out_ia, peer_effective_addr, 6);
 
-        ble_hs_conn_peer_effective_addr(conn, out_ia);
-        *out_iat = ble_hs_misc_addr_type_to_ident(conn->bhc_addr_type);
+        *out_rat = our_id_addr_type;
+        memcpy(out_ra, our_effective_addr, 6);
     }
 
     return 0;

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/eb177946/net/nimble/host/src/ble_sm_alg.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_sm_alg.c b/net/nimble/host/src/ble_sm_alg.c
index b59ff99..1885d09 100644
--- a/net/nimble/host/src/ble_sm_alg.c
+++ b/net/nimble/host/src/ble_sm_alg.c
@@ -316,6 +316,7 @@ ble_sm_alg_f5(uint8_t *w, uint8_t *n1, uint8_t *n2, uint8_t a1t,
     uint8_t t[16];
     int rc;
 
+    BLE_HS_LOG(DEBUG, "ble_sm_alg_f5()\n");
     ble_sm_alg_log_buf("w", w, 32);
     ble_sm_alg_log_buf("n1", n1, 16);
     ble_sm_alg_log_buf("n2", n2, 16);
@@ -369,6 +370,7 @@ ble_sm_alg_f6(uint8_t *w, uint8_t *n1, uint8_t *n2, uint8_t *r,
     uint8_t m[65];
     int rc;
 
+    BLE_HS_LOG(DEBUG, "ble_sm_alg_f6()\n");
     ble_sm_alg_log_buf("w", w, 16);
     ble_sm_alg_log_buf("n1", n1, 16);
     ble_sm_alg_log_buf("n2", n2, 16);
@@ -412,6 +414,7 @@ ble_sm_alg_g2(uint8_t *u, uint8_t *v, uint8_t *x, uint8_t *y, uint32_t *passkey)
     uint8_t m[80], xs[16];
     int rc;
 
+    BLE_HS_LOG(DEBUG, "ble_sm_alg_g2()\n");
     ble_sm_alg_log_buf("u", u, 32);
     ble_sm_alg_log_buf("v", v, 32);
     ble_sm_alg_log_buf("x", x, 16);

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/eb177946/net/nimble/host/src/ble_sm_lgcy.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_sm_lgcy.c b/net/nimble/host/src/ble_sm_lgcy.c
index b95a7a2..4696a07 100644
--- a/net/nimble/host/src/ble_sm_lgcy.c
+++ b/net/nimble/host/src/ble_sm_lgcy.c
@@ -111,7 +111,7 @@ ble_sm_lgcy_confirm_prepare_args(struct ble_sm_proc *proc,
 {
     int rc;
 
-    rc = ble_sm_addrs(proc, iat, ia, rat, ra);
+    rc = ble_sm_ia_ra(proc, iat, ia, rat, ra);
     if (rc != 0) {
         return rc;
     }

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/eb177946/net/nimble/host/src/ble_sm_priv.h
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_sm_priv.h b/net/nimble/host/src/ble_sm_priv.h
index c710823..5b6e157 100644
--- a/net/nimble/host/src/ble_sm_priv.h
+++ b/net/nimble/host/src/ble_sm_priv.h
@@ -447,7 +447,8 @@ void ble_sm_process_result(uint16_t conn_handle, struct ble_sm_result *res);
 void ble_sm_confirm_advance(struct ble_sm_proc *proc);
 int ble_sm_peer_addr(struct ble_sm_proc *proc,
                      uint8_t *out_type, uint8_t **out_addr);
-int ble_sm_addrs(struct ble_sm_proc *proc, uint8_t *out_iat, uint8_t *out_ia,
+int ble_sm_ia_ra(struct ble_sm_proc *proc,
+                 uint8_t *out_iat, uint8_t *out_ia,
                  uint8_t *out_rat, uint8_t *out_ra);
 
 void ble_sm_heartbeat(void);

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/eb177946/net/nimble/host/src/ble_sm_sc.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_sm_sc.c b/net/nimble/host/src/ble_sm_sc.c
index 7163b8d..5939916 100644
--- a/net/nimble/host/src/ble_sm_sc.c
+++ b/net/nimble/host/src/ble_sm_sc.c
@@ -375,7 +375,7 @@ ble_sm_sc_random_rx(struct ble_sm_proc *proc, struct ble_sm_result *res)
     }
 
     /* Calculate the mac key and ltk. */
-    rc = ble_sm_addrs(proc, &iat, ia, &rat, ra);
+    rc = ble_sm_ia_ra(proc, &iat, ia, &rat, ra);
     if (rc != 0) {
         res->app_status = rc;
         res->sm_err = BLE_SM_ERR_UNSPECIFIED;
@@ -520,6 +520,29 @@ ble_sm_sc_public_key_rx(uint16_t conn_handle, uint8_t op, struct os_mbuf **om,
     ble_hs_unlock();
 }
 
+static int
+ble_sm_sc_dhkey_addrs(struct ble_sm_proc *proc,
+                      uint8_t *out_our_id_addr_type,
+                      uint8_t **out_our_effective_addr,
+                      uint8_t *out_peer_id_addr_type,
+                      uint8_t **out_peer_effective_addr)
+{
+    struct ble_hs_conn *conn;
+
+    conn = ble_hs_conn_find(proc->conn_handle);
+    if (conn == NULL) {
+        return BLE_HS_ENOTCONN;
+    }
+
+    ble_hs_conn_addrs(conn,
+                      NULL, out_our_effective_addr,
+                      out_our_id_addr_type, NULL,
+                      NULL, out_peer_effective_addr,
+                      out_peer_id_addr_type, NULL);
+
+    return 0;
+}
+
 static void
 ble_sm_sc_dhkey_check_iocap(struct ble_sm_pair_cmd *pair_cmd,
                             uint8_t *out_iocap)
@@ -534,11 +557,11 @@ ble_sm_sc_dhkey_check_exec(struct ble_sm_proc *proc, struct ble_sm_result *res,
                            void *arg)
 {
     struct ble_sm_dhkey_check cmd;
-    uint8_t our_addr[6];
+    uint8_t *our_effective_addr;
+    uint8_t *peer_effective_addr;
+    uint8_t peer_id_addr_type;
+    uint8_t our_id_addr_type;
     uint8_t iocap[3];
-    uint8_t *peer_addr;
-    uint8_t peer_addr_type;
-    uint8_t our_addr_type;
     int rc;
 
     if (proc->flags & BLE_SM_PROC_F_INITIATOR) {
@@ -547,16 +570,17 @@ ble_sm_sc_dhkey_check_exec(struct ble_sm_proc *proc, struct ble_sm_result *res,
         ble_sm_sc_dhkey_check_iocap(&proc->pair_rsp, iocap);
     }
 
-    bls_hs_priv_copy_local_identity_addr(our_addr, &our_addr_type);
-
-    rc = ble_sm_peer_addr(proc, &peer_addr_type, &peer_addr);
+    rc = ble_sm_sc_dhkey_addrs(proc,
+                               &our_id_addr_type, &our_effective_addr,
+                               &peer_id_addr_type, &peer_effective_addr);
     if (rc != 0) {
         goto err;
     }
 
     rc = ble_sm_alg_f6(proc->mackey, ble_sm_our_pair_rand(proc),
                        ble_sm_peer_pair_rand(proc), proc->tk, iocap,
-                       our_addr_type, our_addr, peer_addr_type, peer_addr,
+                       our_id_addr_type, our_effective_addr,
+                       peer_id_addr_type, peer_effective_addr,
                        cmd.value);
     if (rc != 0) {
         goto err;
@@ -585,11 +609,11 @@ ble_sm_dhkey_check_process(struct ble_sm_proc *proc,
                            struct ble_sm_result *res)
 {
     uint8_t exp_value[16];
-    uint8_t our_addr[6];
+    uint8_t *peer_effective_addr;
+    uint8_t *our_effective_addr;
+    uint8_t peer_id_addr_type;
+    uint8_t our_id_addr_type;
     uint8_t iocap[3];
-    uint8_t *peer_addr;
-    uint8_t peer_addr_type;
-    uint8_t our_addr_type;
     uint8_t ioact;
 
     if (proc->flags & BLE_SM_PROC_F_INITIATOR) {
@@ -598,9 +622,11 @@ ble_sm_dhkey_check_process(struct ble_sm_proc *proc,
         ble_sm_sc_dhkey_check_iocap(&proc->pair_req, iocap);
     }
 
-    bls_hs_priv_copy_local_identity_addr(our_addr, &our_addr_type);
-
-    res->app_status = ble_sm_peer_addr(proc, &peer_addr_type, &peer_addr);
+    res->app_status = ble_sm_sc_dhkey_addrs(proc,
+                                            &our_id_addr_type,
+                                            &our_effective_addr,
+                                            &peer_id_addr_type,
+                                            &peer_effective_addr);
     if (res->app_status != 0) {
         res->sm_err = BLE_SM_ERR_UNSPECIFIED;
         res->enc_cb = 1;
@@ -613,9 +639,11 @@ ble_sm_dhkey_check_process(struct ble_sm_proc *proc,
 
     res->app_status = ble_sm_alg_f6(proc->mackey,
                                     ble_sm_peer_pair_rand(proc),
-                                    ble_sm_our_pair_rand(proc), proc->tk,
-                                    iocap, peer_addr_type, peer_addr,
-                                    our_addr_type, our_addr, exp_value);
+                                    ble_sm_our_pair_rand(proc),
+                                    proc->tk, iocap,
+                                    peer_id_addr_type, peer_effective_addr,
+                                    our_id_addr_type, our_effective_addr,
+                                    exp_value);
     if (res->app_status != 0) {
         res->sm_err = BLE_SM_ERR_UNSPECIFIED;
         res->enc_cb = 1;