1 /*
2 * Copyright (c) 2017 Intel Corporation
3 * Copyright (c) 2020 Lingao Meng
4 *
5 * SPDX-License-Identifier: Apache-2.0
6 */
7
8 #ifndef ZEPHYR_SUBSYS_BLUETOOTH_MESH_PROV_H_
9 #define ZEPHYR_SUBSYS_BLUETOOTH_MESH_PROV_H_
10
11 #include "prov_bearer.h"
12
13 #define PROV_ERR_NONE 0x00
14 #define PROV_ERR_NVAL_PDU 0x01
15 #define PROV_ERR_NVAL_FMT 0x02
16 #define PROV_ERR_UNEXP_PDU 0x03
17 #define PROV_ERR_CFM_FAILED 0x04
18 #define PROV_ERR_RESOURCES 0x05
19 #define PROV_ERR_DECRYPT 0x06
20 #define PROV_ERR_UNEXP_ERR 0x07
21 #define PROV_ERR_ADDR 0x08
22
23 #define AUTH_METHOD_NO_OOB 0x00
24 #define AUTH_METHOD_STATIC 0x01
25 #define AUTH_METHOD_OUTPUT 0x02
26 #define AUTH_METHOD_INPUT 0x03
27
28 #define OUTPUT_OOB_BLINK 0x00
29 #define OUTPUT_OOB_BEEP 0x01
30 #define OUTPUT_OOB_VIBRATE 0x02
31 #define OUTPUT_OOB_NUMBER 0x03
32 #define OUTPUT_OOB_STRING 0x04
33
34 #define INPUT_OOB_PUSH 0x00
35 #define INPUT_OOB_TWIST 0x01
36 #define INPUT_OOB_NUMBER 0x02
37 #define INPUT_OOB_STRING 0x03
38
39 #define PUB_KEY_NO_OOB 0x00
40 #define PUB_KEY_OOB 0x01
41
42 #define PROV_INVITE 0x00
43 #define PROV_CAPABILITIES 0x01
44 #define PROV_START 0x02
45 #define PROV_PUB_KEY 0x03
46 #define PROV_INPUT_COMPLETE 0x04
47 #define PROV_CONFIRM 0x05
48 #define PROV_RANDOM 0x06
49 #define PROV_DATA 0x07
50 #define PROV_COMPLETE 0x08
51 #define PROV_FAILED 0x09
52
53 #define PROV_NO_PDU 0xff
54
55 #define PDU_LEN_INVITE 1
56 #define PDU_LEN_CAPABILITIES 11
57 #define PDU_LEN_START 5
58 #define PDU_LEN_PUB_KEY 64
59 #define PDU_LEN_INPUT_COMPLETE 0
60 #define PDU_LEN_CONFIRM 16
61 #define PDU_LEN_RANDOM 16
62 #define PDU_LEN_DATA 33
63 #define PDU_LEN_COMPLETE 0
64 #define PDU_LEN_FAILED 1
65
66 #define PDU_OP_LEN 1
67
68 #define PROV_ALG_P256 0x00
69
70 #define PROV_BUF(name, len) \
71 NET_BUF_SIMPLE_DEFINE(name, PROV_BEARER_BUF_HEADROOM + PDU_OP_LEN + len)
72
73 enum {
74 WAIT_PUB_KEY, /* Waiting for local PubKey to be generated */
75 LINK_ACTIVE, /* Link has been opened */
76 WAIT_NUMBER, /* Waiting for number input from user */
77 WAIT_STRING, /* Waiting for string input from user */
78 NOTIFY_INPUT_COMPLETE, /* Notify that input has been completed. */
79 PROVISIONER, /* The link was opened as provisioner */
80 OOB_PUB_KEY, /* OOB Public key used */
81 PUB_KEY_SENT, /* Public key has been sent */
82 REMOTE_PUB_KEY, /* Remote key has been received */
83 INPUT_COMPLETE, /* Device input completed */
84 WAIT_CONFIRM, /* Wait for send confirm */
85 WAIT_AUTH, /* Wait for auth response */
86 OOB_STATIC_KEY, /* OOB Static Authentication */
87 WAIT_DH_KEY, /* Wait for DH Key */
88
89 NUM_FLAGS,
90 };
91
92 /** Provisioning role */
93 struct bt_mesh_prov_role {
94 void (*link_opened)(void);
95
96 void (*link_closed)(void);
97
98 void (*error)(uint8_t reason);
99
100 void (*input_complete)(void);
101
102 void (*op[10])(const uint8_t *data);
103 };
104
105 struct bt_mesh_prov_link {
106 ATOMIC_DEFINE(flags, NUM_FLAGS);
107
108 const struct prov_bearer *bearer;
109 const struct bt_mesh_prov_role *role;
110
111 uint8_t oob_method; /* Authen method */
112 uint8_t oob_action; /* Authen action */
113 uint8_t oob_size; /* Authen size */
114 uint8_t auth[16]; /* Authen value */
115
116 uint8_t dhkey[BT_DH_KEY_LEN]; /* Calculated DHKey */
117 uint8_t expect; /* Next expected PDU */
118
119 uint8_t conf[16]; /* Local/Remote Confirmation */
120 uint8_t rand[16]; /* Local Random */
121
122 uint8_t conf_salt[16]; /* ConfirmationSalt */
123 uint8_t conf_key[16]; /* ConfirmationKey */
124 /* ConfirmationInput fields: */
125 struct {
126 uint8_t invite[PDU_LEN_INVITE];
127 uint8_t capabilities[PDU_LEN_CAPABILITIES];
128 uint8_t start[PDU_LEN_START];
129 uint8_t pub_key_provisioner[PDU_LEN_PUB_KEY]; /* big-endian */
130 uint8_t pub_key_device[PDU_LEN_PUB_KEY]; /* big-endian */
131 } conf_inputs;
132 uint8_t prov_salt[16]; /* Provisioning Salt */
133 };
134
135 extern struct bt_mesh_prov_link bt_mesh_prov_link;
136 extern const struct bt_mesh_prov *bt_mesh_prov;
137
bt_mesh_prov_send(struct net_buf_simple * buf,prov_bearer_send_complete_t cb)138 static inline int bt_mesh_prov_send(struct net_buf_simple *buf,
139 prov_bearer_send_complete_t cb)
140 {
141 return bt_mesh_prov_link.bearer->send(buf, cb, NULL);
142 }
143
bt_mesh_prov_buf_init(struct net_buf_simple * buf,uint8_t type)144 static inline void bt_mesh_prov_buf_init(struct net_buf_simple *buf, uint8_t type)
145 {
146 net_buf_simple_reserve(buf, PROV_BEARER_BUF_HEADROOM);
147 net_buf_simple_add_u8(buf, type);
148 }
149
150 int bt_mesh_prov_reset_state(void (*func)(const uint8_t key[BT_PUB_KEY_LEN]));
151
152 bool bt_mesh_prov_active(void);
153
154 int bt_mesh_prov_auth(uint8_t method, uint8_t action, uint8_t size);
155
156 int bt_mesh_pb_gatt_open(struct bt_conn *conn);
157 int bt_mesh_pb_gatt_close(struct bt_conn *conn);
158 int bt_mesh_pb_gatt_recv(struct bt_conn *conn, struct net_buf_simple *buf);
159
160 const struct bt_mesh_prov *bt_mesh_prov_get(void);
161
162 void bt_mesh_prov_complete(uint16_t net_idx, uint16_t addr);
163 void bt_mesh_prov_reset(void);
164
165 const struct prov_bearer_cb *bt_mesh_prov_bearer_cb_get(void);
166
167 void bt_mesh_pb_adv_recv(struct net_buf_simple *buf);
168
169 int bt_mesh_prov_init(const struct bt_mesh_prov *prov);
170
171 #endif /* ZEPHYR_SUBSYS_BLUETOOTH_MESH_PROV_H_ */
172