1 // Copyright 2017-2019 Espressif Systems (Shanghai) PTE LTD
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 
7 //     http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 #include <string.h>
16 #include <errno.h>
17 
18 #include "btc_ble_mesh_health_model.h"
19 #include "foundation.h"
20 #include "esp_ble_mesh_health_model_api.h"
21 
22 #if CONFIG_BLE_MESH_HEALTH_CLI
23 #include "health_cli.h"
24 
25 /* Health Client Model related functions */
26 
btc_ble_mesh_health_client_cb_to_app(esp_ble_mesh_health_client_cb_event_t event,esp_ble_mesh_health_client_cb_param_t * param)27 static inline void btc_ble_mesh_health_client_cb_to_app(esp_ble_mesh_health_client_cb_event_t event,
28                                                         esp_ble_mesh_health_client_cb_param_t *param)
29 {
30     esp_ble_mesh_health_client_cb_t btc_ble_mesh_cb =
31         (esp_ble_mesh_health_client_cb_t)btc_profile_cb_get(BTC_PID_HEALTH_CLIENT);
32     if (btc_ble_mesh_cb) {
33         btc_ble_mesh_cb(event, param);
34     }
35 }
36 
btc_ble_mesh_health_client_arg_deep_copy(btc_msg_t * msg,void * p_dest,void * p_src)37 void btc_ble_mesh_health_client_arg_deep_copy(btc_msg_t *msg, void *p_dest, void *p_src)
38 {
39     btc_ble_mesh_health_client_args_t *dst = (btc_ble_mesh_health_client_args_t *)p_dest;
40     btc_ble_mesh_health_client_args_t *src = (btc_ble_mesh_health_client_args_t *)p_src;
41 
42     if (!msg || !dst || !src) {
43         BT_ERR("%s, Invalid parameter", __func__);
44         return;
45     }
46 
47     switch (msg->act) {
48     case BTC_BLE_MESH_ACT_HEALTH_CLIENT_GET_STATE: {
49         dst->health_client_get_state.params = (esp_ble_mesh_client_common_param_t *)bt_mesh_malloc(sizeof(esp_ble_mesh_client_common_param_t));
50         if (dst->health_client_get_state.params) {
51             memcpy(dst->health_client_get_state.params, src->health_client_get_state.params,
52                    sizeof(esp_ble_mesh_client_common_param_t));
53         } else {
54             BT_ERR("%s, Out of memory, act %d", __func__, msg->act);
55             break;
56         }
57         if (src->health_client_get_state.get_state) {
58             dst->health_client_get_state.get_state = (esp_ble_mesh_health_client_get_state_t *)bt_mesh_malloc(sizeof(esp_ble_mesh_health_client_get_state_t));
59             if (dst->health_client_get_state.get_state) {
60                 memcpy(dst->health_client_get_state.get_state, src->health_client_get_state.get_state,
61                     sizeof(esp_ble_mesh_health_client_get_state_t));
62             } else {
63                 BT_ERR("%s, Out of memory, act %d", __func__, msg->act);
64             }
65         }
66         break;
67     }
68     case BTC_BLE_MESH_ACT_HEALTH_CLIENT_SET_STATE: {
69         dst->health_client_set_state.params = (esp_ble_mesh_client_common_param_t *)bt_mesh_malloc(sizeof(esp_ble_mesh_client_common_param_t));
70         dst->health_client_set_state.set_state = (esp_ble_mesh_health_client_set_state_t *)bt_mesh_malloc(sizeof(esp_ble_mesh_health_client_set_state_t));
71         if (dst->health_client_set_state.params && dst->health_client_set_state.set_state) {
72             memcpy(dst->health_client_set_state.params, src->health_client_set_state.params,
73                    sizeof(esp_ble_mesh_client_common_param_t));
74             memcpy(dst->health_client_set_state.set_state, src->health_client_set_state.set_state,
75                    sizeof(esp_ble_mesh_health_client_set_state_t));
76         } else {
77             BT_ERR("%s, Out of memory, act %d", __func__, msg->act);
78         }
79         break;
80     }
81     default:
82         BT_DBG("%s, Unknown act %d", __func__, msg->act);
83         break;
84     }
85 }
86 
btc_ble_mesh_health_client_arg_deep_free(btc_msg_t * msg)87 static void btc_ble_mesh_health_client_arg_deep_free(btc_msg_t *msg)
88 {
89     btc_ble_mesh_health_client_args_t *arg = NULL;
90 
91     if (!msg || !msg->arg) {
92         BT_ERR("%s, Invalid parameter", __func__);
93         return;
94     }
95 
96     arg = (btc_ble_mesh_health_client_args_t *)(msg->arg);
97 
98     switch (msg->act) {
99     case BTC_BLE_MESH_ACT_HEALTH_CLIENT_GET_STATE:
100         if (arg->health_client_get_state.params) {
101             bt_mesh_free(arg->health_client_get_state.params);
102         }
103         if (arg->health_client_get_state.get_state) {
104             bt_mesh_free(arg->health_client_get_state.get_state);
105         }
106         break;
107     case BTC_BLE_MESH_ACT_HEALTH_CLIENT_SET_STATE:
108         if (arg->health_client_set_state.params) {
109             bt_mesh_free(arg->health_client_set_state.params);
110         }
111         if (arg->health_client_set_state.set_state) {
112             bt_mesh_free(arg->health_client_set_state.set_state);
113         }
114         break;
115     default:
116         break;
117     }
118 }
119 
btc_ble_mesh_health_client_copy_req_data(btc_msg_t * msg,void * p_dest,void * p_src)120 static void btc_ble_mesh_health_client_copy_req_data(btc_msg_t *msg, void *p_dest, void *p_src)
121 {
122     esp_ble_mesh_health_client_cb_param_t *p_dest_data = (esp_ble_mesh_health_client_cb_param_t *)p_dest;
123     esp_ble_mesh_health_client_cb_param_t *p_src_data = (esp_ble_mesh_health_client_cb_param_t *)p_src;
124     uint16_t length = 0U;
125 
126     if (!msg || !p_src_data || !p_dest_data) {
127         BT_ERR("%s, Invalid parameter", __func__);
128         return;
129     }
130 
131     if (p_src_data->params) {
132         p_dest_data->params = bt_mesh_malloc(sizeof(esp_ble_mesh_client_common_param_t));
133         if (!p_dest_data->params) {
134             BT_ERR("%s, Out of memory, act %d", __func__, msg->act);
135             return;
136         }
137 
138         memcpy(p_dest_data->params, p_src_data->params, sizeof(esp_ble_mesh_client_common_param_t));
139     }
140 
141     switch (msg->act) {
142     case ESP_BLE_MESH_HEALTH_CLIENT_GET_STATE_EVT:
143     case ESP_BLE_MESH_HEALTH_CLIENT_SET_STATE_EVT:
144     case ESP_BLE_MESH_HEALTH_CLIENT_PUBLISH_EVT:
145         if (p_src_data->params) {
146             switch (p_src_data->params->opcode) {
147             case OP_HEALTH_CURRENT_STATUS:
148                 if (p_src_data->status_cb.current_status.fault_array) {
149                     length = p_src_data->status_cb.current_status.fault_array->len;
150                     p_dest_data->status_cb.current_status.fault_array = bt_mesh_alloc_buf(length);
151                     if (!p_dest_data->status_cb.current_status.fault_array) {
152                         BT_ERR("%s, Out of memory, act %d", __func__, msg->act);
153                         return;
154                     }
155                     net_buf_simple_add_mem(p_dest_data->status_cb.current_status.fault_array,
156                                            p_src_data->status_cb.current_status.fault_array->data,
157                                            p_src_data->status_cb.current_status.fault_array->len);
158                 }
159                 break;
160             case OP_HEALTH_FAULT_GET:
161             case OP_HEALTH_FAULT_CLEAR:
162             case OP_HEALTH_FAULT_TEST:
163             case OP_HEALTH_FAULT_STATUS:
164                 if (p_src_data->status_cb.fault_status.fault_array) {
165                     length = p_src_data->status_cb.fault_status.fault_array->len;
166                     p_dest_data->status_cb.fault_status.fault_array = bt_mesh_alloc_buf(length);
167                     if (!p_dest_data->status_cb.fault_status.fault_array) {
168                         BT_ERR("%s, Out of memory, act %d", __func__, msg->act);
169                         return;
170                     }
171                     net_buf_simple_add_mem(p_dest_data->status_cb.fault_status.fault_array,
172                                            p_src_data->status_cb.fault_status.fault_array->data,
173                                            p_src_data->status_cb.fault_status.fault_array->len);
174                 }
175                 break;
176             default:
177                 break;
178             }
179         }
180     case ESP_BLE_MESH_HEALTH_CLIENT_TIMEOUT_EVT:
181         break;
182     default:
183         break;
184     }
185 }
186 
btc_ble_mesh_health_client_free_req_data(btc_msg_t * msg)187 static void btc_ble_mesh_health_client_free_req_data(btc_msg_t *msg)
188 {
189     esp_ble_mesh_health_client_cb_param_t *arg = NULL;
190 
191     if (!msg || !msg->arg) {
192         BT_ERR("%s, Invalid parameter", __func__);
193         return;
194     }
195 
196     arg = (esp_ble_mesh_health_client_cb_param_t *)(msg->arg);
197 
198     switch (msg->act) {
199     case ESP_BLE_MESH_HEALTH_CLIENT_GET_STATE_EVT:
200     case ESP_BLE_MESH_HEALTH_CLIENT_SET_STATE_EVT:
201     case ESP_BLE_MESH_HEALTH_CLIENT_PUBLISH_EVT:
202         if (arg->params) {
203             switch (arg->params->opcode) {
204             case OP_HEALTH_CURRENT_STATUS:
205                 bt_mesh_free_buf(arg->status_cb.current_status.fault_array);
206                 break;
207             case OP_HEALTH_FAULT_GET:
208             case OP_HEALTH_FAULT_CLEAR:
209             case OP_HEALTH_FAULT_TEST:
210             case OP_HEALTH_FAULT_STATUS:
211                 bt_mesh_free_buf(arg->status_cb.fault_status.fault_array);
212                 break;
213             default:
214                 break;
215             }
216         }
217     case ESP_BLE_MESH_HEALTH_CLIENT_TIMEOUT_EVT:
218         if (arg->params) {
219             bt_mesh_free(arg->params);
220         }
221         break;
222     default:
223         break;
224     }
225 }
226 
btc_ble_mesh_health_client_callback(esp_ble_mesh_health_client_cb_param_t * cb_params,uint8_t act)227 static void btc_ble_mesh_health_client_callback(esp_ble_mesh_health_client_cb_param_t *cb_params, uint8_t act)
228 {
229     btc_msg_t msg = {0};
230 
231     BT_DBG("%s", __func__);
232 
233     /* If corresponding callback is not registered, event will not be posted. */
234     if (!btc_profile_cb_get(BTC_PID_HEALTH_CLIENT)) {
235         return;
236     }
237 
238     msg.sig = BTC_SIG_API_CB;
239     msg.pid = BTC_PID_HEALTH_CLIENT;
240     msg.act = act;
241 
242     btc_transfer_context(&msg, cb_params, sizeof(esp_ble_mesh_health_client_cb_param_t),
243                          btc_ble_mesh_health_client_copy_req_data);
244 }
245 
bt_mesh_health_client_cb_evt_to_btc(uint32_t opcode,uint8_t evt_type,struct bt_mesh_model * model,struct bt_mesh_msg_ctx * ctx,const uint8_t * val,uint16_t len)246 void bt_mesh_health_client_cb_evt_to_btc(uint32_t opcode, uint8_t evt_type,
247                                          struct bt_mesh_model *model,
248                                          struct bt_mesh_msg_ctx *ctx,
249                                          const uint8_t *val, uint16_t len)
250 {
251     esp_ble_mesh_health_client_cb_param_t cb_params = {0};
252     esp_ble_mesh_client_common_param_t params = {0};
253     uint8_t act = 0U;
254 
255     if (!model || !ctx) {
256         BT_ERR("%s, Invalid parameter", __func__);
257         return;
258     }
259 
260     switch (evt_type) {
261     case BTC_BLE_MESH_EVT_HEALTH_CLIENT_GET_STATE:
262         act = ESP_BLE_MESH_HEALTH_CLIENT_GET_STATE_EVT;
263         break;
264     case BTC_BLE_MESH_EVT_HEALTH_CLIENT_SET_STATE:
265         act = ESP_BLE_MESH_HEALTH_CLIENT_SET_STATE_EVT;
266         break;
267     case BTC_BLE_MESH_EVT_HEALTH_CLIENT_PUBLISH:
268         act = ESP_BLE_MESH_HEALTH_CLIENT_PUBLISH_EVT;
269         break;
270     case BTC_BLE_MESH_EVT_HEALTH_CLIENT_TIMEOUT:
271         act = ESP_BLE_MESH_HEALTH_CLIENT_TIMEOUT_EVT;
272         break;
273     default:
274         BT_ERR("Unknown Health client event type %d", evt_type);
275         return;
276     }
277 
278     params.opcode = opcode;
279     params.model = (esp_ble_mesh_model_t *)model;
280     params.ctx.net_idx = ctx->net_idx;
281     params.ctx.app_idx = ctx->app_idx;
282     params.ctx.addr = ctx->addr;
283     params.ctx.recv_ttl = ctx->recv_ttl;
284     params.ctx.recv_op = ctx->recv_op;
285     params.ctx.recv_dst = ctx->recv_dst;
286     params.ctx.recv_rssi = ctx->recv_rssi;
287     params.ctx.send_ttl = ctx->send_ttl;
288 
289     cb_params.error_code = 0;
290     cb_params.params = &params;
291 
292     if (val && len) {
293         memcpy(&cb_params.status_cb, val, MIN(len, sizeof(cb_params.status_cb)));
294     }
295 
296     btc_ble_mesh_health_client_callback(&cb_params, act);
297     return;
298 }
299 
btc_ble_mesh_health_publish_callback(uint32_t opcode,struct bt_mesh_model * model,struct bt_mesh_msg_ctx * ctx,struct net_buf_simple * buf)300 void btc_ble_mesh_health_publish_callback(uint32_t opcode, struct bt_mesh_model *model,
301                                           struct bt_mesh_msg_ctx *ctx,
302                                           struct net_buf_simple *buf)
303 {
304     if (!model || !ctx || !buf) {
305         BT_ERR("%s, Invalid parameter", __func__);
306         return;
307     }
308 
309     bt_mesh_health_client_cb_evt_to_btc(opcode, BTC_BLE_MESH_EVT_HEALTH_CLIENT_PUBLISH,
310                                         model, ctx, buf->data, buf->len);
311     return;
312 }
313 
btc_ble_mesh_health_client_get_state(esp_ble_mesh_client_common_param_t * params,esp_ble_mesh_health_client_get_state_t * get)314 static int btc_ble_mesh_health_client_get_state(esp_ble_mesh_client_common_param_t *params,
315                                                 esp_ble_mesh_health_client_get_state_t *get)
316 {
317     bt_mesh_client_common_param_t param = {0};
318 
319     if (params == NULL) {
320         BT_ERR("%s, Invalid parameter", __func__);
321         return -EINVAL;
322     }
323 
324     if (params->opcode == ESP_BLE_MESH_MODEL_OP_HEALTH_FAULT_GET && get == NULL) {
325         BT_ERR("Invalid Health Get");
326         return -EINVAL;
327     }
328 
329     param.opcode = params->opcode;
330     param.model = (struct bt_mesh_model *)params->model;
331     param.ctx.net_idx = params->ctx.net_idx;
332     param.ctx.app_idx = params->ctx.app_idx;
333     param.ctx.addr = params->ctx.addr;
334     param.ctx.send_rel = params->ctx.send_rel;
335     param.ctx.send_ttl = params->ctx.send_ttl;
336     param.msg_timeout = params->msg_timeout;
337     param.msg_role = params->msg_role;
338 
339     switch (param.opcode) {
340     case ESP_BLE_MESH_MODEL_OP_ATTENTION_GET:
341         return bt_mesh_health_attention_get(&param);
342     case ESP_BLE_MESH_MODEL_OP_HEALTH_PERIOD_GET:
343         return bt_mesh_health_period_get(&param);
344     case ESP_BLE_MESH_MODEL_OP_HEALTH_FAULT_GET:
345         return bt_mesh_health_fault_get(&param, get->fault_get.company_id);
346     default:
347         BT_ERR("Invalid Health Get opcode 0x%04x", param.opcode);
348         return -EINVAL;
349     }
350 
351     return 0;
352 }
353 
btc_ble_mesh_health_client_set_state(esp_ble_mesh_client_common_param_t * params,esp_ble_mesh_health_client_set_state_t * set)354 static int btc_ble_mesh_health_client_set_state(esp_ble_mesh_client_common_param_t *params,
355                                                 esp_ble_mesh_health_client_set_state_t *set)
356 {
357     bt_mesh_client_common_param_t param = {0};
358 
359     if (params == NULL || set == NULL) {
360         BT_ERR("%s, Invalid parameter", __func__);
361         return -EINVAL;
362     }
363 
364     param.opcode = params->opcode;
365     param.model = (struct bt_mesh_model *)params->model;
366     param.ctx.net_idx = params->ctx.net_idx;
367     param.ctx.app_idx = params->ctx.app_idx;
368     param.ctx.addr = params->ctx.addr;
369     param.ctx.send_rel = params->ctx.send_rel;
370     param.ctx.send_ttl = params->ctx.send_ttl;
371     param.msg_timeout = params->msg_timeout;
372     param.msg_role = params->msg_role;
373 
374     switch (param.opcode) {
375     case ESP_BLE_MESH_MODEL_OP_ATTENTION_SET:
376         return bt_mesh_health_attention_set(&param, set->attention_set.attention, true);
377     case ESP_BLE_MESH_MODEL_OP_ATTENTION_SET_UNACK:
378         return bt_mesh_health_attention_set(&param, set->attention_set.attention, false);
379     case ESP_BLE_MESH_MODEL_OP_HEALTH_PERIOD_SET:
380         return bt_mesh_health_period_set(&param, set->period_set.fast_period_divisor, true);
381     case ESP_BLE_MESH_MODEL_OP_HEALTH_PERIOD_SET_UNACK:
382         return bt_mesh_health_period_set(&param, set->period_set.fast_period_divisor, false);
383     case ESP_BLE_MESH_MODEL_OP_HEALTH_FAULT_TEST:
384         return bt_mesh_health_fault_test(&param, set->fault_test.company_id, set->fault_test.test_id, true);
385     case ESP_BLE_MESH_MODEL_OP_HEALTH_FAULT_TEST_UNACK:
386         return bt_mesh_health_fault_test(&param, set->fault_test.company_id, set->fault_test.test_id, false);
387     case ESP_BLE_MESH_MODEL_OP_HEALTH_FAULT_CLEAR:
388         return bt_mesh_health_fault_clear(&param, set->fault_clear.company_id, true);
389     case ESP_BLE_MESH_MODEL_OP_HEALTH_FAULT_CLEAR_UNACK:
390         return bt_mesh_health_fault_clear(&param, set->fault_clear.company_id, false);
391     default:
392         BT_ERR("Invalid Health Set opcode 0x%04x", param.opcode);
393         return -EINVAL;
394     }
395 
396     return 0;
397 }
398 
btc_ble_mesh_health_client_call_handler(btc_msg_t * msg)399 void btc_ble_mesh_health_client_call_handler(btc_msg_t *msg)
400 {
401     btc_ble_mesh_health_client_args_t *arg = NULL;
402     esp_ble_mesh_health_client_cb_param_t cb = {0};
403 
404     if (!msg || !msg->arg) {
405         BT_ERR("%s, Invalid parameter", __func__);
406         return;
407     }
408 
409     arg = (btc_ble_mesh_health_client_args_t *)(msg->arg);
410 
411     switch (msg->act) {
412     case BTC_BLE_MESH_ACT_HEALTH_CLIENT_GET_STATE: {
413         cb.params = arg->health_client_get_state.params;
414         cb.error_code = btc_ble_mesh_health_client_get_state(arg->health_client_get_state.params,
415                                                              arg->health_client_get_state.get_state);
416         if (cb.error_code) {
417             /* If send failed, callback error_code to app layer immediately */
418             btc_ble_mesh_health_client_callback(&cb, ESP_BLE_MESH_HEALTH_CLIENT_GET_STATE_EVT);
419         }
420         break;
421     }
422     case BTC_BLE_MESH_ACT_HEALTH_CLIENT_SET_STATE: {
423         cb.params = arg->health_client_set_state.params;
424         cb.error_code = btc_ble_mesh_health_client_set_state(arg->health_client_set_state.params,
425                                                              arg->health_client_set_state.set_state);
426         if (cb.error_code) {
427             /* If send failed, callback error_code to app layer immediately */
428             btc_ble_mesh_health_client_callback(&cb, ESP_BLE_MESH_HEALTH_CLIENT_SET_STATE_EVT);
429         }
430         break;
431     }
432     default:
433         break;
434     }
435 
436     btc_ble_mesh_health_client_arg_deep_free(msg);
437     return;
438 }
439 
btc_ble_mesh_health_client_cb_handler(btc_msg_t * msg)440 void btc_ble_mesh_health_client_cb_handler(btc_msg_t *msg)
441 {
442     esp_ble_mesh_health_client_cb_param_t *param = NULL;
443 
444     if (!msg || !msg->arg) {
445         BT_ERR("%s, Invalid parameter", __func__);
446         return;
447     }
448 
449     param = (esp_ble_mesh_health_client_cb_param_t *)(msg->arg);
450 
451     if (msg->act < ESP_BLE_MESH_HEALTH_CLIENT_EVT_MAX) {
452         btc_ble_mesh_health_client_cb_to_app(msg->act, param);
453     } else {
454         BT_ERR("%s, Unknown act %d", __func__, msg->act);
455     }
456 
457     btc_ble_mesh_health_client_free_req_data(msg);
458     return;
459 }
460 
461 #endif /* CONFIG_BLE_MESH_HEALTH_CLI */
462 
463 #if CONFIG_BLE_MESH_HEALTH_SRV
464 #include "health_srv.h"
465 
466 /* Health Server Model related functions */
467 
btc_ble_mesh_health_server_cb_to_app(esp_ble_mesh_health_server_cb_event_t event,esp_ble_mesh_health_server_cb_param_t * param)468 static inline void btc_ble_mesh_health_server_cb_to_app(esp_ble_mesh_health_server_cb_event_t event,
469                                                         esp_ble_mesh_health_server_cb_param_t *param)
470 {
471     esp_ble_mesh_health_server_cb_t btc_ble_mesh_cb =
472         (esp_ble_mesh_health_server_cb_t)btc_profile_cb_get(BTC_PID_HEALTH_SERVER);
473     if (btc_ble_mesh_cb) {
474         btc_ble_mesh_cb(event, param);
475     }
476 }
477 
btc_ble_mesh_health_server_arg_deep_copy(btc_msg_t * msg,void * p_dest,void * p_src)478 void btc_ble_mesh_health_server_arg_deep_copy(btc_msg_t *msg, void *p_dest, void *p_src)
479 {
480     if (!msg) {
481         BT_ERR("%s, Invalid parameter", __func__);
482         return;
483     }
484 
485     switch (msg->act) {
486     case BTC_BLE_MESH_ACT_HEALTH_SERVER_FAULT_UPDATE:
487         break;
488     default:
489         break;
490     }
491 }
492 
btc_ble_mesh_health_server_arg_deep_free(btc_msg_t * msg)493 static void btc_ble_mesh_health_server_arg_deep_free(btc_msg_t *msg)
494 {
495     if (!msg) {
496         BT_ERR("%s, Invalid parameter", __func__);
497         return;
498     }
499 
500     switch (msg->act) {
501     case BTC_BLE_MESH_ACT_HEALTH_SERVER_FAULT_UPDATE:
502         break;
503     default:
504         break;
505     }
506 }
507 
btc_ble_mesh_health_server_copy_req_data(btc_msg_t * msg,void * p_dest,void * p_src)508 static void btc_ble_mesh_health_server_copy_req_data(btc_msg_t *msg, void *p_dest, void *p_src)
509 {
510     if (!msg) {
511         BT_ERR("%s, Invalid parameter", __func__);
512         return;
513     }
514 
515     switch (msg->act) {
516     case ESP_BLE_MESH_HEALTH_SERVER_FAULT_UPDATE_COMP_EVT:
517         break;
518     default:
519         break;
520     }
521 }
522 
btc_ble_mesh_health_server_free_req_data(btc_msg_t * msg)523 static void btc_ble_mesh_health_server_free_req_data(btc_msg_t *msg)
524 {
525     if (!msg) {
526         BT_ERR("%s, Invalid parameter", __func__);
527         return;
528     }
529 
530     switch (msg->act) {
531     case ESP_BLE_MESH_HEALTH_SERVER_FAULT_UPDATE_COMP_EVT:
532         break;
533     default:
534         break;
535     }
536 }
537 
btc_ble_mesh_health_server_callback(esp_ble_mesh_health_server_cb_param_t * cb_params,uint8_t act)538 static void btc_ble_mesh_health_server_callback(esp_ble_mesh_health_server_cb_param_t *cb_params, uint8_t act)
539 {
540     btc_msg_t msg = {0};
541 
542     BT_DBG("%s", __func__);
543 
544     /* If corresponding callback is not registered, event will not be posted. */
545     if (!btc_profile_cb_get(BTC_PID_HEALTH_SERVER)) {
546         return;
547     }
548 
549     msg.sig = BTC_SIG_API_CB;
550     msg.pid = BTC_PID_HEALTH_SERVER;
551     msg.act = act;
552 
553     btc_transfer_context(&msg, cb_params, sizeof(esp_ble_mesh_health_server_cb_param_t),
554                          btc_ble_mesh_health_server_copy_req_data);
555 }
556 
btc_ble_mesh_health_server_call_handler(btc_msg_t * msg)557 void btc_ble_mesh_health_server_call_handler(btc_msg_t *msg)
558 {
559     esp_ble_mesh_health_server_cb_param_t param = {0};
560     btc_ble_mesh_health_server_args_t *arg = NULL;
561 
562     if (!msg || !msg->arg) {
563         BT_ERR("%s, Invalid parameter", __func__);
564         return;
565     }
566 
567     arg = (btc_ble_mesh_health_server_args_t *)(msg->arg);
568 
569     switch (msg->act) {
570     case BTC_BLE_MESH_ACT_HEALTH_SERVER_FAULT_UPDATE:
571         param.fault_update_comp.element = arg->health_fault_update.element;
572         param.fault_update_comp.error_code =
573             bt_mesh_fault_update((struct bt_mesh_elem *)arg->health_fault_update.element);
574         btc_ble_mesh_health_server_callback(&param, ESP_BLE_MESH_HEALTH_SERVER_FAULT_UPDATE_COMP_EVT);
575         break;
576     default:
577         break;
578     }
579 
580     btc_ble_mesh_health_server_arg_deep_free(msg);
581     return;
582 }
583 
btc_ble_mesh_health_server_cb_handler(btc_msg_t * msg)584 void btc_ble_mesh_health_server_cb_handler(btc_msg_t *msg)
585 {
586     esp_ble_mesh_health_server_cb_param_t *param = NULL;
587 
588     if (!msg || !msg->arg) {
589         BT_ERR("%s, Invalid parameter", __func__);
590         return;
591     }
592 
593     param = (esp_ble_mesh_health_server_cb_param_t *)(msg->arg);
594 
595     if (msg->act < ESP_BLE_MESH_HEALTH_SERVER_EVT_MAX) {
596         btc_ble_mesh_health_server_cb_to_app(msg->act, param);
597     } else {
598         BT_ERR("%s, Unknown act %d", __func__, msg->act);
599     }
600 
601     btc_ble_mesh_health_server_free_req_data(msg);
602     return;
603 }
604 
btc_ble_mesh_health_server_fault_clear(struct bt_mesh_model * model,uint16_t company_id)605 void btc_ble_mesh_health_server_fault_clear(struct bt_mesh_model *model, uint16_t company_id)
606 {
607     esp_ble_mesh_health_server_cb_param_t param = {0};
608 
609     param.fault_clear.model = (esp_ble_mesh_model_t *)model;
610     param.fault_clear.company_id = company_id;
611 
612     btc_ble_mesh_health_server_callback(&param, ESP_BLE_MESH_HEALTH_SERVER_FAULT_CLEAR_EVT);
613 }
614 
btc_ble_mesh_health_server_fault_test(struct bt_mesh_model * model,uint8_t test_id,uint16_t company_id)615 void btc_ble_mesh_health_server_fault_test(struct bt_mesh_model *model,
616                                            uint8_t test_id, uint16_t company_id)
617 {
618     esp_ble_mesh_health_server_cb_param_t param = {0};
619 
620     param.fault_test.model = (esp_ble_mesh_model_t *)model;
621     param.fault_test.test_id = test_id;
622     param.fault_test.company_id = company_id;
623 
624     btc_ble_mesh_health_server_callback(&param, ESP_BLE_MESH_HEALTH_SERVER_FAULT_TEST_EVT);
625 }
626 
btc_ble_mesh_health_server_attention_on(struct bt_mesh_model * model,uint8_t time)627 void btc_ble_mesh_health_server_attention_on(struct bt_mesh_model *model, uint8_t time)
628 {
629     esp_ble_mesh_health_server_cb_param_t param = {0};
630 
631     param.attention_on.model = (esp_ble_mesh_model_t *)model;
632     param.attention_on.time = time;
633 
634     btc_ble_mesh_health_server_callback(&param, ESP_BLE_MESH_HEALTH_SERVER_ATTENTION_ON_EVT);
635 }
636 
btc_ble_mesh_health_server_attention_off(struct bt_mesh_model * model)637 void btc_ble_mesh_health_server_attention_off(struct bt_mesh_model *model)
638 {
639     esp_ble_mesh_health_server_cb_param_t param = {0};
640 
641     param.attention_off.model = (esp_ble_mesh_model_t *)model;
642 
643     btc_ble_mesh_health_server_callback(&param, ESP_BLE_MESH_HEALTH_SERVER_ATTENTION_OFF_EVT);
644 }
645 #endif /* CONFIG_BLE_MESH_HEALTH_SRV */
646