Mesh: Implement Network Key operations
[platform/core/connectivity/bluetooth-frwk.git] / bt-api / bt-mesh.c
1 /*
2  * Copyright (c) 2020 Samsung Electronics Co., Ltd All Rights Reserved
3  *
4  * @author: Anupam Roy  <anupam.r@samsung.com>
5  *
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  *              http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  *
18  */
19
20 #include "bluetooth-api.h"
21 #include "bt-internal-types.h"
22
23 #include "bt-common.h"
24 #include "bt-request-sender.h"
25 #include "bt-event-handler.h"
26
27 #include "bluetooth-mesh-api.h"
28
29 #define BLUETOOTH_MESH_NETWORK_NAME_STRING_MAX 100
30 #define BLUETOOTH_MESH_TOKEN_STRING_MAX 100
31
32 BT_EXPORT_API int bluetooth_mesh_init(mesh_cb_func_ptr cb,
33                         void *user_data)
34 {
35         int ret;
36
37         if (cb == NULL) {
38                 BT_ERR("callback is NULL");
39                 return BLUETOOTH_ERROR_INVALID_PARAM;
40         }
41         ret = _bt_init_event_handler();
42
43         if (ret != BLUETOOTH_ERROR_NONE &&
44                         ret != BLUETOOTH_ERROR_ALREADY_INITIALIZED) {
45                 BT_ERR("Fail to init the event handler");
46                 return ret;
47         }
48
49         _bt_set_user_data(BT_MESH, (void *)cb, user_data);
50
51         /* Register All events */
52         ret = _bt_register_event(BT_MESH_EVENT, (void *)cb, user_data);
53         if (ret != BLUETOOTH_ERROR_NONE &&
54                         ret != BLUETOOTH_ERROR_ALREADY_INITIALIZED) {
55                 _bt_deinit_event_handler();
56                 return ret;
57         }
58
59         BT_INFO("Mesh: Event registsred");
60         return BLUETOOTH_ERROR_NONE;
61 }
62
63 BT_EXPORT_API int bluetooth_mesh_deinit(void)
64 {
65         _bt_unregister_event(BT_MESH_EVENT);
66         _bt_set_user_data(BT_MESH, NULL, NULL);
67
68         return BLUETOOTH_ERROR_NONE;
69 }
70
71 BT_EXPORT_API int bluetooth_mesh_network_create(
72         const char *net_name, bluetooth_mesh_node_t *node,
73                 uint16_t total_models, bluetooth_mesh_model_t **models,
74                         bluetooth_mesh_network_t *network)
75 {
76         int result;
77         char network_name[BLUETOOTH_MESH_NETWORK_NAME_STRING_MAX+1];
78
79         BT_CHECK_PARAMETER(net_name, return);
80         BT_CHECK_PARAMETER(node, return);
81         BT_CHECK_PARAMETER(models, return);
82
83         BT_INIT_PARAMS();
84         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
85
86         g_array_append_vals(in_param1, node,  sizeof(bluetooth_mesh_node_t));
87
88         g_strlcpy(network_name, net_name, sizeof(network_name));
89         g_array_append_vals(in_param2, network_name,
90                         BLUETOOTH_MESH_NETWORK_NAME_STRING_MAX);
91
92         for(int i = 0; i < total_models; i++)
93                 g_array_append_vals(in_param3, models[i],
94                                 sizeof(bluetooth_mesh_model_t));
95
96         result = _bt_send_request(BT_BLUEZ_SERVICE,
97                         BT_MESH_NETWORK_CREATE,
98                                 in_param1, in_param2, in_param3,
99                                         in_param4, &out_param);
100
101         if (result == BLUETOOTH_ERROR_NONE) {
102                 *network = g_array_index(out_param,
103                                 bluetooth_mesh_network_t, 0);
104         }
105
106         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
107
108         return result;
109 }
110
111 BT_EXPORT_API int bluetooth_mesh_network_scan(
112                         bluetooth_mesh_network_t *network,
113                                 bluetooth_mesh_scan_param_t *scan_param)
114 {
115         int result;
116
117         BT_CHECK_PARAMETER(network, return);
118         BT_CHECK_PARAMETER(scan_param, return);
119
120         BT_INIT_PARAMS();
121         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
122
123         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
124
125         g_array_append_vals(in_param2, scan_param, sizeof(bluetooth_mesh_scan_param_t));
126
127         BT_INFO("Mesh:Start Scan, time [%u]", scan_param->scan_time);
128         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_SCAN,
129                         in_param1, in_param2, in_param3, in_param4, &out_param);
130         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
131
132         return result;
133 }
134
135 BT_EXPORT_API int bluetooth_mesh_network_cancel_scan(
136                 bluetooth_mesh_network_t *network)
137 {
138         int result;
139
140         BT_CHECK_PARAMETER(network, return);
141
142         BT_INIT_PARAMS();
143         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
144
145         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
146
147         BT_INFO("Mesh: Cancel Scan");
148         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_CANCEL_SCAN,
149                         in_param1, in_param2, in_param3, in_param4, &out_param);
150         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
151
152         return result;
153 }
154
155 BT_EXPORT_API int bluetooth_mesh_network_set_capabilities(
156         bluetooth_mesh_network_t *network,
157                 bluetooth_mesh_provisioner_caps_t *caps)
158 {
159         int result;
160
161         BT_CHECK_PARAMETER(network, return);
162         BT_CHECK_PARAMETER(caps, return);
163
164         BT_INIT_PARAMS();
165         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
166
167         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
168
169         g_array_append_vals(in_param2, caps, sizeof(bluetooth_mesh_provisioner_caps_t));
170
171         BT_INFO("Mesh: Set Provisioner capabilities");
172         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_SET_CAPABILITIES,
173                         in_param1, in_param2, in_param3, in_param4, &out_param);
174         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
175
176         return result;
177 }
178
179 BT_EXPORT_API int bluetooth_mesh_network_provision_device(
180                 bluetooth_mesh_provisioning_request_t *req)
181 {
182         int result;
183         bt_user_info_t *user_info;
184
185         BT_CHECK_PARAMETER(req, return);
186
187         user_info = _bt_get_user_data(BT_MESH);
188         retv_if(user_info->cb == NULL, BLUETOOTH_ERROR_INTERNAL);
189
190         BT_INIT_PARAMS();
191         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
192
193         g_array_append_vals(in_param1, req,
194                         sizeof(bluetooth_mesh_provisioning_request_t));
195
196         BT_INFO("Mesh: Set Provision Device");
197         result = _bt_send_request_async(BT_BLUEZ_SERVICE,
198                         BT_MESH_NETWORK_PROVISION_DEVICE,
199                         in_param1, in_param2, in_param3, in_param4,
200                         user_info->cb, user_info->user_data);
201
202         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
203
204         return result;
205 }
206
207 BT_EXPORT_API int bluetooth_mesh_authentication_reply(int auth_type,
208                 const char *auth_val, gboolean reply)
209 {
210         int result;
211
212         char auth_string[BLUETOOTH_MESH_AUTH_VALUE_LENGTH_MAX];
213
214         BT_CHECK_PARAMETER(auth_val, return);
215
216         BT_INIT_PARAMS();
217         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
218
219         g_strlcpy(auth_string, auth_val,
220                         sizeof(auth_string));
221         g_array_append_vals(in_param1,
222                         &auth_type, sizeof(int));
223         g_array_append_vals(in_param2, auth_string,
224                         BLUETOOTH_MESH_AUTH_VALUE_LENGTH_MAX);
225         g_array_append_vals(in_param3, &reply, sizeof(gboolean));
226
227         BT_INFO("Mesh: Set Provisioner Authentication Reply");
228         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_AUTHENTICATION_REPLY,
229                         in_param1, in_param2, in_param3, in_param4, &out_param);
230
231         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
232
233         return result;
234 }
235
236 BT_EXPORT_API int bluetooth_mesh_network_set_name(
237         bluetooth_mesh_network_t *network)
238 {
239         int result;
240
241         BT_CHECK_PARAMETER(network, return);
242
243         BT_INIT_PARAMS();
244         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
245
246         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
247
248         BT_INFO("Mesh:Set Network Name");
249         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_SET_NAME,
250                         in_param1, in_param2, in_param3, in_param4, &out_param);
251         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
252
253         return result;
254 }
255
256 BT_EXPORT_API int bluetooth_mesh_network_add_netkey(
257                 bluetooth_mesh_network_t *network,
258                         uint16_t *netkey_idx)
259 {
260         int result;
261
262         BT_CHECK_PARAMETER(network, return);
263         BT_CHECK_PARAMETER(netkey_idx, return);
264
265         BT_INIT_PARAMS();
266         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
267
268         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
269
270         BT_INFO("Mesh:Set Create Subnetwork key");
271         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_ADD_NETKEY,
272                         in_param1, in_param2, in_param3, in_param4, &out_param);
273         if (result == BLUETOOTH_ERROR_NONE) {
274                 *netkey_idx = g_array_index(out_param, guint16, 0);
275         }
276         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
277
278         return result;
279 }
280
281 BT_EXPORT_API int bluetooth_mesh_network_delete_netkey(
282         bluetooth_mesh_network_t *network,
283                 uint16_t netkey_idx)
284 {
285         int result;
286
287         BT_CHECK_PARAMETER(network, return);
288
289         BT_INIT_PARAMS();
290         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
291
292         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
293         g_array_append_vals(in_param2, &netkey_idx,  sizeof(guint16));
294
295         BT_INFO("Mesh: Delete Subnetwork key");
296         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_DELETE_NETKEY,
297                         in_param1, in_param2, in_param3, in_param4, &out_param);
298         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
299
300         return result;
301 }
302
303 BT_EXPORT_API int bluetooth_mesh_network_update_netkey(
304         bluetooth_mesh_network_t *network,
305                 uint16_t netkey_idx)
306 {
307         int result;
308
309         BT_CHECK_PARAMETER(network, return);
310
311         BT_INIT_PARAMS();
312         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
313
314         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
315         g_array_append_vals(in_param2, &netkey_idx,  sizeof(guint16));
316
317         BT_INFO("Mesh: Update Subnetwork key");
318         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_UPDATE_NETKEY,
319                         in_param1, in_param2, in_param3, in_param4, &out_param);
320         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
321
322         return result;
323 }
324
325 BT_EXPORT_API int bluetooth_mesh_network_add_appkey(
326                 bluetooth_mesh_network_t *network,
327                         uint16_t netkey_index,
328                                 uint16_t *appkey_index)
329 {
330         int result;
331
332         BT_CHECK_PARAMETER(network, return);
333         BT_CHECK_PARAMETER(appkey_index, return);
334
335         BT_INIT_PARAMS();
336         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
337
338         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
339         g_array_append_vals(in_param2, &netkey_index,  sizeof(guint16));
340
341         BT_INFO("Mesh: Create AppKey");
342         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_ADD_APPKEY,
343                         in_param1, in_param2, in_param3, in_param4, &out_param);
344
345         if (result == BLUETOOTH_ERROR_NONE) {
346                 *appkey_index = g_array_index(out_param, guint16, 0);
347         }
348         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
349
350         return result;
351 }
352
353 BT_EXPORT_API int bluetooth_mesh_network_update_appkey(
354                 bluetooth_mesh_network_t *network,
355                         uint16_t netkey_index, uint16_t appkey_index)
356 {
357         int result;
358
359         BT_CHECK_PARAMETER(network, return);
360
361         BT_INIT_PARAMS();
362         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
363
364         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
365         g_array_append_vals(in_param2, &netkey_index,  sizeof(guint16));
366         g_array_append_vals(in_param3, &appkey_index,  sizeof(guint16));
367
368         BT_INFO("Mesh:BTAPI: Update AppKey");
369         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_UPDATE_APPKEY,
370                         in_param1, in_param2, in_param3, in_param4, &out_param);
371
372         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
373
374         return result;
375 }
376
377 BT_EXPORT_API int bluetooth_mesh_network_delete_appkey(bluetooth_mesh_network_t *network,
378                         uint16_t netkey_index, uint16_t appkey_index)
379 {
380         int result;
381
382         BT_CHECK_PARAMETER(network, return);
383
384         BT_INIT_PARAMS();
385         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
386
387         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
388         g_array_append_vals(in_param2, &netkey_index,  sizeof(guint16));
389         g_array_append_vals(in_param3, &appkey_index,  sizeof(guint16));
390
391         BT_INFO("Mesh: Delete AppKey");
392         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_DELETE_APPKEY,
393                         in_param1, in_param2, in_param3, in_param4, &out_param);
394
395         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
396
397         return result;
398 }
399
400 BT_EXPORT_API int bluetooth_mesh_network_get_all_netkey(
401         bluetooth_mesh_network_t *network,
402                 GPtrArray **netkeys)
403 {
404         int result = BLUETOOTH_ERROR_NONE;
405         guint size;
406         int i;
407
408         BT_CHECK_PARAMETER(network, return);
409         BT_CHECK_PARAMETER(netkeys, return);
410
411         BT_INIT_PARAMS();
412         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
413
414         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
415
416         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_GET_NETKEYS,
417                         in_param1, in_param2, in_param3, in_param4, &out_param);
418
419         if (result == BLUETOOTH_ERROR_NONE) {
420                 if (out_param == NULL) {
421                         BT_ERR("Mesh: out_param is NULL");
422                         result = BLUETOOTH_ERROR_INTERNAL;
423                 } else {
424                         size = (out_param->len) / sizeof(guint16);
425
426                         if (size == 0) {
427                                 BT_ERR("Mesh: No netkeys created for the network");
428                                 result = BLUETOOTH_ERROR_NOT_FOUND;
429                         }
430
431                         for (i = 0; i < size; i++) {
432                                 uint16_t netkey_index;
433                                 uint16_t *netkey_idx = NULL;
434
435                                 netkey_index = g_array_index(out_param,
436                                                 guint16, i);
437
438                                 netkey_idx = g_memdup(&netkey_index, sizeof(guint16));
439                                 g_ptr_array_add(*netkeys, (gpointer)netkey_idx);
440                         }
441                 }
442         }
443
444         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
445
446         return result;
447 }
448
449 BT_EXPORT_API int bluetooth_mesh_netkey_get_all_appkey(
450                 bluetooth_mesh_network_t *network,
451                         uint16_t netkey_idx,
452                                 GPtrArray **appkeys)
453 {
454         int result = BLUETOOTH_ERROR_NONE;
455         guint size;
456         int i;
457
458         BT_CHECK_PARAMETER(network, return);
459         BT_CHECK_PARAMETER(appkeys, return);
460
461         BT_INIT_PARAMS();
462         BT_ALLOC_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
463
464         g_array_append_vals(in_param1, network,  sizeof(bluetooth_mesh_network_t));
465         g_array_append_vals(in_param2, &netkey_idx,  sizeof(guint16));
466
467         result = _bt_send_request(BT_BLUEZ_SERVICE, BT_MESH_NETWORK_GET_APPKEYS,
468                         in_param1, in_param2, in_param3, in_param4, &out_param);
469
470         if (result == BLUETOOTH_ERROR_NONE) {
471                 if (out_param == NULL) {
472                         BT_ERR("Mesh: out_param is NULL");
473                         result = BLUETOOTH_ERROR_INTERNAL;
474                 } else {
475                         size = (out_param->len) / sizeof(guint16);
476
477                         if (size == 0) {
478                                 BT_ERR("Mesh: No Appkeys created for the NetKey in the network");
479                                 result = BLUETOOTH_ERROR_NOT_FOUND;
480                         }
481
482                         for (i = 0; i < size; i++) {
483                                 uint16_t appkey_index;
484                                 uint16_t *appkey_idx = NULL;
485
486                                 appkey_index = g_array_index(out_param,
487                                                 guint16, i);
488
489                                 appkey_idx = g_memdup(&appkey_index, sizeof(guint16));
490                                 g_ptr_array_add(*appkeys, (gpointer)appkey_idx);
491                         }
492                 }
493         }
494
495         BT_FREE_PARAMS(in_param1, in_param2, in_param3, in_param4, out_param);
496
497         return result;
498 }