1 /** @file
2  *  @brief Bluetooth Mesh Access Layer APIs.
3  */
4 
5 /*
6  * Copyright (c) 2017 Intel Corporation
7  * Additional Copyright (c) 2018 Espressif Systems (Shanghai) PTE LTD
8  *
9  * SPDX-License-Identifier: Apache-2.0
10  */
11 #ifndef _BLE_MESH_ACCESS_H_
12 #define _BLE_MESH_ACCESS_H_
13 
14 #include "mesh_config.h"
15 #include "mesh_buf.h"
16 #include "mesh_timer.h"
17 
18 /**
19  * @brief Bluetooth Mesh Access Layer
20  * @defgroup bt_mesh_access Bluetooth Mesh Access Layer
21  * @ingroup bt_mesh
22  * @{
23  */
24 
25 #ifdef __cplusplus
26 extern "C" {
27 #endif
28 
29 #define BLE_MESH_CID_NVAL          0xFFFF
30 
31 #define BLE_MESH_ADDR_UNASSIGNED   0x0000
32 #define BLE_MESH_ADDR_ALL_NODES    0xffff
33 #define BLE_MESH_ADDR_PROXIES      0xfffc
34 #define BLE_MESH_ADDR_FRIENDS      0xfffd
35 #define BLE_MESH_ADDR_RELAYS       0xfffe
36 
37 #define BLE_MESH_KEY_UNUSED        0xffff
38 #define BLE_MESH_KEY_DEV           0xfffe
39 
40 /** Helper to define a mesh element within an array.
41  *
42  *  In case the element has no SIG or Vendor models the helper
43  *  macro BLE_MESH_MODEL_NONE can be given instead.
44  *
45  *  @param _loc       Location Descriptor.
46  *  @param _mods      Array of models.
47  *  @param _vnd_mods  Array of vendor models.
48  */
49 #define BLE_MESH_ELEM(_loc, _mods, _vnd_mods)   \
50 {                                               \
51     .loc              = (_loc),                 \
52     .model_count      = ARRAY_SIZE(_mods),      \
53     .models           = (_mods),                \
54     .vnd_model_count  = ARRAY_SIZE(_vnd_mods),  \
55     .vnd_models       = (_vnd_mods),            \
56 }
57 
58 /** Abstraction that describes a Mesh Element */
59 struct bt_mesh_elem {
60     /* Unicast Address. Set at runtime during provisioning. */
61     uint16_t addr;
62 
63     /* Location Descriptor (GATT Bluetooth Namespace Descriptors) */
64     const uint16_t loc;
65 
66     const uint8_t model_count;
67     const uint8_t vnd_model_count;
68 
69     struct bt_mesh_model *const models;
70     struct bt_mesh_model *const vnd_models;
71 };
72 
73 /* Foundation Models */
74 #define BLE_MESH_MODEL_ID_CFG_SRV                   0x0000
75 #define BLE_MESH_MODEL_ID_CFG_CLI                   0x0001
76 #define BLE_MESH_MODEL_ID_HEALTH_SRV                0x0002
77 #define BLE_MESH_MODEL_ID_HEALTH_CLI                0x0003
78 
79 /* Models from the Mesh Model Specification */
80 #define BLE_MESH_MODEL_ID_GEN_ONOFF_SRV             0x1000
81 #define BLE_MESH_MODEL_ID_GEN_ONOFF_CLI             0x1001
82 #define BLE_MESH_MODEL_ID_GEN_LEVEL_SRV             0x1002
83 #define BLE_MESH_MODEL_ID_GEN_LEVEL_CLI             0x1003
84 #define BLE_MESH_MODEL_ID_GEN_DEF_TRANS_TIME_SRV    0x1004
85 #define BLE_MESH_MODEL_ID_GEN_DEF_TRANS_TIME_CLI    0x1005
86 #define BLE_MESH_MODEL_ID_GEN_POWER_ONOFF_SRV       0x1006
87 #define BLE_MESH_MODEL_ID_GEN_POWER_ONOFF_SETUP_SRV 0x1007
88 #define BLE_MESH_MODEL_ID_GEN_POWER_ONOFF_CLI       0x1008
89 #define BLE_MESH_MODEL_ID_GEN_POWER_LEVEL_SRV       0x1009
90 #define BLE_MESH_MODEL_ID_GEN_POWER_LEVEL_SETUP_SRV 0x100a
91 #define BLE_MESH_MODEL_ID_GEN_POWER_LEVEL_CLI       0x100b
92 #define BLE_MESH_MODEL_ID_GEN_BATTERY_SRV           0x100c
93 #define BLE_MESH_MODEL_ID_GEN_BATTERY_CLI           0x100d
94 #define BLE_MESH_MODEL_ID_GEN_LOCATION_SRV          0x100e
95 #define BLE_MESH_MODEL_ID_GEN_LOCATION_SETUP_SRV    0x100f
96 #define BLE_MESH_MODEL_ID_GEN_LOCATION_CLI          0x1010
97 #define BLE_MESH_MODEL_ID_GEN_ADMIN_PROP_SRV        0x1011
98 #define BLE_MESH_MODEL_ID_GEN_MANUFACTURER_PROP_SRV 0x1012
99 #define BLE_MESH_MODEL_ID_GEN_USER_PROP_SRV         0x1013
100 #define BLE_MESH_MODEL_ID_GEN_CLIENT_PROP_SRV       0x1014
101 #define BLE_MESH_MODEL_ID_GEN_PROP_CLI              0x1015
102 #define BLE_MESH_MODEL_ID_SENSOR_SRV                0x1100
103 #define BLE_MESH_MODEL_ID_SENSOR_SETUP_SRV          0x1101
104 #define BLE_MESH_MODEL_ID_SENSOR_CLI                0x1102
105 #define BLE_MESH_MODEL_ID_TIME_SRV                  0x1200
106 #define BLE_MESH_MODEL_ID_TIME_SETUP_SRV            0x1201
107 #define BLE_MESH_MODEL_ID_TIME_CLI                  0x1202
108 #define BLE_MESH_MODEL_ID_SCENE_SRV                 0x1203
109 #define BLE_MESH_MODEL_ID_SCENE_SETUP_SRV           0x1204
110 #define BLE_MESH_MODEL_ID_SCENE_CLI                 0x1205
111 #define BLE_MESH_MODEL_ID_SCHEDULER_SRV             0x1206
112 #define BLE_MESH_MODEL_ID_SCHEDULER_SETUP_SRV       0x1207
113 #define BLE_MESH_MODEL_ID_SCHEDULER_CLI             0x1208
114 #define BLE_MESH_MODEL_ID_LIGHT_LIGHTNESS_SRV       0x1300
115 #define BLE_MESH_MODEL_ID_LIGHT_LIGHTNESS_SETUP_SRV 0x1301
116 #define BLE_MESH_MODEL_ID_LIGHT_LIGHTNESS_CLI       0x1302
117 #define BLE_MESH_MODEL_ID_LIGHT_CTL_SRV             0x1303
118 #define BLE_MESH_MODEL_ID_LIGHT_CTL_SETUP_SRV       0x1304
119 #define BLE_MESH_MODEL_ID_LIGHT_CTL_CLI             0x1305
120 #define BLE_MESH_MODEL_ID_LIGHT_CTL_TEMP_SRV        0x1306
121 #define BLE_MESH_MODEL_ID_LIGHT_HSL_SRV             0x1307
122 #define BLE_MESH_MODEL_ID_LIGHT_HSL_SETUP_SRV       0x1308
123 #define BLE_MESH_MODEL_ID_LIGHT_HSL_CLI             0x1309
124 #define BLE_MESH_MODEL_ID_LIGHT_HSL_HUE_SRV         0x130a
125 #define BLE_MESH_MODEL_ID_LIGHT_HSL_SAT_SRV         0x130b
126 #define BLE_MESH_MODEL_ID_LIGHT_XYL_SRV             0x130c
127 #define BLE_MESH_MODEL_ID_LIGHT_XYL_SETUP_SRV       0x130d
128 #define BLE_MESH_MODEL_ID_LIGHT_XYL_CLI             0x130e
129 #define BLE_MESH_MODEL_ID_LIGHT_LC_SRV              0x130f
130 #define BLE_MESH_MODEL_ID_LIGHT_LC_SETUP_SRV        0x1310
131 #define BLE_MESH_MODEL_ID_LIGHT_LC_CLI              0x1311
132 
133 /** Message sending context. */
134 struct bt_mesh_msg_ctx {
135     /** NetKey Index of the subnet to send the message on. */
136     uint16_t net_idx;
137 
138     /** AppKey Index to encrypt the message with. */
139     uint16_t app_idx;
140 
141     /** Remote address. */
142     uint16_t addr;
143 
144     /** Destination address of a received message. Not used for sending. */
145     uint16_t recv_dst;
146 
147     /** RSSI of received packet. Not used for sending. */
148     int8_t  recv_rssi;
149 
150     /** Received TTL value. Not used for sending. */
151     uint8_t  recv_ttl: 7;
152 
153     /** Force sending reliably by using segment acknowledgement */
154     uint8_t  send_rel: 1;
155 
156     /** TTL, or BLE_MESH_TTL_DEFAULT for default TTL. */
157     uint8_t  send_ttl;
158 
159     /** Change by Espressif, opcode of a received message.
160      *  Not used for sending message. */
161     uint32_t recv_op;
162 
163     /** Change by Espressif, model corresponds to the message */
164     struct bt_mesh_model *model;
165 
166     /** Change by Espressif, if the message is sent by a server
167      *  model. Not used for receiving message. */
168     bool srv_send;
169 };
170 
171 struct bt_mesh_model_op {
172     /* OpCode encoded using the BLE_MESH_MODEL_OP_* macros */
173     const uint32_t  opcode;
174 
175     /* Minimum required message length */
176     const size_t min_len;
177 
178     /* Message handler for the opcode */
179     void (*const func)(struct bt_mesh_model *model,
180                        struct bt_mesh_msg_ctx *ctx,
181                        struct net_buf_simple *buf);
182 };
183 
184 #define BLE_MESH_MODEL_OP_1(b0)         (b0)
185 #define BLE_MESH_MODEL_OP_2(b0, b1)     (((b0) << 8) | (b1))
186 #define BLE_MESH_MODEL_OP_3(b0, cid)    ((((b0) << 16) | 0xc00000) | (cid))
187 
188 #define BLE_MESH_MODEL_OP_END           { 0, 0, NULL }
189 #define BLE_MESH_MODEL_NO_OPS           ((struct bt_mesh_model_op []) \
190                                         { BLE_MESH_MODEL_OP_END })
191 
192 /** Helper to define an empty model array */
193 #define BLE_MESH_MODEL_NONE             ((struct bt_mesh_model []){})
194 
195 /** Length of a short Mesh MIC. */
196 #define BLE_MESH_MIC_SHORT              4
197 /** Length of a long Mesh MIC. */
198 #define BLE_MESH_MIC_LONG               8
199 
200 /** @def BLE_MESH_MODEL_OP_LEN
201  *
202  * @brief Helper to determine the length of an opcode.
203  *
204  * @param _op Opcode.
205  */
206 #define BLE_MESH_MODEL_OP_LEN(_op) ((_op) <= 0xff ? 1 : (_op) <= 0xffff ? 2 : 3)
207 
208 /** @def BLE_MESH_MODEL_BUF_LEN
209  *
210  * @brief Helper for model message buffer length.
211  *
212  * Returns the length of a Mesh model message buffer, including the opcode
213  * length and a short MIC.
214  *
215  * @param _op Opcode of the message.
216  * @param _payload_len Length of the model payload.
217  */
218 #define BLE_MESH_MODEL_BUF_LEN(_op, _payload_len)                \
219         (BLE_MESH_MODEL_OP_LEN(_op) + (_payload_len) + BLE_MESH_MIC_SHORT)
220 
221 /** @def BLE_MESH_MODEL_BUF_LEN_LONG_MIC
222  *
223  * @brief Helper for model message buffer length.
224  *
225  * Returns the length of a Mesh model message buffer, including the opcode
226  * length and a long MIC.
227  *
228  * @param _op Opcode of the message.
229  * @param _payload_len Length of the model payload.
230  */
231 #define BLE_MESH_MODEL_BUF_LEN_LONG_MIC(_op, _payload_len)       \
232         (BLE_MESH_MODEL_OP_LEN(_op) + (_payload_len) + BLE_MESH_MIC_LONG)
233 
234 /** @def BLE_MESH_MODEL_BUF_DEFINE
235  *
236  * @brief Define a Mesh model message buffer using @ref NET_BUF_SIMPLE_DEFINE.
237  *
238  * @param _buf Buffer name.
239  * @param _op Opcode of the message.
240  * @param _payload_len Length of the model message payload.
241  */
242 #define BLE_MESH_MODEL_BUF_DEFINE(_buf, _op, _payload_len)       \
243         NET_BUF_SIMPLE_DEFINE(_buf, BLE_MESH_MODEL_BUF_LEN((_op), (_payload_len)))
244 
245 /** @def BLE_MESH_MODEL_CB
246  *
247  *  @brief Composition data SIG model entry with callback functions.
248  *
249  *  @param _id        Model ID.
250  *  @param _op        Array of model opcode handlers.
251  *  @param _pub       Model publish parameters.
252  *  @param _user_data User data for the model.
253  *  @param _cb        Callback structure, or NULL to keep no callbacks.
254  */
255 #define BLE_MESH_MODEL_CB(_id, _op, _pub, _user_data, _cb)          \
256 {                                                                   \
257     .id = (_id),                                                    \
258     .op = (_op),                                                    \
259     .keys = { [0 ... (CONFIG_BLE_MESH_MODEL_KEY_COUNT - 1)] =       \
260             BLE_MESH_KEY_UNUSED },                                  \
261     .pub = (_pub),                                                  \
262     .groups = { [0 ... (CONFIG_BLE_MESH_MODEL_GROUP_COUNT - 1)] =   \
263             BLE_MESH_ADDR_UNASSIGNED },                             \
264     .user_data = (_user_data),                                      \
265     .cb = (_cb),                                                    \
266 }
267 
268 /** @def BLE_MESH_MODEL_VND_CB
269  *
270  *  @brief Composition data vendor model entry with callback functions.
271  *
272  *  @param _company   Company ID.
273  *  @param _id        Model ID.
274  *  @param _op        Array of model opcode handlers.
275  *  @param _pub       Model publish parameters.
276  *  @param _user_data User data for the model.
277  *  @param _cb        Callback structure, or NULL to keep no callbacks.
278  */
279 #define BLE_MESH_MODEL_VND_CB(_company, _id, _op, _pub, _user_data, _cb) \
280 {                                                                   \
281     .vnd.company = (_company),                                      \
282     .vnd.id = (_id),                                                \
283     .op = (_op),                                                    \
284     .pub = (_pub),                                                  \
285     .keys = { [0 ... (CONFIG_BLE_MESH_MODEL_KEY_COUNT - 1)] =       \
286             BLE_MESH_KEY_UNUSED },                                  \
287     .groups = { [0 ... (CONFIG_BLE_MESH_MODEL_GROUP_COUNT - 1)] =   \
288             BLE_MESH_ADDR_UNASSIGNED },                             \
289     .user_data = (_user_data),                                      \
290     .cb = (_cb),                                                    \
291 }
292 
293 /** @def BLE_MESH_TRANSMIT
294  *
295  *  @brief Encode transmission count & interval steps.
296  *
297  *  @param count   Number of retransmissions (first transmission is excluded).
298  *  @param int_ms  Interval steps in milliseconds. Must be greater than 0
299  *                 and a multiple of 10.
300  *
301  *  @return Mesh transmit value that can be used e.g. for the default
302  *          values of the configuration model data.
303  */
304 #define BLE_MESH_TRANSMIT(count, int_ms) ((count) | ((((int_ms) / 10) - 1) << 3))
305 
306 /** @def BLE_MESH_TRANSMIT_COUNT
307  *
308  *  @brief Decode transmit count from a transmit value.
309  *
310  *  @param transmit Encoded transmit count & interval value.
311  *
312  *  @return Transmission count (actual transmissions is N + 1).
313  */
314 #define BLE_MESH_TRANSMIT_COUNT(transmit) (((transmit) & (uint8_t)BIT_MASK(3)))
315 
316 /** @def BLE_MESH_TRANSMIT_INT
317  *
318  *  @brief Decode transmit interval from a transmit value.
319  *
320  *  @param transmit Encoded transmit count & interval value.
321  *
322  *  @return Transmission interval in milliseconds.
323  */
324 #define BLE_MESH_TRANSMIT_INT(transmit) ((((transmit) >> 3) + 1) * 10)
325 
326 /** @def BLE_MESH_PUB_TRANSMIT
327  *
328  *  @brief Encode Publish Retransmit count & interval steps.
329  *
330  *  @param count   Number of retransmissions (first transmission is excluded).
331  *  @param int_ms  Interval steps in milliseconds. Must be greater than 0
332  *                 and a multiple of 50.
333  *
334  *  @return Mesh transmit value that can be used e.g. for the default
335  *          values of the configuration model data.
336  */
337 #define BLE_MESH_PUB_TRANSMIT(count, int_ms) BLE_MESH_TRANSMIT((count), (int_ms) / 5)
338 
339 /** @def BLE_MESH_PUB_TRANSMIT_COUNT
340  *
341  *  @brief Decode Publish Retransmit count from a given value.
342  *
343  *  @param transmit Encoded Publish Retransmit count & interval value.
344  *
345  *  @return Retransmission count (actual transmissions is N + 1).
346  */
347 #define BLE_MESH_PUB_TRANSMIT_COUNT(transmit) BLE_MESH_TRANSMIT_COUNT(transmit)
348 
349 /** @def BLE_MESH_PUB_TRANSMIT_INT
350  *
351  *  @brief Decode Publish Retransmit interval from a given value.
352  *
353  *  @param transmit Encoded Publish Retransmit count & interval value.
354  *
355  *  @return Transmission interval in milliseconds.
356  */
357 #define BLE_MESH_PUB_TRANSMIT_INT(transmit) ((((transmit) >> 3) + 1) * 50)
358 
359 /** Model publication context. */
360 struct bt_mesh_model_pub {
361     /** The model the context belongs to. Initialized by the stack. */
362     struct bt_mesh_model *mod;
363 
364     uint16_t addr;          /**< Publish Address. */
365     uint16_t key:12,        /**< Publish AppKey Index. */
366              cred:1,        /**< Friendship Credentials Flag. */
367              send_rel:1;    /**< Force reliable sending (segment acks) */
368 
369     uint8_t  ttl;           /**< Publish Time to Live. */
370     uint8_t  retransmit;    /**< Retransmit Count & Interval Steps. */
371     uint8_t  period;        /**< Publish Period. */
372     uint8_t  period_div:4,  /**< Divisor for the Period. */
373              fast_period:1, /**< Use FastPeriodDivisor */
374              count:3;       /**< Retransmissions left. */
375 
376     uint32_t period_start;  /**< Start of the current period. */
377 
378     /** @brief Publication buffer, containing the publication message.
379      *
380      *  This will get correctly created when the publication context
381      *  has been defined using the BLE_MESH_MODEL_PUB_DEFINE macro.
382      *
383      *  BLE_MESH_MODEL_PUB_DEFINE(name, update, size);
384      */
385     struct net_buf_simple *msg;
386 
387     /** @brief Callback for updating the publication buffer.
388      *
389      *  When set to NULL, the model is assumed not to support
390      *  periodic publishing. When set to non-NULL the callback
391      *  will be called periodically and is expected to update
392      *  @ref bt_mesh_model_pub.msg with a valid publication
393      *  message.
394      *
395      *  If the callback returns non-zero, the publication is skipped
396      *  and will resume on the next periodic publishing interval.
397      *
398      *  @param mod The Model the Publication Context belongs to.
399      *
400      *  @return Zero on success or (negative) error code otherwise.
401      */
402     int (*update)(struct bt_mesh_model *mod);
403 
404     /** Publish Period Timer. Only for stack-internal use. */
405     struct k_delayed_work timer;
406 
407     /* Change by Espressif, role of the device going to publish messages */
408     uint8_t dev_role;
409 };
410 
411 /** @def BLE_MESH_MODEL_PUB_DEFINE
412  *
413  *  Define a model publication context.
414  *
415  *  @param _name Variable name given to the context.
416  *  @param _update Optional message update callback (may be NULL).
417  *  @param _msg_len Length of the publication message.
418  */
419 #define BLE_MESH_MODEL_PUB_DEFINE(_name, _update, _msg_len) \
420     NET_BUF_SIMPLE_DEFINE_STATIC(bt_mesh_pub_msg_##_name, _msg_len); \
421     static struct bt_mesh_model_pub _name = { \
422         .update = _update, \
423         .msg = &bt_mesh_pub_msg_##_name, \
424     }
425 
426 /** Model callback functions. */
427 struct bt_mesh_model_cb {
428     /** @brief Model init callback.
429      *
430      *  Called on every model instance during mesh initialization.
431      *
432      *  If any of the model init callbacks return an error, the mesh
433      *  subsystem initialization will be aborted, and the error will
434      *  be returned to the caller of @ref bt_mesh_init.
435      *
436      *  @param model Model to be initialized.
437      *
438      *  @return 0 on success, error otherwise.
439      */
440     int (*const init)(struct bt_mesh_model *model);
441 
442 #if CONFIG_BLE_MESH_DEINIT
443     /** @brief Model deinit callback.
444      *
445      *  Called on every model instance during mesh deinitialization.
446      *  All model data is deleted, and the model should clear its state.
447      *
448      *  If any of the model deinit callbacks return an error, the mesh
449      *  subsystem deinitialization will be aborted, and the error will
450      *  be returned to the caller of @ref bt_mesh_deinit.
451      *
452      *  @param model Model to be de-initialized.
453      */
454     int (*const deinit)(struct bt_mesh_model *model);
455 #endif /* CONFIG_BLE_MESH_DEINIT */
456 };
457 
458 /** Abstraction that describes a Mesh Model instance */
459 struct bt_mesh_model {
460     union {
461         const uint16_t id;
462         struct {
463             uint16_t company;
464             uint16_t id;
465         } vnd;
466     };
467 
468     /* Internal information, mainly for persistent storage */
469     uint8_t  elem_idx;  /* Belongs to Nth element */
470     uint8_t  model_idx; /* Is the Nth model in the element */
471     uint16_t flags;     /* Information about what has changed */
472 
473     /* The Element this Model belongs to */
474     struct bt_mesh_elem *elem;
475 
476     /* Model Publication */
477     struct bt_mesh_model_pub *const pub;
478 
479     /* AppKey List */
480     uint16_t keys[CONFIG_BLE_MESH_MODEL_KEY_COUNT];
481 
482     /* Subscription List (group or virtual addresses) */
483     uint16_t groups[CONFIG_BLE_MESH_MODEL_GROUP_COUNT];
484 
485     /** Opcode handler list */
486     const struct bt_mesh_model_op *const op;
487 
488     /** Model callback structure. */
489     const struct bt_mesh_model_cb *const cb;
490 
491     /* Model-specific user data */
492     void *user_data;
493 };
494 
495 struct bt_mesh_send_cb {
496     void (*start)(uint16_t duration, int err, void *cb_data);
497     void (*end)(int err, void *cb_data);
498 };
499 
500 void bt_mesh_model_msg_init(struct net_buf_simple *msg, uint32_t opcode);
501 
502 /** Special TTL value to request using configured default TTL */
503 #define BLE_MESH_TTL_DEFAULT    0xff
504 
505 /** Maximum allowed TTL value */
506 #define BLE_MESH_TTL_MAX        0x7f
507 
508 /**
509  * @brief Send an Access Layer message.
510  *
511  * @param model     Mesh (client) Model that the message belongs to.
512  * @param ctx       Message context, includes keys, TTL, etc.
513  * @param msg       Access Layer payload (the actual message to be sent).
514  * @param cb        Optional "message sent" callback.
515  * @param cb_data   User data to be passed to the callback.
516  *
517  * @return 0 on success, or (negative) error code on failure.
518  */
519 int bt_mesh_model_send(struct bt_mesh_model *model,
520                        struct bt_mesh_msg_ctx *ctx,
521                        struct net_buf_simple *msg,
522                        const struct bt_mesh_send_cb *cb,
523                        void *cb_data);
524 
525 /**
526  * @brief Send a model publication message.
527  *
528  * Before calling this function, the user needs to ensure that the model
529  * publication message (@ref bt_mesh_model_pub.msg) contains a valid
530  * message to be sent. Note that this API is only to be used for
531  * non-period publishing. For periodic publishing the app only needs
532  * to make sure that @ref bt_mesh_model_pub.msg contains a valid message
533  * whenever the @ref bt_mesh_model_pub.update callback is called.
534  *
535  * @param model  Mesh (client) Model that's publishing the message.
536  *
537  * @return 0 on success, or (negative) error code on failure.
538  */
539 int bt_mesh_model_publish(struct bt_mesh_model *model);
540 
541 /**
542  * @brief Get the element that a model belongs to.
543  *
544  * @param mod  Mesh model.
545  *
546  * @return Pointer to the element that the given model belongs to.
547  */
548 struct bt_mesh_elem *bt_mesh_model_elem(struct bt_mesh_model *mod);
549 
550 /** @brief Find a SIG model.
551  *
552  *  @param elem Element to search for the model in.
553  *  @param id   Model ID of the model.
554  *
555  *  @return A pointer to the Mesh model matching the given parameters, or NULL
556  *          if no SIG model with the given ID exists in the given element.
557  */
558 struct bt_mesh_model *bt_mesh_model_find(struct bt_mesh_elem *elem, uint16_t id);
559 
560 /** @brief Find a vendor model.
561  *
562  *  @param elem    Element to search for the model in.
563  *  @param company Company ID of the model.
564  *  @param id      Model ID of the model.
565  *
566  *  @return A pointer to the Mesh model matching the given parameters, or NULL
567  *          if no vendor model with the given ID exists in the given element.
568  */
569 struct bt_mesh_model *bt_mesh_model_find_vnd(struct bt_mesh_elem *elem,
570                                              uint16_t company, uint16_t id);
571 
572 /** @brief Get whether the model is in the primary element of the device.
573  *
574  *  @param mod Mesh model.
575  *
576  *  @return true if the model is on the primary element, false otherwise.
577  */
bt_mesh_model_in_primary(const struct bt_mesh_model * mod)578 static inline bool bt_mesh_model_in_primary(const struct bt_mesh_model *mod)
579 {
580     return (mod->elem_idx == 0);
581 }
582 
583 /** Node Composition */
584 struct bt_mesh_comp {
585     uint16_t cid;
586     uint16_t pid;
587     uint16_t vid;
588 
589     size_t elem_count;
590     struct bt_mesh_elem *elem;
591 };
592 
593 #ifdef __cplusplus
594 }
595 #endif
596 
597 /**
598  * @}
599  */
600 
601 #endif /* __BLE_MESH_ACCESS_H */
602