1 /*
2 * Copyright (c) 2017 Intel Corporation
3 * Copyright (c) 2020 Nordic Semiconductor ASA
4 *
5 * SPDX-License-Identifier: Apache-2.0
6 */
7 #include <stdint.h>
8 #include <string.h>
9 #include <zephyr/bluetooth/conn.h>
10 #include <zephyr/bluetooth/mesh.h>
11 #include <zephyr/net_buf.h>
12 #include "testing.h"
13 #include "net.h"
14 #include "crypto.h"
15 #include "beacon.h"
16 #include "prov.h"
17
18 #include "common/bt_str.h"
19
20 #define LOG_LEVEL CONFIG_BT_MESH_PROV_LOG_LEVEL
21 #include <zephyr/logging/log.h>
22 LOG_MODULE_REGISTER(bt_mesh_pb_adv);
23
24 #define GPCF(gpc) (gpc & 0x03)
25 #define GPC_START(last_seg) (((last_seg) << 2) | 0x00)
26 #define GPC_ACK 0x01
27 #define GPC_CONT(seg_id) (((seg_id) << 2) | 0x02)
28 #define GPC_CTL(op) (((op) << 2) | 0x03)
29
30 #define START_PAYLOAD_MAX 20
31 #define CONT_PAYLOAD_MAX 23
32 #define RX_BUFFER_MAX 65
33
34 #define START_LAST_SEG(gpc) (gpc >> 2)
35 #define CONT_SEG_INDEX(gpc) (gpc >> 2)
36
37 #define BEARER_CTL(gpc) (gpc >> 2)
38 #define LINK_OPEN 0x00
39 #define LINK_ACK 0x01
40 #define LINK_CLOSE 0x02
41
42 #define XACT_SEG_OFFSET(_seg) (20 + ((_seg - 1) * 23))
43 #define XACT_SEG_DATA(_seg) (&link.rx.buf->data[XACT_SEG_OFFSET(_seg)])
44 #define XACT_SEG_RECV(_seg) (link.rx.seg &= ~(1 << (_seg)))
45
46 #define XACT_ID_MAX 0x7f
47 #define XACT_ID_NVAL 0xff
48 #define SEG_NVAL 0xff
49
50 #define RETRANSMIT_TIMEOUT K_MSEC(CONFIG_BT_MESH_PB_ADV_RETRANS_TIMEOUT)
51 #define BUF_TIMEOUT K_MSEC(400)
52 #define CLOSING_TIMEOUT 3
53 #define TRANSACTION_TIMEOUT 30
54
55 /* Acked messages, will do retransmissions manually, taking acks into account:
56 */
57 #define RETRANSMITS_RELIABLE CONFIG_BT_MESH_PB_ADV_TRANS_PDU_RETRANSMIT_COUNT
58 /* PDU acks: */
59 #define RETRANSMITS_ACK CONFIG_BT_MESH_PB_ADV_TRANS_ACK_RETRANSMIT_COUNT
60 /* Link close retransmits: */
61 #define RETRANSMITS_LINK_CLOSE CONFIG_BT_MESH_PB_ADV_LINK_CLOSE_RETRANSMIT_COUNT
62
63 enum {
64 ADV_LINK_ACTIVE, /* Link has been opened */
65 ADV_LINK_ACK_RECVD, /* Ack for link has been received */
66 ADV_LINK_CLOSING, /* Link is closing down */
67 ADV_LINK_INVALID, /* Error occurred during provisioning */
68 ADV_ACK_PENDING, /* An acknowledgment is being sent */
69 ADV_PROVISIONER, /* The link was opened as provisioner */
70 ADV_LINK_ACK_SENDING, /* Link Ack tx was scheduled but not finished. */
71 ADV_SENDING, /* Sending any PDU */
72
73 ADV_NUM_FLAGS,
74 };
75
76 struct pb_adv {
77 uint32_t id; /* Link ID */
78
79 ATOMIC_DEFINE(flags, ADV_NUM_FLAGS);
80
81 const struct prov_bearer_cb *cb;
82 void *cb_data;
83
84 struct {
85 uint8_t id; /* Most recent transaction ID */
86 uint8_t seg; /* Bit-field of unreceived segments */
87 uint8_t last_seg; /* Last segment (to check length) */
88 uint8_t fcs; /* Expected FCS value */
89 struct net_buf_simple *buf;
90 } rx;
91
92 struct {
93 /* Start timestamp of the transaction */
94 int64_t start;
95
96 /* Transaction id */
97 uint8_t id;
98
99 /* Current ack id */
100 uint8_t pending_ack;
101
102 /* Transaction timeout in seconds */
103 uint8_t timeout;
104
105 /* Pending outgoing adv(s) (Link Open, Gen Trans Start and Gen Trans Cont) */
106 struct bt_mesh_adv *adv[3];
107
108 /* Index of the next adv to be sent */
109 int next;
110
111 prov_bearer_send_complete_t cb;
112
113 void *cb_data;
114
115 /* Retransmit timer */
116 struct k_work_delayable retransmit;
117
118 /* Unacked adv buffers (Link Ack, Link Close and Gen Trans Ack). Array size is
119 * hardcoded to 2 allowing to send Gen Trans Ack and Link Close at the same time.
120 */
121 struct unacked_adv_ctx {
122 struct bt_mesh_adv *adv;
123 prov_bearer_send_complete_t cb;
124 void *cb_data;
125 } unacked[2];
126
127 /* Last sent unacked[] buffer */
128 int last_unacked;
129 } tx;
130
131 /* Protocol timeout */
132 struct k_work_delayable prot_timer;
133 };
134
135 struct prov_rx {
136 uint32_t link_id;
137 uint8_t xact_id;
138 uint8_t gpc;
139 };
140
141 NET_BUF_SIMPLE_DEFINE_STATIC(rx_buf, RX_BUFFER_MAX);
142
143 static struct pb_adv link = { .rx = { .buf = &rx_buf } };
144
145 static void gen_prov_ack_send(uint8_t xact_id);
146 static void link_open(struct prov_rx *rx, struct net_buf_simple *buf);
147 static void link_ack(struct prov_rx *rx, struct net_buf_simple *buf);
148 static void link_close(struct prov_rx *rx, struct net_buf_simple *buf);
149 static void prov_link_close(enum prov_bearer_link_status status);
150 static void close_link(enum prov_bearer_link_status status);
151
152 static void tx_work_handler(struct k_work *work);
153 static K_WORK_DELAYABLE_DEFINE(tx_work, tx_work_handler);
154
tx_schedule(void)155 static void tx_schedule(void)
156 {
157 uint16_t random_delay;
158
159 if (atomic_test_bit(link.flags, ADV_SENDING)) {
160 LOG_DBG("Another tx is in progress");
161 return;
162 }
163
164 (void)bt_rand(&random_delay, sizeof(random_delay));
165 random_delay = 20 + (random_delay % 30);
166
167 LOG_DBG("Next PDU delayed by %ums", random_delay);
168
169 (void)k_work_schedule(&tx_work, K_MSEC(random_delay));
170 }
171
send_unacked(struct bt_mesh_adv * adv,prov_bearer_send_complete_t cb,void * cb_data)172 static int send_unacked(struct bt_mesh_adv *adv, prov_bearer_send_complete_t cb,
173 void *cb_data)
174 {
175 for (int i = 0; i < ARRAY_SIZE(link.tx.unacked); i++) {
176 if (link.tx.unacked[i].adv != NULL) {
177 continue;
178 }
179
180 link.tx.unacked[i].adv = adv;
181 link.tx.unacked[i].cb = cb;
182 link.tx.unacked[i].cb_data = cb_data;
183
184 tx_schedule();
185
186 return 0;
187 }
188
189 LOG_WRN("No memory to send unacked PDU: %s", bt_hex(adv->b.data, adv->b.len));
190 return -ENOMEM;
191 }
192
send_reliable(void)193 static void send_reliable(void)
194 {
195 /* Dropping next tx adv index to start transmission from the first adv buffer. */
196 link.tx.next = 0;
197
198 tx_schedule();
199 }
200
delayed_adv_send_end(int err,void * user_data)201 static void delayed_adv_send_end(int err, void *user_data)
202 {
203 bool unacked = (bool)user_data;
204 struct unacked_adv_ctx *unacked_adv = &link.tx.unacked[link.tx.last_unacked];
205
206 if (unacked && unacked_adv->adv != NULL) {
207 if (unacked_adv->cb) {
208 unacked_adv->cb(err, unacked_adv->cb_data);
209 }
210
211 bt_mesh_adv_unref(unacked_adv->adv);
212 unacked_adv->adv = NULL;
213 }
214
215 atomic_clear_bit(link.flags, ADV_SENDING);
216 tx_schedule();
217 }
218
delayed_adv_send_start(uint16_t duration,int err,void * user_data)219 static void delayed_adv_send_start(uint16_t duration, int err, void *user_data)
220 {
221 if (err) {
222 delayed_adv_send_end(err, user_data);
223 }
224 }
225
226 static const struct bt_mesh_send_cb delayed_adv_send_cb = {
227 .start = delayed_adv_send_start,
228 .end = delayed_adv_send_end,
229 };
230
tx_work_handler(struct k_work * work)231 static void tx_work_handler(struct k_work *work)
232 {
233 int i;
234
235 /* Send Link Ack, Link Close and Gen Trans Ack first. */
236 for (i = 0; i < ARRAY_SIZE(link.tx.unacked); i++) {
237 int idx = (i + link.tx.last_unacked) % ARRAY_SIZE(link.tx.unacked);
238 struct unacked_adv_ctx *unacked = &link.tx.unacked[idx];
239
240 if (!unacked->adv) {
241 continue;
242 }
243
244 atomic_set_bit(link.flags, ADV_SENDING);
245 bt_mesh_adv_send(unacked->adv, &delayed_adv_send_cb, (void *)true);
246
247 link.tx.last_unacked = idx;
248
249 return;
250 }
251
252 /* Send Trans Start, Trans Cont and Link Open */
253 if (link.tx.next >= ARRAY_SIZE(link.tx.adv) || link.tx.adv[link.tx.next] == NULL) {
254 LOG_DBG("All PDUs were sent");
255 return;
256 }
257
258 atomic_set_bit(link.flags, ADV_SENDING);
259 bt_mesh_adv_send(link.tx.adv[link.tx.next], &delayed_adv_send_cb, (void *)false);
260
261 link.tx.next++;
262
263 if (link.tx.next == ARRAY_SIZE(link.tx.adv) || link.tx.adv[link.tx.next] == NULL) {
264 /* All ack-able PDUs are sent. Now we can run the retransmit timer. */
265 LOG_DBG("Starting retransmit timer");
266 k_work_reschedule(&link.tx.retransmit, RETRANSMIT_TIMEOUT);
267 }
268 }
269
last_seg(uint16_t len)270 static uint8_t last_seg(uint16_t len)
271 {
272 if (len <= START_PAYLOAD_MAX) {
273 return 0;
274 }
275
276 len -= START_PAYLOAD_MAX;
277
278 return 1 + (len / CONT_PAYLOAD_MAX);
279 }
280
free_segments(void)281 static void free_segments(void)
282 {
283 int i;
284 bool canceled = false;
285
286 for (i = 0; i < ARRAY_SIZE(link.tx.adv); i++) {
287 struct bt_mesh_adv *adv = link.tx.adv[i];
288 int err;
289
290 if (!adv) {
291 break;
292 }
293
294 link.tx.adv[i] = NULL;
295
296 /* Terminate active adv */
297 if (adv->ctx.busy == 0U) {
298 err = bt_mesh_adv_terminate(adv);
299 if (err == 0) {
300 canceled = true;
301 }
302 } else {
303 /* Mark as canceled */
304 adv->ctx.busy = 0U;
305 canceled = true;
306 }
307
308 bt_mesh_adv_unref(adv);
309 }
310
311 if (canceled) {
312 atomic_clear_bit(link.flags, ADV_SENDING);
313 tx_schedule();
314 }
315 }
316
next_transaction_id(uint8_t id)317 static uint8_t next_transaction_id(uint8_t id)
318 {
319 return (((id + 1) & XACT_ID_MAX) | (id & (XACT_ID_MAX+1)));
320 }
321
prov_clear_tx(void)322 static void prov_clear_tx(void)
323 {
324 LOG_DBG("");
325
326 /* If this fails, the work handler will not find any advs to send,
327 * and return without rescheduling. The work handler also checks the
328 * LINK_ACTIVE flag, so if this call is part of reset_adv_link, it'll
329 * exit early.
330 */
331 (void)k_work_cancel_delayable(&link.tx.retransmit);
332
333 free_segments();
334 }
335
reset_adv_link(void)336 static void reset_adv_link(void)
337 {
338 LOG_DBG("");
339 prov_clear_tx();
340
341 /* If this fails, the work handler will exit early on the LINK_ACTIVE
342 * check.
343 */
344 (void)k_work_cancel_delayable(&link.prot_timer);
345
346 if (atomic_test_bit(link.flags, ADV_PROVISIONER)) {
347 /* Clear everything except the retransmit and protocol timer
348 * delayed work objects.
349 */
350 (void)memset(&link, 0, offsetof(struct pb_adv, tx.retransmit));
351 link.rx.id = XACT_ID_NVAL;
352 } else {
353 /* If provisioned, reset the link callback to stop receiving provisioning advs,
354 * otherwise keep the callback to accept another provisioning attempt.
355 */
356 if (bt_mesh_is_provisioned()) {
357 link.cb = NULL;
358 }
359
360 link.id = 0;
361 atomic_clear(link.flags);
362 link.rx.id = XACT_ID_MAX;
363 link.tx.id = XACT_ID_NVAL;
364 }
365
366 link.tx.pending_ack = XACT_ID_NVAL;
367 link.rx.buf = &rx_buf;
368 net_buf_simple_reset(link.rx.buf);
369 }
370
close_link(enum prov_bearer_link_status reason)371 static void close_link(enum prov_bearer_link_status reason)
372 {
373 const struct prov_bearer_cb *cb = link.cb;
374 void *cb_data = link.cb_data;
375
376 reset_adv_link();
377 cb->link_closed(&bt_mesh_pb_adv, cb_data, reason);
378 }
379
adv_create(uint8_t retransmits)380 static struct bt_mesh_adv *adv_create(uint8_t retransmits)
381 {
382 struct bt_mesh_adv *adv;
383
384 adv = bt_mesh_adv_create(BT_MESH_ADV_PROV, BT_MESH_ADV_TAG_PROV,
385 BT_MESH_TRANSMIT(retransmits, 20),
386 BUF_TIMEOUT);
387 if (!adv) {
388 LOG_ERR("Out of provisioning advs");
389 return NULL;
390 }
391
392 return adv;
393 }
394
ack_complete(int err,void * user_data)395 static void ack_complete(int err, void *user_data)
396 {
397 LOG_DBG("xact 0x%x complete", (uint8_t)link.tx.pending_ack);
398 atomic_clear_bit(link.flags, ADV_ACK_PENDING);
399 }
400
ack_pending(void)401 static bool ack_pending(void)
402 {
403 return atomic_test_bit(link.flags, ADV_ACK_PENDING);
404 }
405
prov_failed(uint8_t err)406 static void prov_failed(uint8_t err)
407 {
408 LOG_DBG("%u", err);
409 link.cb->error(&bt_mesh_pb_adv, link.cb_data, err);
410 atomic_set_bit(link.flags, ADV_LINK_INVALID);
411 }
412
prov_msg_recv(void)413 static void prov_msg_recv(void)
414 {
415 k_work_reschedule(&link.prot_timer, bt_mesh_prov_protocol_timeout_get());
416
417 if (!bt_mesh_fcs_check(link.rx.buf, link.rx.fcs)) {
418 LOG_ERR("Incorrect FCS");
419 return;
420 }
421
422 gen_prov_ack_send(link.rx.id);
423
424 if (atomic_test_bit(link.flags, ADV_LINK_INVALID)) {
425 LOG_WRN("Unexpected msg 0x%02x on invalidated link", link.rx.buf->data[0]);
426 prov_failed(PROV_ERR_UNEXP_PDU);
427 return;
428 }
429
430 link.cb->recv(&bt_mesh_pb_adv, link.cb_data, link.rx.buf);
431 }
432
protocol_timeout(struct k_work * work)433 static void protocol_timeout(struct k_work *work)
434 {
435 if (!atomic_test_bit(link.flags, ADV_LINK_ACTIVE)) {
436 return;
437 }
438
439 LOG_DBG("");
440
441 link.rx.seg = 0U;
442 prov_link_close(PROV_BEARER_LINK_STATUS_TIMEOUT);
443 }
444 /*******************************************************************************
445 * Generic provisioning
446 ******************************************************************************/
447
gen_prov_ack_send(uint8_t xact_id)448 static void gen_prov_ack_send(uint8_t xact_id)
449 {
450 struct bt_mesh_adv *adv;
451 bool pending = atomic_test_and_set_bit(link.flags, ADV_ACK_PENDING);
452 int err;
453
454 LOG_DBG("xact_id 0x%x", xact_id);
455
456 if (pending && link.tx.pending_ack == xact_id) {
457 LOG_DBG("Not sending duplicate ack");
458 return;
459 }
460
461 adv = adv_create(RETRANSMITS_ACK);
462 if (!adv) {
463 atomic_clear_bit(link.flags, ADV_ACK_PENDING);
464 return;
465 }
466
467 if (!pending) {
468 link.tx.pending_ack = xact_id;
469 }
470
471 net_buf_simple_add_be32(&adv->b, link.id);
472 net_buf_simple_add_u8(&adv->b, xact_id);
473 net_buf_simple_add_u8(&adv->b, GPC_ACK);
474
475 err = send_unacked(adv, pending ? NULL : ack_complete, NULL);
476 if (err) {
477 atomic_clear_bit(link.flags, ADV_ACK_PENDING);
478 }
479 }
480
gen_prov_cont(struct prov_rx * rx,struct net_buf_simple * buf)481 static void gen_prov_cont(struct prov_rx *rx, struct net_buf_simple *buf)
482 {
483 uint8_t seg = CONT_SEG_INDEX(rx->gpc);
484
485 if (link.tx.adv[0]) {
486 LOG_DBG("Ongoing tx transaction has not been completed yet");
487 return;
488 }
489
490 LOG_DBG("len %u, seg_index %u", buf->len, seg);
491
492 if (!link.rx.seg && link.rx.id == rx->xact_id) {
493 if (!ack_pending()) {
494 LOG_DBG("Resending ack");
495 gen_prov_ack_send(rx->xact_id);
496 }
497
498 return;
499 }
500
501 if (!link.rx.seg &&
502 next_transaction_id(link.rx.id) == rx->xact_id) {
503 LOG_DBG("Start segment lost");
504
505 link.rx.id = rx->xact_id;
506
507 net_buf_simple_reset(link.rx.buf);
508
509 link.rx.seg = SEG_NVAL;
510 link.rx.last_seg = SEG_NVAL;
511
512 prov_clear_tx();
513 } else if (rx->xact_id != link.rx.id) {
514 LOG_WRN("Data for unknown transaction (0x%x != 0x%x)", rx->xact_id, link.rx.id);
515 return;
516 }
517
518 if (seg > link.rx.last_seg) {
519 LOG_ERR("Invalid segment index %u", seg);
520 prov_failed(PROV_ERR_NVAL_FMT);
521 return;
522 }
523
524 if (!(link.rx.seg & BIT(seg))) {
525 LOG_DBG("Ignoring already received segment");
526 return;
527 }
528
529 if (XACT_SEG_OFFSET(seg) + buf->len > RX_BUFFER_MAX) {
530 LOG_WRN("Rx buffer overflow. Malformed generic prov frame?");
531 return;
532 }
533
534 memcpy(XACT_SEG_DATA(seg), buf->data, buf->len);
535 XACT_SEG_RECV(seg);
536
537 if (seg == link.rx.last_seg && !(link.rx.seg & BIT(0))) {
538 uint8_t expect_len;
539
540 expect_len = (link.rx.buf->len - 20U -
541 ((link.rx.last_seg - 1) * 23U));
542 if (expect_len != buf->len) {
543 LOG_ERR("Incorrect last seg len: %u != %u", expect_len, buf->len);
544 prov_failed(PROV_ERR_NVAL_FMT);
545 return;
546 }
547 }
548
549 if (!link.rx.seg) {
550 prov_msg_recv();
551 }
552 }
553
gen_prov_ack(struct prov_rx * rx,struct net_buf_simple * buf)554 static void gen_prov_ack(struct prov_rx *rx, struct net_buf_simple *buf)
555 {
556 LOG_DBG("len %u", buf->len);
557
558 if (!link.tx.adv[0]) {
559 return;
560 }
561
562 if (rx->xact_id == link.tx.id) {
563 /* Don't clear resending of link_close messages */
564 if (!atomic_test_bit(link.flags, ADV_LINK_CLOSING)) {
565 prov_clear_tx();
566 }
567
568 if (link.tx.cb) {
569 link.tx.cb(0, link.tx.cb_data);
570 }
571 }
572 }
573
gen_prov_start(struct prov_rx * rx,struct net_buf_simple * buf)574 static void gen_prov_start(struct prov_rx *rx, struct net_buf_simple *buf)
575 {
576 uint8_t seg = SEG_NVAL;
577
578 if (link.tx.adv[0]) {
579 LOG_DBG("Ongoing tx transaction has not been completed yet");
580 return;
581 }
582
583 if (rx->xact_id == link.rx.id) {
584 if (!link.rx.seg) {
585 if (!ack_pending()) {
586 LOG_DBG("Resending ack");
587 gen_prov_ack_send(rx->xact_id);
588 }
589
590 return;
591 }
592
593 if (!(link.rx.seg & BIT(0))) {
594 LOG_DBG("Ignoring duplicate segment");
595 return;
596 }
597 } else if (rx->xact_id != next_transaction_id(link.rx.id)) {
598 LOG_WRN("Unexpected xact 0x%x, expected 0x%x", rx->xact_id,
599 next_transaction_id(link.rx.id));
600 return;
601 }
602
603 net_buf_simple_reset(link.rx.buf);
604 link.rx.buf->len = net_buf_simple_pull_be16(buf);
605 link.rx.id = rx->xact_id;
606 link.rx.fcs = net_buf_simple_pull_u8(buf);
607
608 LOG_DBG("len %u last_seg %u total_len %u fcs 0x%02x", buf->len, START_LAST_SEG(rx->gpc),
609 link.rx.buf->len, link.rx.fcs);
610
611 if (link.rx.buf->len < 1) {
612 LOG_ERR("Ignoring zero-length provisioning PDU");
613 prov_failed(PROV_ERR_NVAL_FMT);
614 return;
615 }
616
617 if (link.rx.buf->len > link.rx.buf->size) {
618 LOG_ERR("Too large provisioning PDU (%u bytes)", link.rx.buf->len);
619 prov_failed(PROV_ERR_NVAL_FMT);
620 return;
621 }
622
623 if (START_LAST_SEG(rx->gpc) > 0 && link.rx.buf->len <= 20U) {
624 LOG_ERR("Too small total length for multi-segment PDU");
625 prov_failed(PROV_ERR_NVAL_FMT);
626 return;
627 }
628
629 if (START_LAST_SEG(rx->gpc) != last_seg(link.rx.buf->len)) {
630 LOG_ERR("Invalid SegN (%u, calculated %u)", START_LAST_SEG(rx->gpc),
631 last_seg(link.rx.buf->len));
632 prov_failed(PROV_ERR_NVAL_FMT);
633 return;
634 }
635
636 prov_clear_tx();
637
638 link.rx.last_seg = START_LAST_SEG(rx->gpc);
639
640 /* This (BIT(0) is set) can happen if we received a Transaction Continuation PDU, before
641 * receiving a Transaction Start PDU (see `gen_prov_cont`). Now we received the Transaction
642 * Start PDU and we can extract the last segment number. Knowing this, we check if
643 * previously received segment exceeds the last segment number. If so, we reject the
644 * Transaction Start PDU.
645 */
646 if ((link.rx.seg & BIT(0)) &&
647 ((link.rx.seg & SEG_NVAL) != SEG_NVAL) &&
648 (find_msb_set((~link.rx.seg) & SEG_NVAL) - 1 > link.rx.last_seg)) {
649 LOG_ERR("Invalid segment index %u", seg);
650 prov_failed(PROV_ERR_NVAL_FMT);
651 return;
652 }
653
654 if (link.rx.seg) {
655 seg = link.rx.seg;
656 }
657
658 link.rx.seg = seg & ((1 << (START_LAST_SEG(rx->gpc) + 1)) - 1);
659 memcpy(link.rx.buf->data, buf->data, buf->len);
660 XACT_SEG_RECV(0);
661
662 if (!link.rx.seg) {
663 prov_msg_recv();
664 }
665 }
666
gen_prov_ctl(struct prov_rx * rx,struct net_buf_simple * buf)667 static void gen_prov_ctl(struct prov_rx *rx, struct net_buf_simple *buf)
668 {
669 LOG_DBG("op 0x%02x len %u", BEARER_CTL(rx->gpc), buf->len);
670
671 switch (BEARER_CTL(rx->gpc)) {
672 case LINK_OPEN:
673 link_open(rx, buf);
674 break;
675 case LINK_ACK:
676 if (!atomic_test_bit(link.flags, ADV_LINK_ACTIVE)) {
677 return;
678 }
679
680 link_ack(rx, buf);
681 break;
682 case LINK_CLOSE:
683 if (!atomic_test_bit(link.flags, ADV_LINK_ACTIVE)) {
684 return;
685 }
686
687 link_close(rx, buf);
688 break;
689 default:
690 LOG_ERR("Unknown bearer opcode: 0x%02x", BEARER_CTL(rx->gpc));
691
692 if (IS_ENABLED(CONFIG_BT_TESTING)) {
693 bt_mesh_test_prov_invalid_bearer(BEARER_CTL(rx->gpc));
694 }
695
696 return;
697 }
698 }
699
700 static const struct {
701 void (*func)(struct prov_rx *rx, struct net_buf_simple *buf);
702 bool require_link;
703 uint8_t min_len;
704 } gen_prov[] = {
705 { gen_prov_start, true, 3 },
706 { gen_prov_ack, true, 0 },
707 { gen_prov_cont, true, 0 },
708 { gen_prov_ctl, false, 0 },
709 };
710
gen_prov_recv(struct prov_rx * rx,struct net_buf_simple * buf)711 static void gen_prov_recv(struct prov_rx *rx, struct net_buf_simple *buf)
712 {
713 if (buf->len < gen_prov[GPCF(rx->gpc)].min_len) {
714 LOG_ERR("Too short GPC message type %u", GPCF(rx->gpc));
715 return;
716 }
717
718 if (!atomic_test_bit(link.flags, ADV_LINK_ACTIVE) &&
719 gen_prov[GPCF(rx->gpc)].require_link) {
720 LOG_DBG("Ignoring message that requires active link");
721 return;
722 }
723
724 gen_prov[GPCF(rx->gpc)].func(rx, buf);
725 }
726
727 /*******************************************************************************
728 * TX
729 ******************************************************************************/
730
prov_retransmit(struct k_work * work)731 static void prov_retransmit(struct k_work *work)
732 {
733 LOG_DBG("");
734
735 if (!atomic_test_bit(link.flags, ADV_LINK_ACTIVE)) {
736 LOG_WRN("Link not active");
737 return;
738 }
739
740 if (k_uptime_get() - link.tx.start > link.tx.timeout * MSEC_PER_SEC) {
741 LOG_WRN("Giving up transaction");
742 prov_link_close(PROV_BEARER_LINK_STATUS_TIMEOUT);
743 return;
744 }
745
746 send_reliable();
747 }
748
ctl_adv_create(uint8_t op,const void * data,uint8_t data_len,uint8_t retransmits)749 static struct bt_mesh_adv *ctl_adv_create(uint8_t op, const void *data, uint8_t data_len,
750 uint8_t retransmits)
751 {
752 struct bt_mesh_adv *adv;
753
754 LOG_DBG("op 0x%02x data_len %u", op, data_len);
755
756 adv = adv_create(retransmits);
757 if (!adv) {
758 return NULL;
759 }
760
761 net_buf_simple_add_be32(&adv->b, link.id);
762 /* Transaction ID, always 0 for Bearer messages */
763 net_buf_simple_add_u8(&adv->b, 0x00);
764 net_buf_simple_add_u8(&adv->b, GPC_CTL(op));
765 net_buf_simple_add_mem(&adv->b, data, data_len);
766
767 return adv;
768 }
769
bearer_ctl_send(struct bt_mesh_adv * adv)770 static int bearer_ctl_send(struct bt_mesh_adv *adv)
771 {
772 if (!adv) {
773 return -ENOMEM;
774 }
775
776 prov_clear_tx();
777 k_work_reschedule(&link.prot_timer, bt_mesh_prov_protocol_timeout_get());
778
779 link.tx.start = k_uptime_get();
780 link.tx.adv[0] = adv;
781 send_reliable();
782
783 return 0;
784 }
785
buf_sent(int err,void * user_data)786 static void buf_sent(int err, void *user_data)
787 {
788 enum prov_bearer_link_status reason = (enum prov_bearer_link_status)(int)user_data;
789
790 atomic_clear_bit(link.flags, ADV_LINK_ACK_SENDING);
791
792 if (atomic_test_and_clear_bit(link.flags, ADV_LINK_CLOSING)) {
793 close_link(reason);
794 return;
795 }
796 }
797
bearer_ctl_send_unacked(struct bt_mesh_adv * adv,void * user_data)798 static int bearer_ctl_send_unacked(struct bt_mesh_adv *adv, void *user_data)
799 {
800 int err;
801
802 if (!adv) {
803 return -ENOMEM;
804 }
805
806 prov_clear_tx();
807 k_work_reschedule(&link.prot_timer, bt_mesh_prov_protocol_timeout_get());
808
809 err = send_unacked(adv, &buf_sent, user_data);
810 if (err) {
811 bt_mesh_adv_unref(adv);
812 }
813
814 return err;
815 }
816
prov_send_adv(struct net_buf_simple * msg,prov_bearer_send_complete_t cb,void * cb_data)817 static int prov_send_adv(struct net_buf_simple *msg,
818 prov_bearer_send_complete_t cb, void *cb_data)
819 {
820 struct bt_mesh_adv *start, *adv;
821 uint8_t seg_len, seg_id;
822
823 prov_clear_tx();
824 k_work_reschedule(&link.prot_timer, bt_mesh_prov_protocol_timeout_get());
825
826 start = adv_create(RETRANSMITS_RELIABLE);
827 if (!start) {
828 return -ENOBUFS;
829 }
830
831 link.tx.id = next_transaction_id(link.tx.id);
832 net_buf_simple_add_be32(&start->b, link.id);
833 net_buf_simple_add_u8(&start->b, link.tx.id);
834
835 net_buf_simple_add_u8(&start->b, GPC_START(last_seg(msg->len)));
836 net_buf_simple_add_be16(&start->b, msg->len);
837 net_buf_simple_add_u8(&start->b, bt_mesh_fcs_calc(msg->data, msg->len));
838
839 link.tx.adv[0] = start;
840 link.tx.cb = cb;
841 link.tx.cb_data = cb_data;
842 link.tx.start = k_uptime_get();
843
844 LOG_DBG("xact_id: 0x%x len: %u", link.tx.id, msg->len);
845
846 seg_len = MIN(msg->len, START_PAYLOAD_MAX);
847 LOG_DBG("seg 0 len %u: %s", seg_len, bt_hex(msg->data, seg_len));
848 net_buf_simple_add_mem(&start->b, msg->data, seg_len);
849 net_buf_simple_pull(msg, seg_len);
850
851 adv = start;
852 for (seg_id = 1U; msg->len > 0; seg_id++) {
853 if (seg_id >= ARRAY_SIZE(link.tx.adv)) {
854 LOG_ERR("Too big message");
855 free_segments();
856 return -E2BIG;
857 }
858
859 adv = adv_create(RETRANSMITS_RELIABLE);
860 if (!adv) {
861 free_segments();
862 return -ENOBUFS;
863 }
864
865 link.tx.adv[seg_id] = adv;
866
867 seg_len = MIN(msg->len, CONT_PAYLOAD_MAX);
868
869 LOG_DBG("seg %u len %u: %s", seg_id, seg_len, bt_hex(msg->data, seg_len));
870
871 net_buf_simple_add_be32(&adv->b, link.id);
872 net_buf_simple_add_u8(&adv->b, link.tx.id);
873 net_buf_simple_add_u8(&adv->b, GPC_CONT(seg_id));
874 net_buf_simple_add_mem(&adv->b, msg->data, seg_len);
875 net_buf_simple_pull(msg, seg_len);
876 }
877
878 send_reliable();
879
880 return 0;
881 }
882
883 /*******************************************************************************
884 * Link management rx
885 ******************************************************************************/
886
link_open(struct prov_rx * rx,struct net_buf_simple * buf)887 static void link_open(struct prov_rx *rx, struct net_buf_simple *buf)
888 {
889 int err;
890
891 LOG_DBG("len %u", buf->len);
892
893 if (buf->len < 16) {
894 LOG_ERR("Too short bearer open message (len %u)", buf->len);
895 return;
896 }
897
898 if (atomic_test_bit(link.flags, ADV_LINK_ACTIVE)) {
899 /* Send another link ack if the provisioner missed the last */
900 if (link.id != rx->link_id) {
901 LOG_DBG("Ignoring bearer open: link already active");
902 return;
903 }
904
905 if (atomic_test_bit(link.flags, ADV_LINK_ACK_SENDING)) {
906 LOG_DBG("Still sending Link Ack");
907 return;
908 }
909
910 /* Ignore errors, message will be attempted again if we keep receiving link open: */
911 atomic_set_bit(link.flags, ADV_LINK_ACK_SENDING);
912 (void)bearer_ctl_send_unacked(
913 ctl_adv_create(LINK_ACK, NULL, 0, RETRANSMITS_ACK),
914 (void *)PROV_BEARER_LINK_STATUS_SUCCESS);
915 return;
916 }
917
918 if (memcmp(buf->data, bt_mesh_prov_get()->uuid, 16)) {
919 LOG_DBG("Bearer open message not for us");
920 return;
921 }
922
923 link.id = rx->link_id;
924 atomic_set_bit(link.flags, ADV_LINK_ACTIVE);
925 net_buf_simple_reset(link.rx.buf);
926
927 atomic_set_bit(link.flags, ADV_LINK_ACK_SENDING);
928 err = bearer_ctl_send_unacked(
929 ctl_adv_create(LINK_ACK, NULL, 0, RETRANSMITS_ACK),
930 (void *)PROV_BEARER_LINK_STATUS_SUCCESS);
931 if (err) {
932 reset_adv_link();
933 return;
934 }
935
936 link.cb->link_opened(&bt_mesh_pb_adv, link.cb_data);
937 }
938
link_ack(struct prov_rx * rx,struct net_buf_simple * buf)939 static void link_ack(struct prov_rx *rx, struct net_buf_simple *buf)
940 {
941 LOG_DBG("len %u", buf->len);
942
943 if (atomic_test_bit(link.flags, ADV_PROVISIONER)) {
944 if (atomic_test_and_set_bit(link.flags, ADV_LINK_ACK_RECVD)) {
945 return;
946 }
947
948 prov_clear_tx();
949
950 link.tx.timeout = TRANSACTION_TIMEOUT;
951
952 link.cb->link_opened(&bt_mesh_pb_adv, link.cb_data);
953 }
954 }
955
link_close(struct prov_rx * rx,struct net_buf_simple * buf)956 static void link_close(struct prov_rx *rx, struct net_buf_simple *buf)
957 {
958 LOG_DBG("len %u", buf->len);
959
960 if (buf->len != 1) {
961 return;
962 }
963
964 close_link(net_buf_simple_pull_u8(buf));
965 }
966
967 /*******************************************************************************
968 * Higher level functionality
969 ******************************************************************************/
970
bt_mesh_pb_adv_recv(struct net_buf_simple * buf)971 void bt_mesh_pb_adv_recv(struct net_buf_simple *buf)
972 {
973 struct prov_rx rx;
974
975 if (!link.cb) {
976 return;
977 }
978
979 if (buf->len < 6) {
980 LOG_WRN("Too short provisioning packet (len %u)", buf->len);
981 return;
982 }
983
984 rx.link_id = net_buf_simple_pull_be32(buf);
985 rx.xact_id = net_buf_simple_pull_u8(buf);
986 rx.gpc = net_buf_simple_pull_u8(buf);
987
988 if (atomic_test_bit(link.flags, ADV_LINK_ACTIVE) && link.id != rx.link_id) {
989 return;
990 }
991
992 LOG_DBG("link_id 0x%08x xact_id 0x%x", rx.link_id, rx.xact_id);
993
994 gen_prov_recv(&rx, buf);
995 }
996
prov_link_open(const uint8_t uuid[16],uint8_t timeout,const struct prov_bearer_cb * cb,void * cb_data)997 static int prov_link_open(const uint8_t uuid[16], uint8_t timeout,
998 const struct prov_bearer_cb *cb, void *cb_data)
999 {
1000 int err;
1001
1002 LOG_DBG("uuid %s", bt_hex(uuid, 16));
1003
1004 err = bt_mesh_adv_enable();
1005 if (err) {
1006 LOG_ERR("Failed enabling advertiser");
1007 return err;
1008 }
1009
1010 if (atomic_test_and_set_bit(link.flags, ADV_LINK_ACTIVE)) {
1011 return -EBUSY;
1012 }
1013
1014 atomic_set_bit(link.flags, ADV_PROVISIONER);
1015
1016 bt_rand(&link.id, sizeof(link.id));
1017 link.tx.id = XACT_ID_MAX;
1018 link.rx.id = XACT_ID_NVAL;
1019 link.cb = cb;
1020 link.cb_data = cb_data;
1021
1022 /* The link open time is configurable, but this will be changed to TRANSACTION_TIMEOUT once
1023 * the link is established.
1024 */
1025 link.tx.timeout = timeout;
1026
1027 net_buf_simple_reset(link.rx.buf);
1028
1029 return bearer_ctl_send(ctl_adv_create(LINK_OPEN, uuid, 16, RETRANSMITS_RELIABLE));
1030 }
1031
prov_link_accept(const struct prov_bearer_cb * cb,void * cb_data)1032 static int prov_link_accept(const struct prov_bearer_cb *cb, void *cb_data)
1033 {
1034 int err;
1035
1036 err = bt_mesh_adv_enable();
1037 if (err) {
1038 LOG_ERR("Failed enabling advertiser");
1039 return err;
1040 }
1041
1042 if (atomic_test_bit(link.flags, ADV_LINK_ACTIVE)) {
1043 return -EBUSY;
1044 }
1045
1046 link.rx.id = XACT_ID_MAX;
1047 link.tx.id = XACT_ID_NVAL;
1048 link.cb = cb;
1049 link.cb_data = cb_data;
1050 link.tx.timeout = TRANSACTION_TIMEOUT;
1051
1052 /* Make sure we're scanning for provisioning invitations */
1053 bt_mesh_scan_enable();
1054 /* Enable unprovisioned beacon sending */
1055 bt_mesh_beacon_enable();
1056
1057 return 0;
1058 }
1059
prov_link_close(enum prov_bearer_link_status status)1060 static void prov_link_close(enum prov_bearer_link_status status)
1061 {
1062 int err;
1063
1064 if (atomic_test_and_set_bit(link.flags, ADV_LINK_CLOSING)) {
1065 return;
1066 }
1067
1068 /*
1069 * According to MshPRTv1.1: 5.3.1.4.3, the close message should
1070 * be restransmitted at least three times. Retransmit the LINK_CLOSE
1071 * message until CLOSING_TIMEOUT has elapsed.
1072 */
1073 link.tx.timeout = CLOSING_TIMEOUT;
1074 /* Ignore errors, the link will time out eventually if this doesn't get sent */
1075 err = bearer_ctl_send_unacked(
1076 ctl_adv_create(LINK_CLOSE, &status, 1, RETRANSMITS_LINK_CLOSE),
1077 (void *)status);
1078 if (err) {
1079 close_link(status);
1080 }
1081 }
1082
bt_mesh_pb_adv_init(void)1083 void bt_mesh_pb_adv_init(void)
1084 {
1085 k_work_init_delayable(&link.prot_timer, protocol_timeout);
1086 k_work_init_delayable(&link.tx.retransmit, prov_retransmit);
1087 }
1088
bt_mesh_pb_adv_reset(void)1089 void bt_mesh_pb_adv_reset(void)
1090 {
1091 reset_adv_link();
1092 }
1093
1094 const struct prov_bearer bt_mesh_pb_adv = {
1095 .type = BT_MESH_PROV_ADV,
1096 .link_open = prov_link_open,
1097 .link_accept = prov_link_accept,
1098 .link_close = prov_link_close,
1099 .send = prov_send_adv,
1100 .clear_tx = prov_clear_tx,
1101 };
1102