Mesh: Fix bug in fetching node vendor info
[platform/core/connectivity/bluetooth-frwk.git] / bt-service / services / mesh / bt-service-mesh-config-client.c
1 /*
2  * Bluetooth-frwk
3  *
4  * Copyright (c) 2020 Samsung Electronics Co., Ltd.
5  *
6  * @author: Anupam Roy <anupam.r@samsung.com>
7  *
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  *              http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  *
20  */
21 #include <glib.h>
22 #include <dlog.h>
23 #include <fcntl.h>
24 #include <dirent.h>
25 #include <errno.h>
26 #include <limits.h>
27 #include <stdio.h>
28 #include <unistd.h>
29 #include <sys/stat.h>
30 #include <ell/ell.h>
31
32 #include "bt-service-common.h"
33 #include "bt-service-core-adapter.h"
34 #include "bt-service-event-receiver.h"
35 #include "bt-request-handler.h"
36 #include "bluetooth-api.h"
37
38 #include "bluetooth-api.h"
39 #include "bluetooth-mesh-api.h"
40 #include "bt-internal-types.h"
41 #include "bt-service-util.h"
42 #include "bt-service-common.h"
43 #include "bt-service-core-adapter.h"
44 #include "bt-service-event-receiver.h"
45 #include "bt-request-handler.h"
46 #include "bluetooth-api.h"
47
48 #include "bluetooth-api.h"
49 #include "bluetooth-mesh-api.h"
50 #include "bt-internal-types.h"
51 #include "bt-service-util.h"
52 #include "bt-service-common.h"
53 #include "bt-service-event.h"
54
55 #include "bt-service-mesh-network.h"
56 #include "bt-service-mesh-cdb.h"
57 #include "bt-service-mesh-nodes.h"
58 #include "bt-service-mesh-keys.h"
59 #include "bt-service-mesh-util.h"
60
61 #include <oal-hardware.h>
62 #include <oal-manager.h>
63 #include <oal-event.h>
64 #include <oal-adapter-mgr.h>
65 #include <oal-device-mgr.h>
66 #include <oal-mesh.h>
67
68 #include "bt-internal-types.h"
69
70 #define MESH_CONFIG_BUFFER_MAX_LEN 100
71
72
73 static void __bt_mesh_send_node_browsed_event(int result,
74                 bluetooth_mesh_node_discover_t *browse_evt);
75 static void __bt_mesh_handle_pending_dev_config_request_info(int result,
76                 int service_function, void *param,
77                         unsigned int size);
78
79 struct mesh_config_cmd {
80         uint32_t opcode;
81         uint32_t response;
82         const char *descriptor;
83 };
84
85 static struct l_queue *pending_requests;
86
87 struct mesh_pending_request {
88         struct l_timeout *timer;
89         const struct mesh_config_cmd *cmd;
90         uint8_t net_uuid[16];
91         uint16_t addr;
92         void *data;
93 };
94
95 static struct mesh_config_cmd commands[] = {
96         { MESH_OPCODE_APPKEY_ADD, MESH_OPCODE_APPKEY_STATUS, "AppKeyAdd" },
97         { MESH_OPCODE_APPKEY_DELETE, MESH_OPCODE_APPKEY_STATUS, "AppKeyDelete" },
98         { MESH_OPCODE_APPKEY_GET, MESH_OPCODE_APPKEY_LIST, "AppKeyGet" },
99         { MESH_OPCODE_APPKEY_LIST, MESH_RESPONSE_NONE, "AppKeyList" },
100         { MESH_OPCODE_APPKEY_STATUS, MESH_RESPONSE_NONE, "AppKeyStatus" },
101         { MESH_OPCODE_APPKEY_UPDATE, MESH_OPCODE_APPKEY_STATUS, "AppKeyUpdate" },
102         { MESH_OPCODE_DEV_COMP_GET, MESH_OPCODE_DEV_COMP_STATUS, "DeviceCompositionGet" },
103         { MESH_OPCODE_DEV_COMP_STATUS, MESH_RESPONSE_NONE, "DeviceCompositionStatus" },
104         { MESH_OPCODE_CONFIG_BEACON_GET, MESH_OPCODE_CONFIG_BEACON_STATUS, "BeaconGet" },
105         { MESH_OPCODE_CONFIG_BEACON_SET, MESH_OPCODE_CONFIG_BEACON_STATUS, "BeaconSet" },
106         { MESH_OPCODE_CONFIG_BEACON_STATUS, MESH_RESPONSE_NONE, "BeaconStatus" },
107         { MESH_OPCODE_CONFIG_DEFAULT_TTL_GET, MESH_OPCODE_CONFIG_DEFAULT_TTL_STATUS,
108                 "DefaultTTLGet" },
109         { MESH_OPCODE_CONFIG_DEFAULT_TTL_SET, MESH_OPCODE_CONFIG_DEFAULT_TTL_STATUS,
110                 "DefaultTTLSet" },
111         { MESH_OPCODE_CONFIG_DEFAULT_TTL_STATUS, MESH_RESPONSE_NONE, "DefaultTTLStatus" },
112         { MESH_OPCODE_CONFIG_FRIEND_GET, MESH_OPCODE_CONFIG_FRIEND_STATUS, "FriendGet" },
113         { MESH_OPCODE_CONFIG_FRIEND_SET, MESH_OPCODE_CONFIG_FRIEND_STATUS, "FrienSet" },
114         { MESH_OPCODE_CONFIG_FRIEND_STATUS, MESH_RESPONSE_NONE, "FriendStatus" },
115         { MESH_OPCODE_CONFIG_PROXY_GET, MESH_OPCODE_CONFIG_PROXY_STATUS, "ProxyGet" },
116         { MESH_OPCODE_CONFIG_PROXY_SET, MESH_OPCODE_CONFIG_PROXY_STATUS, "ProxySet" },
117         { MESH_OPCODE_CONFIG_PROXY_STATUS, MESH_RESPONSE_NONE, "ProxyStatus" },
118         { MESH_OPCODE_CONFIG_KEY_REFRESH_PHASE_GET, MESH_OPCODE_CONFIG_KEY_REFRESH_PHASE_STATUS,
119                 "KeyRefreshPhaseGet" },
120         { MESH_OPCODE_CONFIG_KEY_REFRESH_PHASE_SET, MESH_OPCODE_CONFIG_KEY_REFRESH_PHASE_STATUS,
121                 "KeyRefreshPhaseSet" },
122         { MESH_OPCODE_CONFIG_KEY_REFRESH_PHASE_STATUS, MESH_RESPONSE_NONE,
123                 "KeyRefreshPhaseStatus" },
124         { MESH_OPCODE_CONFIG_MODEL_PUB_GET, MESH_OPCODE_CONFIG_MODEL_PUB_STATUS, "ModelPubGet" },
125         { MESH_OPCODE_CONFIG_MODEL_PUB_SET, MESH_OPCODE_CONFIG_MODEL_PUB_STATUS, "ModelPubSet" },
126         { MESH_OPCODE_CONFIG_MODEL_PUB_STATUS, MESH_RESPONSE_NONE, "ModelPubStatus" },
127         { MESH_OPCODE_CONFIG_MODEL_PUB_VIRT_SET, MESH_OPCODE_CONFIG_MODEL_PUB_STATUS,
128                 "ModelPubVirtualSet" },
129         { MESH_OPCODE_CONFIG_MODEL_SUB_ADD, MESH_OPCODE_CONFIG_MODEL_SUB_STATUS, "ModelSubAdd" },
130         { MESH_OPCODE_CONFIG_MODEL_SUB_DELETE, MESH_OPCODE_CONFIG_MODEL_SUB_STATUS,
131                 "ModelSubDelete" },
132         { MESH_OPCODE_CONFIG_MODEL_SUB_DELETE_ALL, MESH_OPCODE_CONFIG_MODEL_SUB_STATUS,
133                 "ModelSubDeleteAll" },
134         { MESH_OPCODE_CONFIG_MODEL_SUB_OVERWRITE, MESH_OPCODE_CONFIG_MODEL_SUB_STATUS,
135                 "ModelSubOverwrite" },
136         { MESH_OPCODE_CONFIG_MODEL_SUB_STATUS, MESH_RESPONSE_NONE, "ModelSubStatus" },
137         { MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_ADD, MESH_OPCODE_CONFIG_MODEL_SUB_STATUS,
138                 "ModelSubVirtAdd" },
139         { MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_DELETE, MESH_OPCODE_CONFIG_MODEL_SUB_STATUS,
140                 "ModelSubVirtDelete" },
141         { MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_OVERWRITE, MESH_OPCODE_CONFIG_MODEL_SUB_STATUS,
142                 "ModelSubVirtOverwrite" },
143         { MESH_OPCODE_CONFIG_NETWORK_TRANSMIT_GET, MESH_OPCODE_CONFIG_NETWORK_TRANSMIT_STATUS,
144                 "NetworkTransmitGet" },
145         { MESH_OPCODE_CONFIG_NETWORK_TRANSMIT_SET, MESH_OPCODE_CONFIG_NETWORK_TRANSMIT_STATUS,
146                 "NetworkTransmitSet" },
147         { MESH_OPCODE_CONFIG_NETWORK_TRANSMIT_STATUS, MESH_RESPONSE_NONE,
148                 "NetworkTransmitStatus" },
149         { MESH_OPCODE_CONFIG_RELAY_GET, MESH_OPCODE_CONFIG_RELAY_STATUS, "RelayGet" },
150         { MESH_OPCODE_CONFIG_RELAY_SET, MESH_OPCODE_CONFIG_RELAY_STATUS, "RelaySet" },
151         { MESH_OPCODE_CONFIG_RELAY_STATUS, MESH_RESPONSE_NONE, "RelayStatus" },
152         { MESH_OPCODE_CONFIG_MODEL_SUB_GET, MESH_OPCODE_CONFIG_MODEL_SUB_LIST, "ModelSubGet" },
153         { MESH_OPCODE_CONFIG_MODEL_SUB_LIST, MESH_RESPONSE_NONE, "ModelSubList" },
154         { MESH_OPCODE_CONFIG_VEND_MODEL_SUB_GET, MESH_OPCODE_CONFIG_VEND_MODEL_SUB_LIST,
155                 "VendorModelSubGet" },
156         { MESH_OPCODE_CONFIG_VEND_MODEL_SUB_LIST, MESH_RESPONSE_NONE, "VendorModelSubList" },
157         { MESH_OPCODE_CONFIG_POLL_TIMEOUT_LIST, MESH_OPCODE_CONFIG_POLL_TIMEOUT_STATUS,
158                 "PollTimeoutList" },
159         { MESH_OPCODE_CONFIG_POLL_TIMEOUT_STATUS, MESH_RESPONSE_NONE, "PollTimeoutStatus" },
160         { MESH_OPCODE_CONFIG_HEARTBEAT_PUB_GET, MESH_OPCODE_CONFIG_HEARTBEAT_PUB_STATUS,
161                 "HeartbeatPubGet" },
162         { MESH_OPCODE_CONFIG_HEARTBEAT_PUB_SET, MESH_OPCODE_CONFIG_HEARTBEAT_PUB_STATUS,
163                 "HeartbeatPubSet" },
164         { MESH_OPCODE_CONFIG_HEARTBEAT_PUB_STATUS, MESH_RESPONSE_NONE, "HeartbeatPubStatus" },
165         { MESH_OPCODE_CONFIG_HEARTBEAT_SUB_GET, MESH_OPCODE_CONFIG_HEARTBEAT_SUB_STATUS,
166                 "HeartbeatSubGet" },
167         { MESH_OPCODE_CONFIG_HEARTBEAT_SUB_SET, MESH_OPCODE_CONFIG_HEARTBEAT_SUB_STATUS,
168                 "HeartbeatSubSet" },
169         { MESH_OPCODE_CONFIG_HEARTBEAT_SUB_STATUS, MESH_RESPONSE_NONE, "HeartbeatSubStatus" },
170         { MESH_OPCODE_MODEL_APP_BIND, MESH_OPCODE_MODEL_APP_STATUS, "ModelAppBind" },
171         { MESH_OPCODE_MODEL_APP_STATUS, MESH_RESPONSE_NONE, "ModelAppStatus" },
172         { MESH_OPCODE_MODEL_APP_UNBIND, MESH_OPCODE_MODEL_APP_STATUS, "ModelAppUnbind" },
173         { MESH_OPCODE_NETKEY_ADD, MESH_OPCODE_NETKEY_STATUS, "NetKeyAdd" },
174         { MESH_OPCODE_NETKEY_DELETE, MESH_OPCODE_NETKEY_STATUS, "NetKeyDelete" },
175         { MESH_OPCODE_NETKEY_GET, MESH_OPCODE_NETKEY_LIST, "NetKeyGet" },
176         { MESH_OPCODE_NETKEY_LIST, MESH_RESPONSE_NONE, "NetKeyList" },
177         { MESH_OPCODE_NETKEY_STATUS, MESH_RESPONSE_NONE, "NetKeyStatus" },
178         { MESH_OPCODE_NETKEY_UPDATE, MESH_OPCODE_NETKEY_STATUS, "NetKeyUpdate" },
179         { MESH_OPCODE_NODE_IDENTITY_GET, MESH_OPCODE_NODE_IDENTITY_STATUS, "NodeIdentityGet" },
180         { MESH_OPCODE_NODE_IDENTITY_SET, MESH_OPCODE_NODE_IDENTITY_STATUS, "NodeIdentitySet" },
181         { MESH_OPCODE_NODE_IDENTITY_STATUS, MESH_RESPONSE_NONE, "NodeIdentityStatus" },
182         { MESH_OPCODE_NODE_RESET, MESH_OPCODE_NODE_RESET_STATUS, "NodeReset" },
183         { MESH_OPCODE_NODE_RESET_STATUS, MESH_RESPONSE_NONE, "NodeResetStatus" },
184         { MESH_OPCODE_MODEL_APP_GET, MESH_OPCODE_MODEL_APP_LIST, "ModelAppGet" },
185         { MESH_OPCODE_MODEL_APP_LIST, MESH_RESPONSE_NONE, "ModelAppList" },
186         { MESH_OPCODE_VENDOR_MODEL_APP_GET, MESH_OPCODE_VENDOR_MODEL_APP_LIST, "VendorModelAppGet" },
187         { MESH_OPCODE_VENDOR_MODEL_APP_LIST, MESH_RESPONSE_NONE, "VendorModelAppList" }
188 };
189
190
191 static const struct mesh_config_cmd *__mesh_get_command(uint32_t opcode)
192 {
193         uint32_t n;
194
195         for (n = 0; n < L_ARRAY_SIZE(commands); n++) {
196                 if (opcode == commands[n].opcode)
197                         return &commands[n];
198         }
199
200         return NULL;
201 }
202
203 static const char *__mesh_get_opcode_string(uint32_t opcode)
204 {
205         const struct mesh_config_cmd *cmd;
206
207         cmd = __mesh_get_command(opcode);
208         if (!cmd)
209                 return "Unknown Command Received";
210
211         return cmd->descriptor;
212 }
213
214 static void __mesh_request_remove(void *a)
215 {
216         struct mesh_pending_request *req = a;
217
218         if (req->data)
219                 l_free(req->data);
220         l_timeout_remove(req->timer);
221         l_free(req);
222 }
223
224 static void __bt_mesh_wait_response_timeout(
225                 struct l_timeout *timeout, void *user_data)
226 {
227         struct mesh_pending_request *req = user_data;
228
229         BT_INFO("Mesh: No response for \"%s\" from %4.4x\n",
230                         req->cmd->descriptor, req->addr);
231
232         /* Node reset case: delete the remote even if there is no response */
233         /* TODO Reset the remote node, as no response is expected on reset command */
234
235
236         switch (req->cmd->opcode) {
237         case MESH_OPCODE_DEV_COMP_GET: {
238                 /* Send event with timeout for Vendor Features */
239                 bluetooth_mesh_node_features_t *vendor_event = \
240                         g_malloc0(sizeof(bluetooth_mesh_node_features_t));
241
242                 _bt_mesh_util_convert_hex_to_string((uint8_t *) req->net_uuid, 16,
243                         vendor_event->net_uuid,
244                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
245                 vendor_event->unicast = req->addr;
246                  __bt_mesh_handle_pending_dev_config_request_info(
247                         BLUETOOTH_ERROR_TIMEOUT, BT_MESH_NODE_GET_VENDOR_FEATURES,
248                                 vendor_event, sizeof(bluetooth_mesh_node_features_t));
249                 g_free(vendor_event);
250
251                 /* Send event with timeout for Node Browse */
252                 event_mesh_devkey_message_t *event = \
253                         g_malloc0(sizeof(event_mesh_devkey_message_t));
254                 memcpy(event->net_uuid.uuid, req->net_uuid, 16);
255                 event->source = req->addr;
256
257                  __bt_mesh_handle_pending_dev_config_request_info(
258                         BLUETOOTH_ERROR_TIMEOUT, BT_MESH_NODE_BROWSE,
259                                 event, sizeof(event_mesh_devkey_message_t));
260
261                 g_free(event);
262                 break;
263         }
264         case MESH_OPCODE_CONFIG_MODEL_SUB_GET:
265         case MESH_OPCODE_CONFIG_VEND_MODEL_SUB_GET:
266                 BT_INFO("Mesh: Command TimedOut: Model Subscription list get");
267                 /* Send event with timeout */
268                  __bt_mesh_handle_pending_dev_config_request_info(
269                         BLUETOOTH_ERROR_TIMEOUT,
270                                 BT_MESH_MODEL_GET_SUBSCRIPTION_LIST, req->data,
271                                         sizeof(bluetooth_mesh_model_configure_t));
272         break;
273         case MESH_OPCODE_NETKEY_ADD:
274         case MESH_OPCODE_NETKEY_UPDATE:
275         case MESH_OPCODE_NETKEY_DELETE:
276         case MESH_OPCODE_APPKEY_ADD:
277         case MESH_OPCODE_APPKEY_UPDATE:
278         case MESH_OPCODE_APPKEY_DELETE:
279                 /* Send event with timeout */
280                  __bt_mesh_handle_pending_dev_config_request_info(
281                         BLUETOOTH_ERROR_TIMEOUT,
282                                 BT_MESH_NODE_CONFIGURE_KEY, req->data,
283                                         sizeof(bluetooth_mesh_key_configure_t));
284                 break;
285         case MESH_OPCODE_CONFIG_DEFAULT_TTL_GET:
286         case MESH_OPCODE_CONFIG_DEFAULT_TTL_SET:
287                 /* Send event with timeout */
288                  __bt_mesh_handle_pending_dev_config_request_info(
289                         BLUETOOTH_ERROR_TIMEOUT,
290                                 BT_MESH_NODE_TTL_EXECUTE, req->data,
291                                         sizeof(bluetooth_mesh_node_ttl_info_t));
292                 break;
293         case MESH_OPCODE_CONFIG_MODEL_SUB_ADD:
294         case MESH_OPCODE_CONFIG_MODEL_SUB_DELETE:
295         case MESH_OPCODE_CONFIG_MODEL_SUB_OVERWRITE:
296                 /* Send event with timeout */
297                  __bt_mesh_handle_pending_dev_config_request_info(
298                         BLUETOOTH_ERROR_TIMEOUT,
299                                 BT_MESH_MODEL_CONFIG_GROUP_SUB, req->data,
300                                         sizeof(bluetooth_mesh_model_configure_t));
301                 break;
302         case MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_ADD:
303         case MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_DELETE:
304         case MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_OVERWRITE:
305                 /* Send event with timeout */
306                  __bt_mesh_handle_pending_dev_config_request_info(
307                         BLUETOOTH_ERROR_TIMEOUT,
308                                 BT_MESH_MODEL_CONFIG_VIRTUAL_GROUP_SUB, req->data,
309                                         sizeof(bluetooth_mesh_model_configure_t));
310                 break;
311         case MESH_OPCODE_CONFIG_MODEL_SUB_DELETE_ALL:
312                 /* Send event with timeout */
313                  __bt_mesh_handle_pending_dev_config_request_info(
314                         BLUETOOTH_ERROR_TIMEOUT,
315                                 BT_MESH_MODEL_CONFIG_VIRTUAL_GROUP_SUB, req->data,
316                                         sizeof(bluetooth_mesh_model_configure_t));
317                 /* Send event with timeout */
318                  __bt_mesh_handle_pending_dev_config_request_info(
319                         BLUETOOTH_ERROR_TIMEOUT,
320                                 BT_MESH_MODEL_CONFIG_GROUP_SUB, req->data,
321                                         sizeof(bluetooth_mesh_model_configure_t));
322                 break;
323         default:
324                 break;
325         }
326         BT_INFO("Mesh: Number of pending requests [%u] Remove the req",
327                 l_queue_length(pending_requests));
328         l_queue_remove(pending_requests, req);
329         __mesh_request_remove(req);
330 }
331
332 static void __bt_mesh_add_request(uint32_t opcode, uint16_t dest,
333                         uint8_t net_uuid[], void *data)
334 {
335         struct mesh_pending_request *req;
336         const struct mesh_config_cmd *cmd;
337         char uuid_str[33];
338
339         cmd = __mesh_get_command(opcode);
340         if (!cmd)
341                 return;
342         _bt_mesh_util_convert_hex_to_string((uint8_t *) net_uuid, 16, uuid_str,
343                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
344         BT_INFO("Mesh: Net UUID[%s]", uuid_str);
345
346         BT_INFO("Mesh: Adding command opcode [0x%2.2x] response [0x%2.2x]",
347                         cmd->opcode, cmd->response);
348         req = l_new(struct mesh_pending_request, 1);
349         req->cmd = cmd;
350         req->addr = dest;
351         req->data = data;
352         memcpy(req->net_uuid, net_uuid, 16);
353         req->timer = l_timeout_create(MESH_DEFAULT_RESPONSE_TIMEOUT,
354                         __bt_mesh_wait_response_timeout, req, NULL);
355
356         if (!pending_requests)
357                 pending_requests = l_queue_new();
358         l_queue_push_tail(pending_requests, req);
359         BT_INFO("Mesh: Number of pending requests [%u]", l_queue_length(pending_requests));
360 }
361
362 static struct mesh_pending_request *__bt_mesh_get_request_by_response(
363                 uint16_t addr, uint8_t net_uuid[],
364                         uint32_t response)
365 {
366         const struct l_queue_entry *entry;
367         char uuid_str[33];
368         char uuid_str1[33];
369
370         BT_INFO("Mesh: Number of pending requests [%u]", l_queue_length(pending_requests));
371         entry = l_queue_get_entries(pending_requests);
372
373         for (; entry; entry = entry->next) {
374                 struct mesh_pending_request *req = entry->data;
375
376                 /* Test */
377                 BT_INFO("Mesh: Req addr [0x%2.2x] req opcode [0x%2.2x] res [0x%2.2x]", req->addr, req->cmd->opcode, req->cmd->response);
378                 BT_INFO("Mesh: Current req addr [0x%2.2x] res [0x%2.2x]", addr, response);
379                 _bt_mesh_util_convert_hex_to_string((uint8_t *) net_uuid, 16, uuid_str,
380                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
381                 BT_INFO("Mesh: Net UUID[%s]", uuid_str);
382
383                 _bt_mesh_util_convert_hex_to_string((uint8_t *) req->net_uuid, 16, uuid_str1,
384                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
385                 BT_INFO("Mesh: Net UUID1[%s]", uuid_str1);
386                 if (!memcmp(net_uuid, req->net_uuid, 16) &&
387                                 req->addr == addr &&
388                                 req->cmd->response == response)
389                         return req;
390         }
391
392         return NULL;
393 }
394
395 bool _bt_mesh_check_pending_request(uint32_t opcode,
396                 uint16_t dest, uint8_t net_uuid[])
397 {
398         const struct mesh_config_cmd *cmd;
399         cmd = __mesh_get_command(opcode);
400
401         if (!cmd)
402                 return false;
403
404         if (__bt_mesh_get_request_by_response(dest,
405                                 net_uuid, cmd->response)) {
406                 BT_ERR("Mesh:Another command is pending\n");
407                 return true;
408         }
409         return false;
410 }
411
412 static uint32_t __bt_mesh_print_model_identifier(uint8_t *data,
413                 bool vendor, const char *offset)
414 {
415         uint32_t mod_id;
416
417         if (!vendor) {
418                 mod_id = l_get_le16(data);
419                 BT_INFO("%sModel ID\t%4.4x\n", offset, mod_id);
420                 mod_id = MESH_VENDOR_ID_MASK | mod_id;
421         } else {
422                 mod_id = l_get_le16(data + 2);
423                 BT_INFO("%sModel ID\t%4.4x %4.4x\n", offset,
424                                 l_get_le16(data), mod_id);
425                 mod_id = l_get_le16(data) << 16 | mod_id;
426         }
427
428         return mod_id;
429 }
430
431 static void __bt_mesh_print_device_composition_data(
432                 uint8_t *data, uint16_t len)
433 {
434         uint16_t features;
435         int i = 0;
436
437         BT_INFO("Mesh: Received composion:\n");
438
439         /* skip page -- We only support Page Zero */
440         data++;
441         len--;
442
443         BT_INFO("\tCID: %4.4x", l_get_le16(&data[0]));
444         BT_INFO("\tPID: %4.4x", l_get_le16(&data[2]));
445         BT_INFO("\tVID: %4.4x", l_get_le16(&data[4]));
446         BT_INFO("\tCRPL: %4.4x", l_get_le16(&data[6]));
447
448         features = l_get_le16(&data[8]);
449         data += 10;
450         len -= 10;
451
452         BT_INFO("\tFeature support:\n");
453         BT_INFO("\t\trelay: %s\n", (features & MESH_FEATURE_RELAY) ?
454                         "yes" : "no");
455         BT_INFO("\t\tproxy: %s\n", (features & MESH_FEATURE_PROXY) ?
456                         "yes" : "no");
457         BT_INFO("\t\tfriend: %s\n", (features & MESH_FEATURE_FRIEND) ?
458                         "yes" : "no");
459         BT_INFO("\t\tlpn: %s\n", (features & MESH_FEATURE_LPN) ?
460                         "yes" : "no");
461         while (len) {
462                 uint8_t m, v;
463
464                 BT_INFO("\t Element %d:\n", i);
465                 BT_INFO("\t\tlocation: %4.4x\n", l_get_le16(data));
466                 data += 2;
467                 len -= 2;
468
469                 m = *data++;
470                 v = *data++;
471                 len -= 2;
472
473                 if (m)
474                         BT_INFO("\t\tSIG defined models:\n");
475
476                 while (len >= 2 && m--) {
477                         __bt_mesh_print_model_identifier(data, false, "\t\t  ");
478                         data += 2;
479                         len -= 2;
480                 }
481
482                 if (v)
483                         BT_INFO("\t\t Vendor defined models:\n");
484
485                 while (len >= 4 && v--) {
486                         __bt_mesh_print_model_identifier(data, true, "\t\t  ");
487                         data += 4;
488                         len -= 4;
489                 }
490
491                 i++;
492         }
493 }
494
495 static void __bt_mesh_send_model_publication_status_event(
496                 int event, int result,
497                         bluetooth_mesh_model_configure_t *evt)
498 {
499         GVariant *out_var = NULL, *param = NULL;
500         GArray *info = NULL;
501
502         if (BLUETOOTH_ERROR_NONE == result) {
503                 BT_INFO("Mesh: Model ID [0x%4.4x]", evt->model);
504                 BT_INFO("Mesh: Model Publication Address [0x%2.2x]", evt->pub_addr);
505                 /* Send event */
506                 info = g_array_new(FALSE, FALSE, sizeof(gchar));
507                 g_array_append_vals(info, evt,
508                                 sizeof(bluetooth_mesh_model_configure_t));
509
510                 out_var = g_variant_new_from_data((const GVariantType *)"ay",
511                                 info->data, info->len,
512                                 TRUE, NULL, NULL);
513
514                 param = g_variant_new("(iv)", result, out_var);
515                 _bt_send_event(BT_MESH_EVENT, event,
516                                 param);
517         }
518 }
519
520 static void __bt_mesh_send_model_subscription_configure_event(
521                 int event, int result,
522                         bluetooth_mesh_model_configure_t *evt)
523 {
524         GVariant *out_var = NULL, *param = NULL;
525         GArray *info = NULL;
526
527         if (BLUETOOTH_ERROR_NONE == result) {
528                 /* Send event */
529                 info = g_array_new(FALSE, FALSE, sizeof(gchar));
530                 g_array_append_vals(info, evt,
531                                 sizeof(bluetooth_mesh_model_configure_t));
532
533                 out_var = g_variant_new_from_data((const GVariantType *)"ay",
534                                 info->data, info->len,
535                                 TRUE, NULL, NULL);
536
537                 param = g_variant_new("(iv)", result, out_var);
538                 _bt_send_event(BT_MESH_EVENT, event,
539                                 param);
540         }
541 }
542
543 static void __bt_mesh_send_model_get_subscription_list_event(
544         int result, bluetooth_mesh_model_configure_t *evt)
545 {
546         GVariant  *param = NULL;
547         GVariantBuilder *builder = NULL;
548         int i;
549         char *net_uuid;
550
551         if (BLUETOOTH_ERROR_NONE == result) {
552                 BT_INFO("Mesh: Total Subscriptions bound to model [%d]",
553                                 evt->sublist_count);
554                 BT_INFO("Mesh: Network [%s]", evt->net_uuid);
555                 builder = g_variant_builder_new(G_VARIANT_TYPE("aq"));
556                 for (i = 0; i < evt->sublist_count; i++) {
557                         BT_INFO("Mesh: Subscription Address [0x%2.2x]",
558                                 *evt->sub_list[i]);
559                         g_variant_builder_add(builder, "q", *evt->sub_list[i]);
560                 }
561
562                 net_uuid = g_strdup(evt->net_uuid);
563                 param = g_variant_new("(isqiui(aq))", result, net_uuid,
564                                 evt->primary_unicast, evt->elem_index, evt->model,
565                                 evt->sublist_count, builder);
566
567                 g_variant_builder_unref(builder);
568
569                 /* Send event */
570                 _bt_send_event(BT_MESH_EVENT,
571                                 BLUETOOTH_EVENT_MESH_MODEL_SUBSCRIPTION_LIST,
572                                 param);
573
574                 if (evt->sublist_count) {
575                         /* Free List data */
576                         for (int i = 0; i < evt->sublist_count; i++)
577                                 g_free(evt->sub_list[i]);
578                         g_free(evt->sub_list);
579                 }
580                 g_free(net_uuid);
581                 BT_INFO("freed net uuid");
582         }
583 }
584
585 static void __bt_mesh_send_model_get_appkey_list_event(int result,
586                 bluetooth_mesh_model_configure_t *evt)
587 {
588         GVariant  *param = NULL;
589         GVariantBuilder *builder = NULL;
590         char *net_uuid;
591         int i;
592
593         if (BLUETOOTH_ERROR_NONE == result) {
594                 builder = g_variant_builder_new(G_VARIANT_TYPE("aq"));
595                 BT_INFO("Mesh: Total AppKeys bound to model [%d]",
596                                 evt->appkeylist_count);
597                 BT_INFO("Mesh: Network [%s]", evt->net_uuid);
598                 for (i = 0; i < evt->appkeylist_count; i++)
599                         g_variant_builder_add(builder, "q", *evt->appkey_list[i]);
600                 net_uuid = g_strdup(evt->net_uuid);
601                 param = g_variant_new("(isqiui(aq))", result, net_uuid,
602                                 evt->primary_unicast, evt->elem_index, evt->model,
603                                 evt->appkeylist_count, builder);
604
605                 g_variant_builder_unref(builder);
606
607                 /* Send event */
608                 _bt_send_event(BT_MESH_EVENT,
609                                 BLUETOOTH_EVENT_MESH_MODEL_APPKEY_LIST,
610                                 param);
611
612                 if (evt->appkeylist_count) {
613                         for (int i = 0; i < evt->appkeylist_count; i++)
614                                 g_free(evt->appkey_list[i]);
615
616                         g_free(evt->appkey_list);
617                 }
618                 /* Free List data */
619                 g_free(net_uuid);
620         }
621 }
622
623 static void __bt_mesh_send_model_configure_appkey_event(int result,
624                 bluetooth_mesh_model_configure_t *evt)
625 {
626         GVariant *out_var = NULL, *param = NULL;
627         GArray *info = NULL;
628
629         if (BLUETOOTH_ERROR_NONE == result) {
630                 /* Send event */
631                 info = g_array_new(FALSE, FALSE, sizeof(gchar));
632                 g_array_append_vals(info, evt, sizeof(bluetooth_mesh_model_configure_t));
633
634                 out_var = g_variant_new_from_data((const GVariantType *)"ay",
635                                 info->data, info->len,
636                                 TRUE, NULL, NULL);
637
638                 param = g_variant_new("(iv)", result, out_var);
639                 _bt_send_event(BT_MESH_EVENT,
640                                 BLUETOOTH_EVENT_MESH_MODEL_APPKEY_BIND,
641                                 param);
642         }
643 }
644
645 static void __bt_mesh_send_node_ttl_configuration_event(int result,
646                 bluetooth_mesh_node_ttl_info_t *ttl_evt)
647 {
648         GVariant *out_var = NULL, *param = NULL;
649         GArray *info = NULL;
650
651         if (BLUETOOTH_ERROR_NONE == result) {
652                 /* Send event */
653                 info = g_array_new(FALSE, FALSE, sizeof(gchar));
654                 g_array_append_vals(info, ttl_evt,
655                         sizeof(bluetooth_mesh_node_ttl_info_t));
656
657                 out_var = g_variant_new_from_data((const GVariantType *)"ay",
658                                 info->data, info->len,
659                                 TRUE, NULL, NULL);
660
661                 param = g_variant_new("(iv)", result, out_var);
662                 _bt_send_event(BT_MESH_EVENT,
663                                 BLUETOOTH_EVENT_MESH_NODE_TTL_CONFIGURED,
664                                 param);
665         }
666 }
667
668 static void __bt_mesh_send_node_key_configuration_event(int result,
669                 bluetooth_mesh_key_configure_t *key_evt)
670 {
671         GVariant *out_var = NULL, *param = NULL;
672         GArray *info = NULL;
673
674         if (BLUETOOTH_ERROR_NONE == result) {
675                 /* Send event */
676                 info = g_array_new(FALSE, FALSE, sizeof(gchar));
677                 g_array_append_vals(info, key_evt,
678                         sizeof(bluetooth_mesh_key_configure_t));
679
680                 out_var = g_variant_new_from_data((const GVariantType *)"ay",
681                                 info->data, info->len,
682                                 TRUE, NULL, NULL);
683
684                 param = g_variant_new("(iv)", result, out_var);
685                 _bt_send_event(BT_MESH_EVENT,
686                                 BLUETOOTH_EVENT_MESH_NODE_KEY_CONFIGURED,
687                                 param);
688         }
689 }
690
691 static void __bt_mesh_send_node_get_vendor_features_event(int result,
692                 bluetooth_mesh_node_features_t *features_evt)
693 {
694         GVariant *out_var = NULL, *param = NULL;
695         GArray *info = NULL;
696
697         if (BLUETOOTH_ERROR_NONE == result) {
698                 /* Send event */
699                 info = g_array_new(FALSE, FALSE, sizeof(gchar));
700                 g_array_append_vals(info, features_evt,
701                                 sizeof(bluetooth_mesh_node_features_t));
702
703                 out_var = g_variant_new_from_data((const GVariantType *)"ay",
704                                 info->data, info->len,
705                                 TRUE, NULL, NULL);
706
707                 param = g_variant_new("(iv)", result, out_var);
708                 _bt_send_event(BT_MESH_EVENT,
709                                 BLUETOOTH_EVENT_MESH_NODE_VENDOR_FEATURES,
710                                 param);
711         }
712 }
713
714 static void __bt_mesh_send_node_browsed_event(int result,
715                 bluetooth_mesh_node_discover_t *browse_evt)
716 {
717         GVariant *out_var = NULL, *param = NULL;
718         GArray *info = NULL;
719
720         if (BLUETOOTH_ERROR_NONE == result) {
721                 /* Send event */
722                 info = g_array_new(FALSE, FALSE, sizeof(gchar));
723                 g_array_append_vals(info, browse_evt,
724                                 sizeof(bluetooth_mesh_node_discover_t));
725
726                 out_var = g_variant_new_from_data((const GVariantType *)"ay",
727                                 info->data, info->len,
728                                 TRUE, NULL, NULL);
729
730                 param = g_variant_new("(iv)", result, out_var);
731                 _bt_send_event(BT_MESH_EVENT,
732                                 BLUETOOTH_EVENT_MESH_NODE_BROWSED,
733                                 param);
734         }
735 }
736
737 static void __bt_mesh_handle_pending_dev_config_request_info(int result,
738                 int service_function, void *param, unsigned int size)
739 {
740         GSList *l;
741         GArray *out_param;
742         invocation_info_t *req_info = NULL;
743
744         for (l = _bt_get_invocation_list(); l != NULL; ) {
745                 req_info = l->data;
746                 l = g_slist_next(l);
747                 if (req_info == NULL ||
748                                 req_info->service_function != service_function)
749                         continue;
750
751                 switch (service_function) {
752                 case BT_MESH_NODE_GET_VENDOR_FEATURES: {
753                         bluetooth_mesh_node_features_t *event;
754                         bluetooth_mesh_node_features_t *req;
755
756                         event = (bluetooth_mesh_node_features_t*) param;
757                         req = (bluetooth_mesh_node_features_t*)req_info->user_data;
758
759                         BT_DBG("Request Sender: [%s]", req_info->sender);
760                         /* Match Network and Remote Node unicast*/
761                         if (!g_strcmp0(event->net_uuid, req->net_uuid) && event->unicast == req->unicast) {
762                                 event->unicast = req->unicast;
763                                 event->elem_count = req->elem_count;
764
765                                 /* Send Event */
766                                 __bt_mesh_send_node_get_vendor_features_event(result, event);
767
768                                 out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
769                                 g_array_append_vals(out_param, event, sizeof(bluetooth_mesh_node_features_t));
770
771                                 /* Return DBUS Invocation*/
772                                 _bt_service_method_return(req_info->context, out_param, result);
773                                 _bt_free_info_from_invocation_list(req_info);
774                                 g_array_free(out_param, TRUE);
775                         }
776                         break;
777                 }
778                 case BT_MESH_NODE_BROWSE: {
779                         bluetooth_mesh_node_discover_t *node;
780                         event_mesh_devkey_message_t *event;
781                         uint16_t remote_addr;
782                         uint8_t elem_count;
783                         uint8_t dev_uuid[16];
784                         char net_uuid[BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1];
785
786                         event = (event_mesh_devkey_message_t*) param;
787                         node = (bluetooth_mesh_node_discover_t*)req_info->user_data;
788                         BT_INFO("Mesh: Request Node UUID [%s]", node->dev_uuid);
789                         BT_INFO("Mesh: Request Network UUID [%s]", node->net_uuid);
790
791                         _bt_mesh_util_convert_hex_to_string((uint8_t *) event->net_uuid.uuid, 16, net_uuid,
792                                         BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
793
794                         _bt_mesh_util_convert_string_to_hex(node->dev_uuid, strlen(node->dev_uuid), dev_uuid, 16);
795
796                         /* Get Unicast from pending request's Dev UUID and match with event */
797                         if (_bt_mesh_node_get_unicast_from_dev_uuid(event->net_uuid.uuid, dev_uuid, &remote_addr)) {
798
799                                 BT_DBG("Request Sender: [%s]", req_info->sender);
800                                 /* Match Network and Remote Node unicast*/
801                                 if (!g_strcmp0(node->net_uuid, net_uuid) && remote_addr == event->source) {
802                                         _bt_mesh_node_get_element_count(event->net_uuid.uuid, remote_addr, &elem_count);
803                                         node->unicast = event->source;
804                                         node->count = elem_count;
805                                         BT_INFO("Mesh: Browse event for Node: Unicast [0x%2.2x] Element Count [%d]",
806                                                 node->unicast, elem_count);
807                                         /* Send Event */
808                                         __bt_mesh_send_node_browsed_event(result, node);
809
810                                         out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
811                                         g_array_append_vals(out_param, node, sizeof(bluetooth_mesh_node_discover_t));
812
813                                         /* Return DBUS Invocation*/
814                                         _bt_service_method_return(req_info->context, out_param, result);
815                                         _bt_free_info_from_invocation_list(req_info);
816                                         g_array_free(out_param, TRUE);
817
818                                 }
819                         }
820                         break;
821                 }
822                 case BT_MESH_NODE_CONFIGURE_KEY: {
823                         bluetooth_mesh_key_configure_t *event;
824                         bluetooth_mesh_key_configure_t *req;
825
826                         event = (bluetooth_mesh_key_configure_t*) param;
827                         req = (bluetooth_mesh_key_configure_t*)req_info->user_data;
828
829                         if (!g_strcmp0(req->net_uuid, event->net_uuid) &&
830                                 req->primary_unicast == event->primary_unicast &&
831                                 req->is_netkey == event->is_netkey) {
832                                 /* Send Event */
833                                 __bt_mesh_send_node_key_configuration_event(result, event);
834
835                                 out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
836                                 g_array_append_vals(out_param, event, sizeof(bluetooth_mesh_key_configure_t));
837
838                                 /* Return DBUS Invocation*/
839                                 _bt_service_method_return(req_info->context, out_param, result);
840                                 _bt_free_info_from_invocation_list(req_info);
841                                 g_array_free(out_param, TRUE);
842                         }
843                         break;
844                 }
845                 case BT_MESH_NODE_TTL_EXECUTE: {
846                         bluetooth_mesh_node_ttl_info_t *event;
847                         bluetooth_mesh_node_ttl_info_t *req;
848
849                         event = (bluetooth_mesh_node_ttl_info_t*) param;
850                         req = (bluetooth_mesh_node_ttl_info_t*)req_info->user_data;
851                         req->ttl = event->ttl;
852
853                         if (!g_strcmp0(req->net_uuid, event->net_uuid) &&
854                                 req->unicast == event->unicast) {
855                                 /* Send Event */
856                                 __bt_mesh_send_node_ttl_configuration_event(result, req);
857
858                                 out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
859                                 g_array_append_vals(out_param, req, sizeof(bluetooth_mesh_node_ttl_info_t));
860
861                                 /* Return DBUS Invocation*/
862                                 _bt_service_method_return(req_info->context, out_param, result);
863                                 _bt_free_info_from_invocation_list(req_info);
864                                 g_array_free(out_param, TRUE);
865                         }
866                         break;
867                 }
868                 case BT_MESH_MODEL_CONFIGURE_APPKEY: {
869                         bluetooth_mesh_model_configure_t *event;
870                         bluetooth_mesh_model_configure_t *req;
871
872                         event = (bluetooth_mesh_model_configure_t*) param;
873                         req = (bluetooth_mesh_model_configure_t*)req_info->user_data;
874
875                         if (!g_strcmp0(req->net_uuid, event->net_uuid) &&
876                                 req->primary_unicast == event->primary_unicast) {
877                                 /* Send Event */
878                                 __bt_mesh_send_model_configure_appkey_event(result, req);
879
880                                 out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
881                                 g_array_append_vals(out_param, req, sizeof(bluetooth_mesh_model_configure_t));
882
883                                 /* Return DBUS Invocation*/
884                                 _bt_service_method_return(req_info->context, out_param, result);
885                                 _bt_free_info_from_invocation_list(req_info);
886                                 g_array_free(out_param, TRUE);
887                         }
888
889                         break;
890                 }
891                 case BT_MESH_MODEL_GET_APPKEY_LIST: {
892                         bluetooth_mesh_model_configure_t *event;
893                         bluetooth_mesh_model_configure_t *req;
894
895                         event = (bluetooth_mesh_model_configure_t*) param;
896                         req = (bluetooth_mesh_model_configure_t*)req_info->user_data;
897
898                         if (!g_strcmp0(req->net_uuid, event->net_uuid) &&
899                                 req->primary_unicast == event->primary_unicast) {
900                                 /* Send Event */
901                                 __bt_mesh_send_model_get_appkey_list_event(result, event);
902
903                                 out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
904                                 g_array_append_vals(out_param, req, sizeof(bluetooth_mesh_model_configure_t));
905
906                                 /* Return DBUS Invocation*/
907                                 _bt_service_method_return(req_info->context, out_param, result);
908                                 _bt_free_info_from_invocation_list(req_info);
909                                 g_array_free(out_param, TRUE);
910                         }
911                         break;
912                 }
913                 case BT_MESH_MODEL_GET_SUBSCRIPTION_LIST: {
914                         bluetooth_mesh_model_configure_t *event;
915                         bluetooth_mesh_model_configure_t *req;
916
917                         BT_INFO("Mesh: Handle event for BT_MESH_MODEL_GET_SUBSCRIPTION_LIST");
918                         event = (bluetooth_mesh_model_configure_t*) param;
919                         req = (bluetooth_mesh_model_configure_t*)req_info->user_data;
920
921                         if (!g_strcmp0(req->net_uuid, event->net_uuid) &&
922                                 req->primary_unicast == event->primary_unicast) {
923                                 /* Send Event */
924                                 __bt_mesh_send_model_get_subscription_list_event(result, event);
925
926                                 out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
927                                 g_array_append_vals(out_param, req, sizeof(bluetooth_mesh_model_configure_t));
928
929                                 /* Return DBUS Invocation*/
930                                 _bt_service_method_return(req_info->context, out_param, result);
931                                 _bt_free_info_from_invocation_list(req_info);
932                                 g_array_free(out_param, TRUE);
933                         }
934                         break;
935                 }
936                 case BT_MESH_MODEL_CONFIG_GROUP_SUB: {
937                         bluetooth_mesh_model_configure_t *event;
938                         bluetooth_mesh_model_configure_t *req;
939
940                         event = (bluetooth_mesh_model_configure_t*) param;
941                         req = (bluetooth_mesh_model_configure_t*)req_info->user_data;
942                         BT_INFO("Mesh: Event Network [%s] Req Network [%s]",
943                                 event->net_uuid, req->net_uuid);
944
945                         BT_INFO("Mesh: Event Unicast [0x%4.4x] Req Unicast [0x%4.4x]",
946                                 event->primary_unicast, req->primary_unicast);
947
948                         if (!g_strcmp0(req->net_uuid, event->net_uuid) &&
949                                 req->primary_unicast == event->primary_unicast) {
950
951                                 req->sub_addr = event->sub_addr;
952                                 BT_INFO("Mesh: Send event for Model Subscription");
953                                 /* Send Event */
954                                 __bt_mesh_send_model_subscription_configure_event(
955                                         BLUETOOTH_EVENT_MESH_MODEL_SUBSCRIPTION_CONFGURED,
956                                                 result, req);
957
958                                 out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
959                                 g_array_append_vals(out_param, req, sizeof(bluetooth_mesh_model_configure_t));
960
961                                 /* Return DBUS Invocation*/
962                                 _bt_service_method_return(req_info->context, out_param, result);
963                                 _bt_free_info_from_invocation_list(req_info);
964                                 g_array_free(out_param, TRUE);
965                         }
966                         break;
967                 }
968                 case BT_MESH_MODEL_CONFIG_VIRTUAL_GROUP_SUB: {
969                         bluetooth_mesh_model_configure_t *event;
970                         bluetooth_mesh_model_configure_t *req;
971
972                         event = (bluetooth_mesh_model_configure_t*) param;
973                         req = (bluetooth_mesh_model_configure_t*)req_info->user_data;
974                         BT_INFO("Mesh: Event Network [%s] Req Network [%s]",
975                                 event->net_uuid, req->net_uuid);
976
977                         BT_INFO("Mesh: Event Unicast [0x%4.4x] Req Unicast [0x%4.4x]",
978                                 event->primary_unicast, req->primary_unicast);
979                         if (!g_strcmp0(req->net_uuid, event->net_uuid) &&
980                                 req->primary_unicast == event->primary_unicast) {
981                                 /* Send Event */
982                                 __bt_mesh_send_model_subscription_configure_event( \
983                                         BLUETOOTH_EVENT_MESH_MODEL_VIRTUAL_SUBSCRIPTION_CONFGURED, \
984                                                 result, req);
985
986                                 out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
987                                 g_array_append_vals(out_param, req, sizeof(bluetooth_mesh_model_configure_t));
988
989                                 /* Return DBUS Invocation*/
990                                 _bt_service_method_return(req_info->context, out_param, result);
991                                 _bt_free_info_from_invocation_list(req_info);
992                                 g_array_free(out_param, TRUE);
993
994                         }
995                         break;
996                 }
997                 case BT_MESH_MODEL_GET_PUBLICATION: {
998                         BT_INFO("Mesh: Event for Model Get Publication Request");
999                         bluetooth_mesh_model_configure_t *event;
1000                         bluetooth_mesh_model_configure_t *req;
1001
1002                         event = (bluetooth_mesh_model_configure_t*) param;
1003                         req = (bluetooth_mesh_model_configure_t*)req_info->user_data;
1004
1005                         if (!g_strcmp0(req->net_uuid, event->net_uuid) &&
1006                                         req->primary_unicast == event->primary_unicast) {
1007                                 /* Send Event */
1008                                 BT_INFO("Mesh: Send Model Publication status for Get Request");
1009                                 __bt_mesh_send_model_publication_status_event( \
1010                                                 BLUETOOTH_EVENT_MESH_MODEL_PUBLICATION_STATUS, \
1011                                                 result, event);
1012
1013                                 out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
1014                                 g_array_append_vals(out_param, req, sizeof(bluetooth_mesh_model_configure_t));
1015
1016                                 /* Return DBUS Invocation*/
1017                                 _bt_service_method_return(req_info->context, out_param, result);
1018                                 _bt_free_info_from_invocation_list(req_info);
1019                                 g_array_free(out_param, TRUE);
1020                         }
1021                         break;
1022                 }
1023                 case BT_MESH_MODEL_SET_PUBLICATION: {
1024                         BT_INFO("Mesh: Event for Model Set Publication Request");
1025                         bluetooth_mesh_model_configure_t *event;
1026                         bluetooth_mesh_model_configure_t *req;
1027
1028                         event = (bluetooth_mesh_model_configure_t*) param;
1029                         req = (bluetooth_mesh_model_configure_t*)req_info->user_data;
1030
1031                         if (!g_strcmp0(req->net_uuid, event->net_uuid) &&
1032                                 req->primary_unicast == event->primary_unicast) {
1033                                 /* Send Event */
1034                                 BT_INFO("Mesh: Send Model Publication status for Set Request");
1035                                 __bt_mesh_send_model_publication_status_event( \
1036                                         BLUETOOTH_EVENT_MESH_MODEL_PUBLICATION_STATUS, \
1037                                                 result, req);
1038
1039                                 out_param = g_array_new(FALSE, FALSE, sizeof(gchar));
1040                                 g_array_append_vals(out_param, req, sizeof(bluetooth_mesh_model_configure_t));
1041
1042                                 /* Return DBUS Invocation*/
1043                                 _bt_service_method_return(req_info->context, out_param, result);
1044                                 _bt_free_info_from_invocation_list(req_info);
1045                                 g_array_free(out_param, TRUE);
1046                         }
1047                         break;
1048                 }
1049                 default:
1050                         BT_DBG("Unknown function(%d)", service_function);
1051                         break;
1052                 }
1053         }
1054 }
1055
1056 const char *__mesh_status_to_string(uint8_t err)
1057 {
1058         switch (err) {
1059         case MESH_STATUS_SUCCESS: return "Success";
1060         case MESH_STATUS_INVALID_ADDRESS: return "Invalid Address";
1061         case MESH_STATUS_INVALID_MODEL: return "Invalid Model";
1062         case MESH_STATUS_INVALID_APPKEY: return "Invalid AppKey";
1063         case MESH_STATUS_INVALID_NETKEY: return "Invalid NetKey";
1064         case MESH_STATUS_INSUFF_RESOURCES: return "Insufficient Resources";
1065         case MESH_STATUS_IDX_ALREADY_STORED: return "Key Idx Already Stored";
1066         case MESH_STATUS_INVALID_PUB_PARAM: return "Invalid Publish Parameters";
1067         case MESH_STATUS_NOT_SUB_MOD: return "Not a Subscribe Model";
1068         case MESH_STATUS_STORAGE_FAIL: return "Storage Failure";
1069         case MESH_STATUS_FEATURE_NO_SUPPORT: return "Feature Not Supported";
1070         case MESH_STATUS_CANNOT_UPDATE: return "Cannot Update";
1071         case MESH_STATUS_CANNOT_REMOVE: return "Cannot Remove";
1072         case MESH_STATUS_CANNOT_BIND: return "Cannot bind";
1073         case MESH_STATUS_UNABLE_CHANGE_STATE: return "Unable to change state";
1074         case MESH_STATUS_CANNOT_SET: return "Cannot set";
1075         case MESH_STATUS_UNSPECIFIED_ERROR: return "Unspecified error";
1076         case MESH_STATUS_INVALID_BINDING: return "Invalid Binding";
1077
1078         default: return "Unknown";
1079         }
1080 }
1081
1082 static void __mesh_handle_model_subscription_event(int result,
1083                 bluetooth_mesh_model_configure_t *param,
1084                         const struct mesh_config_cmd *cmd)
1085 {
1086         BT_INFO("Mesh: Model Subscription Event: Request [%d]", cmd->opcode);
1087         switch (cmd->opcode) {
1088         /* Fall through */
1089         case MESH_OPCODE_CONFIG_MODEL_SUB_ADD:
1090         case MESH_OPCODE_CONFIG_MODEL_SUB_DELETE:
1091         case MESH_OPCODE_CONFIG_MODEL_SUB_OVERWRITE:
1092                 /* Model Bind/UnBind Event */
1093         BT_INFO("Mesh: Handle Event for Request: BT_MESH_MODEL_CONFIG_GROUP_SUB");
1094         __bt_mesh_handle_pending_dev_config_request_info(result,
1095                         BT_MESH_MODEL_CONFIG_GROUP_SUB, param,
1096                                 sizeof(bluetooth_mesh_model_configure_t));
1097                 break;
1098         case MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_ADD:
1099         case MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_DELETE:
1100         case MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_OVERWRITE:
1101         BT_INFO("Mesh: Handle Event for Request: BT_MESH_MODEL_CONFIG_VIRTUAL_GROUP_SUB");
1102         __bt_mesh_handle_pending_dev_config_request_info(result,
1103                         BT_MESH_MODEL_CONFIG_VIRTUAL_GROUP_SUB, param,
1104                                 sizeof(bluetooth_mesh_model_configure_t));
1105                 break;
1106         case MESH_OPCODE_CONFIG_MODEL_SUB_DELETE_ALL:
1107         BT_INFO("Mesh: Handle Event for Request: MESH_OPCODE_CONFIG_MODEL_SUB_DELETE_ALL");
1108         __bt_mesh_handle_pending_dev_config_request_info(result,
1109                         BT_MESH_MODEL_CONFIG_GROUP_SUB, param,
1110                                 sizeof(bluetooth_mesh_model_configure_t));
1111         __bt_mesh_handle_pending_dev_config_request_info(result,
1112                         BT_MESH_MODEL_CONFIG_VIRTUAL_GROUP_SUB, param,
1113                                 sizeof(bluetooth_mesh_model_configure_t));
1114                 break;
1115         default:
1116                 break;
1117         }
1118 }
1119
1120 void _bt_mesh_config_client_devkey_msg_handler(
1121                 event_mesh_devkey_message_t *event)
1122 {
1123         uint32_t opcode;
1124         const struct mesh_config_cmd *cmd;
1125         uint16_t data_len = event->data_len;
1126         uint8_t *data = event->data;
1127         int result = BLUETOOTH_ERROR_NONE;
1128         uint16_t app_idx;
1129         uint16_t addr;
1130         uint16_t net_idx;
1131         uint16_t elem_addr;
1132         uint16_t ele_addr;
1133         uint32_t mod_id;
1134         int n;
1135         struct mesh_pending_request *req;
1136
1137         if (_bt_mesh_util_opcode_get(data, data_len, &opcode, &n)) {
1138                 BT_INFO("Mesh: Opcode of response data [0x%2.2x], actual data len [%d]", opcode, n);
1139                 data_len -= n;
1140                 data += n;
1141         } else
1142                 return;
1143
1144         BT_INFO("Mesh: Received %s (len %u) opcode [0x%2.2x]",
1145                 __mesh_get_opcode_string(opcode), data_len, opcode);
1146
1147         req = __bt_mesh_get_request_by_response(event->source,
1148                 event->net_uuid.uuid, (opcode & ~MESH_OPCODE_UNRELIABLE));
1149         if (req) {
1150                 BT_INFO("Mesh: Got Config Request");
1151                 cmd = req->cmd;
1152                 __mesh_request_remove(req);
1153                 l_queue_remove(pending_requests, req);
1154         } else
1155                 cmd = NULL;
1156
1157
1158         switch (opcode & ~MESH_OPCODE_UNRELIABLE) {
1159         default:
1160                 return;
1161         case MESH_OPCODE_CONFIG_MODEL_PUB_STATUS: {
1162                 if (data_len != 12 && data_len != 14)
1163                         break;
1164                 bluetooth_mesh_model_configure_t param;
1165                 memset(&param, 0x00, sizeof(bluetooth_mesh_model_configure_t));
1166
1167                 _bt_mesh_util_convert_hex_to_string((uint8_t *) event->net_uuid.uuid, 16, param.net_uuid,
1168                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
1169
1170                 BT_INFO("\nNode %4.4x Model Publication status %s\n",
1171                                 event->source, __mesh_status_to_string(data[0]));
1172
1173                 if (data[0] != MESH_STATUS_SUCCESS)
1174                         result = BLUETOOTH_ERROR_INTERNAL;
1175
1176                 /* Extract Element Address */
1177                 ele_addr = l_get_le16(data + 1);
1178
1179                 /* Extract Model ID */
1180                 if (data_len == 14) {
1181                         /* vendor Model */
1182                         mod_id = l_get_le16(data + 10 + 2);
1183                         mod_id = l_get_le16(data) << 16 | mod_id;
1184                 } else {
1185                         /* BT SIG Model */
1186                         mod_id = l_get_le16(data + 10);
1187                         mod_id = MESH_VENDOR_ID_MASK | mod_id;
1188                 }
1189
1190                 param.model = mod_id;
1191                 BT_INFO("Model ID\t%4.4x\n", mod_id);
1192
1193                 param.primary_unicast = event->source;
1194                 param.elem_index = ele_addr - event->source;
1195                 /* Extract Publish Address */
1196                 param.pub_addr = l_get_le16(data + 3);
1197                 BT_INFO("Mesh: Pub Address [0x%2.2x]", param.pub_addr);
1198
1199                 /* Extract Appkey Index */
1200                 param.appkey_idx =  l_get_le16(data + 5);
1201                 BT_INFO("Mesh: AppKey Idx [0x%2.2x]", param.appkey_idx);
1202
1203                 /* Extract TTL */
1204                 param.ttl = data[6];
1205                 BT_INFO("Mesh: TTL [0x%x]", param.ttl);
1206
1207                 /* Extract Period */
1208                 param.period = data[7];
1209                 if (!cmd)
1210                         break;
1211
1212                 if (cmd->opcode == MESH_OPCODE_CONFIG_MODEL_PUB_GET)
1213                         __bt_mesh_handle_pending_dev_config_request_info(result,
1214                                 BT_MESH_MODEL_GET_PUBLICATION, &param,
1215                                 sizeof(bluetooth_mesh_model_configure_t));
1216                 else
1217                         __bt_mesh_handle_pending_dev_config_request_info(result,
1218                                 BT_MESH_MODEL_SET_PUBLICATION, &param,
1219                                 sizeof(bluetooth_mesh_model_configure_t));
1220                 break;
1221         }
1222         case MESH_OPCODE_CONFIG_MODEL_SUB_STATUS: {
1223                 if (data_len != 7 && data_len != 9)
1224                         break;
1225                 bluetooth_mesh_model_configure_t param;
1226                 memset(&param, 0x00, sizeof(bluetooth_mesh_model_configure_t));
1227
1228                 _bt_mesh_util_convert_hex_to_string(
1229                         (uint8_t *) event->net_uuid.uuid, 16, param.net_uuid,
1230                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
1231
1232                 BT_INFO("\nNode %4.4x Subscription status %s\n",
1233                                 event->source, __mesh_status_to_string(data[0]));
1234
1235                 if (data[0] != MESH_STATUS_SUCCESS)
1236                         result = BLUETOOTH_ERROR_INTERNAL;
1237
1238                 if (!cmd) {
1239                         BT_INFO("Mesh: Command not found!!");
1240                         break;
1241                 }
1242
1243                 ele_addr = l_get_le16(data + 1);
1244                 addr = l_get_le16(data + 3);
1245                 BT_INFO("Element Addr\t%4.4x\n", ele_addr);
1246                 BT_INFO("Message Source Addr\t%4.4x\n", event->source);
1247
1248                 if (data_len == 9) {
1249                         /* vendor Model */
1250                         mod_id = l_get_le16(data + 5 + 2);
1251                         mod_id = l_get_le16(data) << 16 | mod_id;
1252                 } else {
1253                         /* BT SIG Model */
1254                         mod_id = l_get_le16(data + 5);
1255                         mod_id = MESH_VENDOR_ID_MASK | mod_id;
1256                 }
1257
1258                 param.primary_unicast = event->source;
1259                 param.elem_index = ele_addr - event->source;
1260                 /* Subscription address, unassigned address in case of Delete All command */
1261                 param.sub_addr = addr;
1262                 param.model = mod_id;
1263                 BT_INFO("Subscr Addr\t%4.4x\n", addr);
1264                 BT_INFO("Model ID\t%4.4x\n", mod_id);
1265
1266                 if (cmd)
1267                         __mesh_handle_model_subscription_event(result, &param, cmd);
1268
1269                 break;
1270         }
1271         case MESH_OPCODE_CONFIG_DEFAULT_TTL_STATUS: {
1272                 if (data_len != 1)
1273                         break;
1274                 bluetooth_mesh_node_ttl_info_t param;
1275                 memset(&param, 0x00, sizeof(bluetooth_mesh_node_ttl_info_t));
1276
1277                 BT_INFO("Node %4.4x Default TTL %d", event->source, data[0]);
1278                  _bt_mesh_util_convert_hex_to_string(
1279                         (uint8_t *) event->net_uuid.uuid, 16, param.net_uuid,
1280                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
1281                 param.unicast = event->source;
1282                 param.ttl = data[0];
1283
1284                 if (!_bt_mesh_network_save_remote_node_ttl(event->net_uuid.uuid,
1285                                 event->source,  data[0])) {
1286                         result = BLUETOOTH_ERROR_INTERNAL;
1287                         BT_INFO("Failed to save node TTL");
1288                 }
1289
1290                 /* Remote Node TTL event */
1291                 __bt_mesh_handle_pending_dev_config_request_info(result,
1292                         BT_MESH_NODE_TTL_EXECUTE, &param,
1293                                 sizeof(bluetooth_mesh_node_ttl_info_t));
1294                 break;
1295         }
1296         case MESH_OPCODE_MODEL_APP_STATUS: {
1297                 if (data_len != 7 && data_len != 9)
1298                         break;
1299                 bluetooth_mesh_model_configure_t param;
1300                 memset(&param, 0x00, sizeof(bluetooth_mesh_model_configure_t));
1301
1302                  _bt_mesh_util_convert_hex_to_string(
1303                         (uint8_t *) event->net_uuid.uuid, 16, param.net_uuid,
1304                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
1305                 BT_INFO("Node %4.4x: Model App status %s\n", event->source,
1306                         __mesh_status_to_string(data[0]));
1307
1308                 if (data[0] != MESH_STATUS_SUCCESS)
1309                         result = BLUETOOTH_ERROR_INTERNAL;
1310
1311                 elem_addr = l_get_le16(data + 1);
1312                 app_idx = l_get_le16(data + 3);
1313
1314                 BT_INFO("Element Addr\t%4.4x", elem_addr);
1315                 if (data_len == 9) {
1316                         /* vendor Model */
1317                         mod_id = l_get_le16(data + 5 + 2);
1318                         mod_id = l_get_le16(data) << 16 | mod_id;
1319                 } else {
1320                         /* BT SIG Model */
1321                         mod_id = l_get_le16(data + 5);
1322                         mod_id = MESH_VENDOR_ID_MASK | mod_id;
1323                 }
1324
1325                 param.primary_unicast = event->source;
1326                 param.elem_index = elem_addr - event->source;
1327                 param.appkey_idx = app_idx;
1328                 param.model = mod_id;
1329                 BT_INFO("AppIdx\t\t%u (0x%3.3x)\n ", app_idx, app_idx);
1330
1331                 /* Model Bind/UnBind Event */
1332                 __bt_mesh_handle_pending_dev_config_request_info(result,
1333                         BT_MESH_MODEL_CONFIGURE_APPKEY, &param,
1334                                 sizeof(bluetooth_mesh_model_configure_t));
1335                 break;
1336         }
1337         case MESH_OPCODE_MODEL_APP_LIST: {
1338                 if (data_len < 5)
1339                         break;
1340                 GArray *garray;
1341                 int total = 0;
1342                 bluetooth_mesh_model_configure_t param;
1343                 memset(&param, 0x00, sizeof(bluetooth_mesh_model_configure_t));
1344
1345                 _bt_mesh_util_convert_hex_to_string(
1346                         (uint8_t *) event->net_uuid.uuid, 16, param.net_uuid,
1347                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
1348
1349                 garray = g_array_new(FALSE, FALSE, sizeof(gchar));
1350
1351                 BT_INFO("\nNode %4.4x Model AppIdx status %s\n",
1352                                 event->source, __mesh_status_to_string(data[0]));
1353
1354                 BT_INFO("Element Addr\t%4.4x\n", l_get_le16(data + 1));
1355                 BT_INFO("Model ID\t%4.4x\n", l_get_le16(data + 3));
1356
1357                 elem_addr = l_get_le16(data + 1);
1358                 /* BT SIG Model */
1359                 mod_id = l_get_le16(data + 3);
1360                 mod_id = MESH_VENDOR_ID_MASK | mod_id;
1361
1362                 param.primary_unicast = event->source;
1363                 param.elem_index = elem_addr - event->source;
1364                 param.model = mod_id;
1365
1366                 data += 5;
1367                 data_len -= 5;
1368
1369                 while (data_len >= 3) {
1370                         app_idx = l_get_le16(data) & 0xfff;
1371                         g_array_append_vals(garray, &app_idx, sizeof(uint16_t));
1372                         BT_INFO("\t%u (0x%3.3x)\n", app_idx, app_idx);
1373
1374                         app_idx = l_get_le16(data + 1) >> 4;
1375                         g_array_append_vals(garray, &app_idx, sizeof(uint16_t));
1376                         BT_INFO("\t%u (0x%3.3x)\n", app_idx, app_idx);
1377                         data += 3;
1378                         data_len -= 3;
1379                 }
1380
1381                 if (data_len == 2) {
1382                         app_idx = l_get_le16(data) & 0xfff;
1383                         g_array_append_vals(garray, &app_idx, sizeof(uint16_t));
1384                         BT_INFO("\t %u (0x%3.3x)\n", app_idx, app_idx);
1385                 }
1386                 total = garray->len / sizeof(uint16_t);
1387                 param.appkey_list = (uint16_t **)g_malloc0(sizeof(uint16_t*) * garray->len);
1388                 param.appkeylist_count = total;
1389                 for (int i = 0; i < total; i++) {
1390                         param.appkey_list[i] = g_malloc(sizeof(uint16_t));
1391                         *param.appkey_list[i] = g_array_index(garray, uint16_t, i);
1392                 }
1393                 g_array_free(garray, TRUE);
1394
1395                 __bt_mesh_handle_pending_dev_config_request_info(result,
1396                         BT_MESH_MODEL_GET_APPKEY_LIST, &param,
1397                                 sizeof(bluetooth_mesh_model_configure_t));
1398                 break;
1399         }
1400         case MESH_OPCODE_CONFIG_MODEL_SUB_LIST: {
1401                 if (data_len < 5)
1402                         break;
1403                 int total = 0;
1404                 int i = 0;
1405                 bluetooth_mesh_model_configure_t param;
1406                 memset(&param, 0x00, sizeof(bluetooth_mesh_model_configure_t));
1407
1408                 _bt_mesh_util_convert_hex_to_string((uint8_t *) event->net_uuid.uuid, 16, param.net_uuid,
1409                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
1410
1411                 BT_INFO("\nNode %4.4x BT SIG Model Subscription List status %s\n",
1412                                 event->source, __mesh_status_to_string(data[0]));
1413
1414                 BT_INFO("Element Addr\t%4.4x\n", l_get_le16(data + 1));
1415                 elem_addr = l_get_le16(data + 1);
1416
1417                 /* BT SIG Model */
1418                 mod_id = l_get_le16(data + 3);
1419                 mod_id = MESH_VENDOR_ID_MASK | mod_id;
1420                 BT_INFO("Model ID\t%4.4x\n", mod_id);
1421
1422                 param.primary_unicast = event->source;
1423                 param.elem_index = elem_addr - event->source;
1424                 param.model = mod_id;
1425                 BT_INFO("Mesh: Data length of All Models Together [%d]", data_len - 5);
1426                 total = (data_len -  5)/2;
1427                 param.sublist_count = total;
1428                 BT_INFO("Mesh: Total Number of subscriptions [%d]", total);
1429                 if (total) {
1430                         param.sub_list = (uint16_t **)g_malloc0(sizeof(uint16_t*) * total);
1431
1432                         i = 5;
1433                         for (int k = 0; i < data_len; k++, i += 2) {
1434                                 BT_INFO("Mesh: Subscription Addr \t\t%4.4x\n ", l_get_le16(data + i));
1435                                 param.sub_list[k] = g_malloc(sizeof(uint16_t));
1436                                 *param.sub_list[k] = l_get_le16(data + i);
1437                         }
1438                 }
1439                 __bt_mesh_handle_pending_dev_config_request_info(result,
1440                         BT_MESH_MODEL_GET_SUBSCRIPTION_LIST, &param,
1441                                 sizeof(bluetooth_mesh_model_configure_t));
1442                 break;
1443         }
1444         case MESH_OPCODE_CONFIG_VEND_MODEL_SUB_LIST: {
1445                 if (data_len < 7)
1446                         break;
1447                 int total = 0;
1448                 int i = 0;
1449                 bluetooth_mesh_model_configure_t param;
1450                 memset(&param, 0x00, sizeof(bluetooth_mesh_model_configure_t));
1451
1452                 _bt_mesh_util_convert_hex_to_string(
1453                         (uint8_t *) event->net_uuid.uuid, 16, param.net_uuid,
1454                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
1455
1456                 BT_INFO("\nNode %4.4x Vendor Model Subscription List status %s\n",
1457                                 event->source, __mesh_status_to_string(data[0]));
1458
1459                 BT_INFO("Element Addr\t%4.4x\n", l_get_le16(data + 1));
1460                 elem_addr = l_get_le16(data + 1);
1461
1462                 /* VENDOR Model */
1463                 mod_id = l_get_le16(data + 5);
1464                 mod_id = l_get_le16(data + 3) << 16 | mod_id;
1465
1466                 BT_INFO("Model ID\t%4.4x\n", mod_id);
1467
1468                 param.primary_unicast = event->source;
1469                 param.elem_index = elem_addr - event->source;
1470                 param.model = mod_id;
1471
1472                 BT_INFO("Mesh: Data length of All Models Together [%d]", data_len - 7);
1473                 total = (data_len -  7)/2;
1474                 param.sublist_count = total;
1475
1476                 BT_INFO("Mesh: Total Number of subscriptions [%d]", total);
1477                 if (total) {
1478                         param.sub_list = (uint16_t **)g_malloc0(sizeof(uint16_t*) * total);
1479
1480                         i = 7;
1481                         for (int k = 0; i < data_len; k++, i += 2) {
1482                                 BT_INFO("Mesh: Subscription Addr \t\t%4.4x\n ", l_get_le16(data + i));
1483                                 param.sub_list[k] = g_malloc(sizeof(uint16_t));
1484                                 *param.sub_list[k] = l_get_le16(data + i);
1485                         }
1486                 }
1487                 __bt_mesh_handle_pending_dev_config_request_info(result,
1488                         BT_MESH_MODEL_GET_SUBSCRIPTION_LIST, &param,
1489                                 sizeof(bluetooth_mesh_model_configure_t));
1490                 break;
1491         }
1492         case MESH_OPCODE_DEV_COMP_STATUS: {
1493                 if (data_len < MESH_MINIMUM_COMPOSITION_LEN)
1494                         break;
1495                 bluetooth_mesh_node_features_t features;
1496                 memset(&features, 0x00, sizeof(bluetooth_mesh_node_features_t));
1497                 BT_INFO("Mesh: Got Response for Device Composition Data");
1498                 __bt_mesh_print_device_composition_data(data, data_len);
1499
1500                 if (!_bt_mesh_network_save_remote_node_composition(
1501                         event->net_uuid.uuid, event->source, data, data_len)) {
1502                         result = BLUETOOTH_ERROR_INTERNAL;
1503                         BT_INFO("Failed to save node composition!");
1504                 }
1505                 /* Browse Remote Node event */
1506                 __bt_mesh_handle_pending_dev_config_request_info(result,
1507                         BT_MESH_NODE_BROWSE, event, sizeof(event_mesh_devkey_message_t));
1508
1509                 /* Vendor Features Discover event */
1510                 _bt_mesh_util_convert_hex_to_string(
1511                         (uint8_t *) event->net_uuid.uuid, 16, features.net_uuid,
1512                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
1513                 features.unicast = event->source;
1514                 BT_INFO("Mesh: Net UUID [%s]", features.net_uuid);
1515
1516                 BT_INFO("Mesh: Composition status for node unicast [0x%2.2x]",
1517                         event->source);
1518                 if (!_bt_mesh_node_get_vendor_features(event->net_uuid.uuid,
1519                         event->source, &features)) {
1520                         BT_ERR("Mesh: Failed to get Vendor Specific Infor for [0x%2.2x]",
1521                                 event->source);
1522                         result = BLUETOOTH_ERROR_INTERNAL;
1523                 } else {
1524                         BT_INFO("Mesh: Got Feature informations for [0x%2.2x]",
1525                                 event->source);
1526                 }
1527                 __bt_mesh_handle_pending_dev_config_request_info(result,
1528                         BT_MESH_NODE_GET_VENDOR_FEATURES, &features,
1529                                 sizeof(bluetooth_mesh_node_features_t));
1530                 break;
1531         }
1532         case MESH_OPCODE_NETKEY_STATUS: {
1533                 if (data_len != 3)
1534                         break;
1535
1536                 bluetooth_mesh_key_configure_t param;
1537                 memset(&param, 0x00, sizeof(bluetooth_mesh_key_configure_t));
1538
1539                 BT_INFO("Mesh: Node %4.4x NetKey status %s",
1540                         event->source,  __mesh_status_to_string(data[0]));
1541                 net_idx = l_get_le16(data + 1) & 0xfff;
1542
1543                 BT_INFO("\tNetKey %u (0x%3.3x)", net_idx, net_idx);
1544
1545                 if (data[0] != 0)
1546                         result = BLUETOOTH_ERROR_INTERNAL;
1547
1548                 if (!cmd)
1549                         break;
1550
1551                 _bt_mesh_util_convert_hex_to_string(
1552                         (uint8_t *) event->net_uuid.uuid, 16, param.net_uuid,
1553                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
1554                 param.primary_unicast = event->source;
1555                 param.netkey_idx = net_idx;
1556                 param.is_netkey = true;
1557
1558                 BT_INFO("Mesh: Resp recvd from node unicast [0x%4.4x]", event->source);
1559                 if (cmd->opcode == MESH_OPCODE_NETKEY_ADD) {
1560                         BT_INFO("Mesh: Resp recvd: MESH_OPCODE_NETKEY_ADD");
1561                         if (result == BLUETOOTH_ERROR_NONE) {
1562                                 if (!_bt_mesh_network_save_remote_node_netkey(
1563                                                         event->net_uuid.uuid, event->source, net_idx)) {
1564                                         result = BLUETOOTH_ERROR_INTERNAL;
1565                                         BT_INFO("Failed to save node Netkey!");
1566                                 }
1567                         }
1568                         param.op = BLUETOOTH_MESH_NODE_KEY_ADD;
1569                 } else if (cmd->opcode == MESH_OPCODE_NETKEY_DELETE) {
1570                         BT_INFO("Mesh: Resp recvd: MESH_OPCODE_NETKEY_DELETE");
1571                         if (result == BLUETOOTH_ERROR_NONE) {
1572                                 if (!_bt_mesh_network_delete_remote_node_netkey(
1573                                                         event->net_uuid.uuid, event->source, net_idx)) {
1574                                         result = BLUETOOTH_ERROR_INTERNAL;
1575                                         BT_INFO("Failed to delete node Netkey!");
1576                                 }
1577                         }
1578                         param.op = BLUETOOTH_MESH_NODE_KEY_DELETE;
1579                 } else if (cmd->opcode == MESH_OPCODE_NETKEY_UPDATE) {
1580                         BT_INFO("Mesh: Resp recvd: MESH_OPCODE_NETKEY_UPDATE");
1581                         param.op = BLUETOOTH_MESH_NODE_KEY_UPDATE;
1582                 }
1583                 /* Node Net Key Configure event */
1584                 __bt_mesh_handle_pending_dev_config_request_info(result,
1585                         BT_MESH_NODE_CONFIGURE_KEY,
1586                                 &param, sizeof(bluetooth_mesh_key_configure_t));
1587                 break;
1588         }
1589         case MESH_OPCODE_APPKEY_STATUS: {
1590                 if (data_len != 4)
1591                         break;
1592
1593                 bluetooth_mesh_key_configure_t param;
1594                 memset(&param, 0x00, sizeof(bluetooth_mesh_key_configure_t));
1595
1596                 BT_INFO("Mesh: Node %4.4x AppKey status %s\n", event->source,
1597                                 __mesh_status_to_string(data[0]));
1598                 net_idx = l_get_le16(data + 1) & 0xfff;
1599                 app_idx = l_get_le16(data + 2) >> 4;
1600
1601                 BT_INFO("NetKey\t%u (0x%3.3x)\n", net_idx, net_idx);
1602                 BT_INFO("AppKey\t%u (0x%3.3x)\n", app_idx, app_idx);
1603
1604                 if (data[0] != MESH_STATUS_SUCCESS)
1605                         result = BLUETOOTH_ERROR_INTERNAL;
1606
1607                 if (!cmd)
1608                         break;
1609
1610                 _bt_mesh_util_convert_hex_to_string(
1611                         (uint8_t *) event->net_uuid.uuid, 16, param.net_uuid,
1612                                 BLUETOOTH_MESH_NETWORK_UUID_STRING_LENGTH + 1);
1613
1614                 param.primary_unicast = event->source;
1615                 param.netkey_idx = net_idx;
1616                 param.appkey_idx = app_idx;
1617                 param.is_netkey = false;
1618
1619                 if (cmd->opcode == MESH_OPCODE_APPKEY_ADD) {
1620                         BT_INFO("Mesh: Resp recvd: MESH_OPCODE_APPKEY_ADD");
1621                         if (result == BLUETOOTH_ERROR_NONE) {
1622                                 if (!_bt_mesh_network_save_remote_node_appkey(
1623                                                 event->net_uuid.uuid, event->source,
1624                                                 net_idx, app_idx)) {
1625                                         result = BLUETOOTH_ERROR_INTERNAL;
1626                                         BT_INFO("Failed to save node Appkey!");
1627                                 }
1628                         }
1629                         param.op = BLUETOOTH_MESH_NODE_KEY_ADD;
1630                 } else if (cmd->opcode == MESH_OPCODE_APPKEY_DELETE) {
1631                         BT_INFO("Mesh: Resp recvd: MESH_OPCODE_APPKEY_DELETE");
1632                         if (result == BLUETOOTH_ERROR_NONE) {
1633                                 if (!_bt_mesh_network_delete_remote_node_appkey(
1634                                                 event->net_uuid.uuid, event->source,
1635                                                 net_idx, app_idx)) {
1636                                         result = BLUETOOTH_ERROR_INTERNAL;
1637                                         BT_INFO("Failed to delete node Appkey!");
1638                                 }
1639                         }
1640                         param.op = BLUETOOTH_MESH_NODE_KEY_DELETE;
1641                 } else if (cmd->opcode == MESH_OPCODE_APPKEY_UPDATE) {
1642                         BT_INFO("Mesh: Resp recvd: MESH_OPCODE_APPKEY_UPDATE");
1643                         param.op = BLUETOOTH_MESH_NODE_KEY_UPDATE;
1644                 }
1645
1646                 /* Node App Key Configure event */
1647                 __bt_mesh_handle_pending_dev_config_request_info(result,
1648                         BT_MESH_NODE_CONFIGURE_KEY,
1649                                 &param, sizeof(bluetooth_mesh_key_configure_t));
1650                 break;
1651         }
1652         }
1653 }
1654
1655 static gboolean __bt_mesh_vendor_feature_event_handler(gpointer data)
1656 {
1657         bluetooth_mesh_node_features_t *result = (bluetooth_mesh_node_features_t*) data;
1658         __bt_mesh_handle_pending_dev_config_request_info(
1659                 BLUETOOTH_ERROR_NONE,
1660                         BT_MESH_NODE_GET_VENDOR_FEATURES,
1661                                 result, sizeof(bluetooth_mesh_node_features_t));
1662         g_free(result);
1663         return FALSE;
1664 }
1665
1666 int _bt_mesh_node_discover_vendor_features(const char *app_cred, const char *sender,
1667                 bluetooth_mesh_node_features_t *req)
1668 {
1669         int ret = OAL_STATUS_SUCCESS;
1670         uint16_t dest;
1671         uint16_t netkey_idx;
1672         uint16_t data_len;
1673         oal_uuid_t net_uuid;
1674         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
1675
1676         BT_INFO("Mesh: Vendor features for Network UUID [%s]", req->net_uuid);
1677         _bt_mesh_util_convert_string_to_hex(req->net_uuid,
1678                         strlen(req->net_uuid), net_uuid.uuid, 16);
1679         /* Check if Node's vendor features are already svaed or not */
1680         if (_bt_mesh_node_get_vendor_features(net_uuid.uuid, req->unicast, req)) {
1681                 BT_INFO("Mesh: Vendor Features already available for Node: Unicast [0x%.2x]",
1682                                 req->unicast);
1683                 /* Schedule event ot Application */
1684                 bluetooth_mesh_node_features_t *event = \
1685                         g_memdup(req, sizeof(bluetooth_mesh_node_features_t));
1686                 g_idle_add(__bt_mesh_vendor_feature_event_handler, (gpointer) event);
1687                 return BLUETOOTH_ERROR_NONE;
1688         }
1689
1690         /* If Scanning is going on */
1691         if (_bt_mesh_is_provisioning() ||
1692                         _bt_mesh_is_scanning()) {
1693                 BT_ERR("Device is buzy..");
1694                 return BLUETOOTH_ERROR_DEVICE_BUSY;
1695         }
1696
1697         _bt_mesh_util_convert_string_to_hex(req->net_uuid,
1698                         strlen(req->net_uuid), net_uuid.uuid, 16);
1699
1700         dest = req->unicast;
1701         BT_INFO("Mesh: Get Vendor Features for Remote Node Unicast [0x%2.2x]", dest);
1702
1703         /* Check pending request */
1704         if (_bt_mesh_check_pending_request(MESH_OPCODE_DEV_COMP_GET,
1705                                 dest, net_uuid.uuid)) {
1706                 BT_ERR("Device is buzy..");
1707                 return BLUETOOTH_ERROR_DEVICE_BUSY;
1708         }
1709
1710         BT_INFO("Mesh: Browse Remote Node: Unicast [0x%2.2x]", dest);
1711         /* Get Subnet index of the rmeote node for TX encryption */
1712         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid, dest);
1713         if (netkey_idx == MESH_NET_IDX_INVALID)
1714                 return BLUETOOTH_ERROR_INTERNAL;
1715
1716         data_len = _bt_mesh_util_opcode_set(MESH_OPCODE_DEV_COMP_GET,
1717                         buffer);
1718
1719         /* By default, use page 0 */
1720         buffer[data_len++] = 0;
1721         ret = mesh_conf_send_message(&net_uuid, dest, true,
1722                         netkey_idx, buffer, data_len);
1723
1724         if (ret != OAL_STATUS_SUCCESS) {
1725                 BT_ERR("ret: %d", ret);
1726                 return BLUETOOTH_ERROR_INTERNAL;
1727         }
1728
1729         /* Queue the request with timeout */
1730         __bt_mesh_add_request(MESH_OPCODE_DEV_COMP_GET,
1731                         dest, net_uuid.uuid, NULL);
1732         return BLUETOOTH_ERROR_NONE;
1733 }
1734
1735 int _bt_mesh_browse_remote_node(const char *app_cred,
1736         const char *sender,
1737                 bluetooth_mesh_node_discover_t *req)
1738 {
1739         int ret = OAL_STATUS_SUCCESS;
1740         uint16_t dest;
1741         uint16_t netkey_idx;
1742         uint16_t data_len;
1743         oal_uuid_t net_uuid;
1744         oal_uuid_t dev_uuid;
1745         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
1746
1747         /* If Scanning is going on */
1748         if (_bt_mesh_is_provisioning() ||
1749                         _bt_mesh_is_scanning()) {
1750                 BT_ERR("Device is buzy..");
1751                 return BLUETOOTH_ERROR_DEVICE_BUSY;
1752         }
1753
1754         _bt_mesh_util_convert_string_to_hex(req->net_uuid,
1755                 strlen(req->net_uuid), net_uuid.uuid, 16);
1756         _bt_mesh_util_convert_string_to_hex(req->dev_uuid,
1757                 strlen(req->dev_uuid), dev_uuid.uuid, 16);
1758
1759         BT_INFO("Mesh: Browse Node UUID [%s]", req->dev_uuid);
1760
1761         /* Get Remote Node unicast address from Dev UUID */
1762         if (!_bt_mesh_node_get_unicast_from_dev_uuid(net_uuid.uuid,
1763                         dev_uuid.uuid, &dest))
1764                 return BLUETOOTH_ERROR_INTERNAL;
1765
1766         BT_INFO("Mesh: Browse Remote Node: Unicast [0x%2.2x]", dest);
1767         /* Check pending request */
1768         if (_bt_mesh_check_pending_request(MESH_OPCODE_DEV_COMP_GET,
1769                         dest, net_uuid.uuid)) {
1770                 BT_ERR("Device is buzy..");
1771                 return BLUETOOTH_ERROR_DEVICE_BUSY;
1772         }
1773
1774         /* Get Subnet index of the rmeote node for TX encryption */
1775         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid, dest);
1776         if (netkey_idx == MESH_NET_IDX_INVALID)
1777                 return BLUETOOTH_ERROR_INTERNAL;
1778
1779         data_len = _bt_mesh_util_opcode_set(MESH_OPCODE_DEV_COMP_GET, buffer);
1780
1781         /* By default, use page 0 */
1782         buffer[data_len++] = 0;
1783         ret = mesh_conf_send_message(&net_uuid, dest, true,
1784                         netkey_idx, buffer, data_len);
1785
1786         if (ret != OAL_STATUS_SUCCESS) {
1787                 BT_ERR("ret: %d", ret);
1788                 return BLUETOOTH_ERROR_INTERNAL;
1789         }
1790
1791         /* Queue the request with timeout */
1792         __bt_mesh_add_request(MESH_OPCODE_DEV_COMP_GET,
1793                         dest, net_uuid.uuid, NULL);
1794         return BLUETOOTH_ERROR_NONE;
1795 }
1796
1797 int _bt_mesh_model_configure_group_subscription(const char *app_cred,
1798                 const char *sender, bluetooth_mesh_model_configure_t *req)
1799 {
1800         int ret = OAL_STATUS_SUCCESS;
1801         uint16_t netkey_idx;
1802         oal_uuid_t net_uuid;
1803         uint16_t data_len;
1804         uint32_t opcode = 0;
1805         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
1806
1807         /* If Scanning is going on */
1808         if (_bt_mesh_is_provisioning() ||
1809                         _bt_mesh_is_scanning()) {
1810                 BT_ERR("Device is buzy..");
1811                 return BLUETOOTH_ERROR_DEVICE_BUSY;
1812         }
1813
1814         BT_INFO("Mesh: group Subscription Req: [%d]", req->op);
1815         if (req->op != BLUETOOTH_MESH_MODEL_SUB_DELETE_ALL) {
1816                 BT_INFO("Mesh: group Subscription Addr [0x%2.2x]", req->sub_addr);
1817
1818                 /* Subscriptio address sanity check */
1819                 if (!MESH_IS_GROUP(req->sub_addr) ||
1820                                 MESH_IS_VIRTUAL(req->sub_addr)) {
1821                         BT_ERR("Mesh: Bad subscription address [0x%2.2x\n]",
1822                                 req->sub_addr);
1823                         return BLUETOOTH_ERROR_INVALID_PARAM;
1824                 }
1825         } else
1826                 BT_INFO("Mesh: group Subscription Req: Delete All");
1827
1828         _bt_mesh_util_convert_string_to_hex(req->net_uuid,
1829                 strlen(req->net_uuid), net_uuid.uuid, 16);
1830         /* Get Subnet index of the remote node for TX encryption */
1831         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid,
1832                                 req->primary_unicast);
1833         if (netkey_idx == MESH_NET_IDX_INVALID)
1834                 return BLUETOOTH_ERROR_INTERNAL;
1835
1836
1837         if (req->op == BLUETOOTH_MESH_MODEL_SUB_ADD)
1838                 opcode = MESH_OPCODE_CONFIG_MODEL_SUB_ADD;
1839         else if (req->op == BLUETOOTH_MESH_MODEL_SUB_DELETE)
1840                 opcode = MESH_OPCODE_CONFIG_MODEL_SUB_DELETE;
1841         else if (req->op == BLUETOOTH_MESH_MODEL_SUB_DELETE_ALL)
1842                 opcode = MESH_OPCODE_CONFIG_MODEL_SUB_DELETE_ALL;
1843         else if (req->op == BLUETOOTH_MESH_MODEL_SUB_OVERWRITE)
1844                 opcode = MESH_OPCODE_CONFIG_MODEL_SUB_OVERWRITE;
1845
1846         /* Check pending request */
1847         if (_bt_mesh_check_pending_request(opcode,
1848                                 req->primary_unicast, net_uuid.uuid)) {
1849                 BT_ERR("Device is buzy..");
1850                 return BLUETOOTH_ERROR_DEVICE_BUSY;
1851         }
1852
1853         data_len = _bt_mesh_util_opcode_set(opcode, buffer);
1854
1855         BT_INFO("Mesh: Group Subscription Primary unicast [0x%2.2x]",
1856                         req->primary_unicast);
1857         /* Element Address */
1858         l_put_le16((req->primary_unicast + req->elem_index),
1859                         buffer + data_len);
1860         data_len += 2;
1861
1862         /* Subscription address */
1863         if (req->op != BLUETOOTH_MESH_MODEL_SUB_DELETE_ALL) {
1864                 l_put_le16(req->sub_addr, buffer + data_len);
1865                 data_len += 2;
1866         }
1867
1868         BT_INFO("Mesh: Group Subscription Model ID [0x%4.4x]", req->model);
1869         /* Insert Model ID */
1870          if (req->model >= 0xFFFF0000) {
1871                 /* 1st 2 octet Company ID is 0xFFFF means, it is BT SIG Model*/
1872                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
1873                 data_len += 2;
1874         } else {
1875                 /* Vendor Model, 1st 2 octetes: Company ID, next 2 octets: Vendor Model ID */
1876                 l_put_le16(req->model & 0xFFFF0000, buffer + data_len);
1877                 data_len += 2;
1878                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
1879                 data_len += 2;
1880         }
1881
1882         ret = mesh_conf_send_message(&net_uuid, req->primary_unicast, true,
1883                         netkey_idx, buffer, data_len);
1884
1885         if (ret != OAL_STATUS_SUCCESS) {
1886                 BT_ERR("ret: %d", ret);
1887                 return BLUETOOTH_ERROR_INTERNAL;
1888         }
1889
1890         BT_INFO("Mesh: Group Subscription Command sent successfully");
1891         /* Queue the request with timeout */
1892         __bt_mesh_add_request(opcode, req->primary_unicast,
1893                 net_uuid.uuid,
1894                         g_memdup(req, sizeof(bluetooth_mesh_model_configure_t)));
1895
1896         return BLUETOOTH_ERROR_NONE;
1897 }
1898
1899 int _bt_mesh_model_configure_virtual_group_subscription(
1900                 const char *app_cred, const char *sender,
1901                         bluetooth_mesh_model_configure_t *req)
1902 {
1903         int ret = OAL_STATUS_SUCCESS;
1904         uint16_t netkey_idx;
1905         oal_uuid_t net_uuid;
1906         uint16_t data_len;
1907         uint32_t opcode = 0;
1908         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
1909
1910         /* If Scanning is going on */
1911         if (_bt_mesh_is_provisioning() ||
1912                         _bt_mesh_is_scanning()) {
1913                 BT_ERR("Device is buzy..");
1914                 return BLUETOOTH_ERROR_DEVICE_BUSY;
1915         }
1916
1917         _bt_mesh_util_convert_string_to_hex(req->net_uuid,
1918                 strlen(req->net_uuid), net_uuid.uuid, 16);
1919
1920         BT_INFO("Mesh: Virtual Group Subscription Req: [%d] Group Addr [0x%2.2x]",
1921                         req->op, req->sub_addr);
1922
1923         if (req->op != BLUETOOTH_MESH_MODEL_SUB_DELETE_ALL) {
1924                 /* Subscription address sanity check */
1925                 if (MESH_IS_GROUP(req->sub_addr) ||
1926                                 !(MESH_IS_VIRTUAL(req->sub_addr))) {
1927                         BT_ERR("Mesh: Bad Virtual Group subscription address [0x%2.2x\n]",
1928                                 req->sub_addr);
1929                         return BLUETOOTH_ERROR_INVALID_PARAM;
1930                 }
1931         } else
1932                 BT_INFO("Mesh: Virtual Group Subscription Req: Delete All");
1933
1934         /* Get Subnet index of the remote node for TX encryption */
1935         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid,
1936                                 req->primary_unicast);
1937         if (netkey_idx == MESH_NET_IDX_INVALID)
1938                 return BLUETOOTH_ERROR_INTERNAL;
1939
1940         if (req->op == BLUETOOTH_MESH_MODEL_SUB_ADD)
1941                 opcode = MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_ADD;
1942         else if (req->op == BLUETOOTH_MESH_MODEL_SUB_DELETE)
1943                 opcode = MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_DELETE;
1944         else if (req->op == BLUETOOTH_MESH_MODEL_SUB_OVERWRITE)
1945                 opcode = MESH_OPCODE_CONFIG_MODEL_SUB_VIRT_OVERWRITE;
1946         else if (req->op == BLUETOOTH_MESH_MODEL_SUB_DELETE_ALL)
1947                 opcode = MESH_OPCODE_CONFIG_MODEL_SUB_DELETE_ALL;
1948
1949         /* Check pending request */
1950         if (_bt_mesh_check_pending_request(opcode,
1951                                 req->primary_unicast, net_uuid.uuid)) {
1952                 BT_ERR("Device is buzy..");
1953                 return BLUETOOTH_ERROR_DEVICE_BUSY;
1954         }
1955
1956         data_len = _bt_mesh_util_opcode_set(opcode, buffer);
1957
1958         /* Element Address */
1959         l_put_le16((req->primary_unicast + req->elem_index), buffer + data_len);
1960         data_len += 2;
1961
1962         /* Subscription address */
1963         if (req->op != BLUETOOTH_MESH_MODEL_SUB_DELETE_ALL) {
1964                 uint8_t label_uuid[16];
1965                 if (!_bt_mesh_network_get_label_uuid_from_sub_addr(
1966                         net_uuid.uuid, req->sub_addr, label_uuid)) {
1967                         BT_ERR("Mesh: Virtual Group Label UUID Not found");
1968                         return BLUETOOTH_ERROR_INVALID_PARAM;
1969                 }
1970                 memcpy(buffer + data_len, label_uuid, 16);
1971                 data_len += 16;
1972         }
1973
1974         BT_INFO("Mesh: Virtual Group Subscription Model ID [0x%4.4x]", req->model);
1975         /* Insert Model ID */
1976          if (req->model >= 0xFFFF0000) {
1977                 /* 1st 2 octet Company ID is 0xFFFF means, it is BT SIG Model*/
1978                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
1979                 data_len += 2;
1980         } else {
1981                 /* Vendor Model, 1st 2 octetes: Company ID, next 2 octets: Vendor Model ID */
1982                 l_put_le16(req->model & 0xFFFF0000, buffer + data_len);
1983                 data_len += 2;
1984                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
1985                 data_len += 2;
1986         }
1987
1988         ret = mesh_conf_send_message(&net_uuid,
1989                         req->primary_unicast, true,
1990                                 netkey_idx, buffer, data_len);
1991
1992         if (ret != OAL_STATUS_SUCCESS) {
1993                 BT_ERR("ret: %d", ret);
1994                 return BLUETOOTH_ERROR_INTERNAL;
1995         }
1996
1997         BT_INFO("Mesh: Virtual Group Subscription Command sent successfully");
1998         /* Queue the request with timeout */
1999         __bt_mesh_add_request(opcode, req->primary_unicast,
2000                 net_uuid.uuid,
2001                         g_memdup(req, sizeof(bluetooth_mesh_model_configure_t)));
2002
2003         return BLUETOOTH_ERROR_NONE;
2004 }
2005
2006 int _bt_mesh_model_get_publication(const char *app_cred, const char *sender,
2007                 bluetooth_mesh_model_configure_t *req)
2008 {
2009         int ret = OAL_STATUS_SUCCESS;
2010         uint16_t netkey_idx;
2011         oal_uuid_t net_uuid;
2012         uint16_t data_len;
2013         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
2014
2015         /* If Scanning is going on */
2016         if (_bt_mesh_is_provisioning() ||
2017                         _bt_mesh_is_scanning()) {
2018                 BT_ERR("Device is buzy..");
2019                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2020         }
2021
2022         _bt_mesh_util_convert_string_to_hex(req->net_uuid,
2023                 strlen(req->net_uuid), net_uuid.uuid, 16);
2024
2025         /* Check pending request */
2026         if (_bt_mesh_check_pending_request(MESH_OPCODE_CONFIG_MODEL_PUB_GET,
2027                                 req->primary_unicast, net_uuid.uuid)) {
2028                 BT_ERR("Device is buzy..");
2029                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2030         }
2031
2032         /* Get Subnet index of the remote node for TX encryption */
2033         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid, req->primary_unicast);
2034         if (netkey_idx == MESH_NET_IDX_INVALID)
2035                 return BLUETOOTH_ERROR_INTERNAL;
2036
2037         /* Set Opcode */
2038         data_len = _bt_mesh_util_opcode_set(MESH_OPCODE_CONFIG_MODEL_PUB_GET, buffer);
2039
2040         /* Element Address */
2041         l_put_le16((req->primary_unicast + req->elem_index), buffer + data_len);
2042         data_len += 2;
2043
2044         /* Insert Model ID */
2045         if (req->model >= 0xFFFF0000) {
2046                 /* 1st 2 octet Company ID is 0xFFFF means, it is BT SIG Model*/
2047                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
2048                 data_len += 2;
2049         } else {
2050                 /* Vendor Model, 1st 2 octetes: Company ID, next 2 octets: Vendor Model ID */
2051                 l_put_le16(req->model & 0xFFFF0000, buffer + data_len);
2052                 data_len += 2;
2053                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
2054                 data_len += 2;
2055         }
2056
2057         ret = mesh_conf_send_message(&net_uuid, req->primary_unicast, true, netkey_idx, buffer, data_len);
2058
2059         if (ret != OAL_STATUS_SUCCESS) {
2060                 BT_ERR("ret: %d", ret);
2061                 return BLUETOOTH_ERROR_INTERNAL;
2062         }
2063
2064         /* Queue the request with timeout */
2065         __bt_mesh_add_request(MESH_OPCODE_CONFIG_MODEL_PUB_GET, req->primary_unicast, net_uuid.uuid,
2066                         g_memdup(req, sizeof(bluetooth_mesh_model_configure_t)));
2067
2068         return BLUETOOTH_ERROR_NONE;
2069 }
2070
2071 int _bt_mesh_model_set_publication(const char *app_cred, const char *sender,
2072                 bluetooth_mesh_model_configure_t *req)
2073 {
2074         int ret = OAL_STATUS_SUCCESS;
2075         uint16_t netkey_idx;
2076         oal_uuid_t net_uuid;
2077         uint16_t data_len;
2078         uint32_t opcode = 0;
2079         uint8_t label_uuid[16];
2080         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
2081
2082         /* If Scanning is going on */
2083         if (_bt_mesh_is_provisioning() ||
2084                         _bt_mesh_is_scanning()) {
2085                 BT_ERR("Device is buzy..");
2086                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2087         }
2088
2089         _bt_mesh_util_convert_string_to_hex(req->net_uuid, strlen(req->net_uuid), net_uuid.uuid, 16);
2090
2091         if (req->pub_addr == MESH_ALL_NODES_ADDRESS)
2092                 BT_INFO("Mesh: Setting Publication to ALL Node Address");
2093
2094         if (!MESH_IS_GROUP(req->pub_addr) && !MESH_IS_VIRTUAL(req->pub_addr) &&
2095                         req->pub_addr != MESH_UNASSIGNED_ADDRESS) {
2096                 BT_ERR("Mesh: Bad Publication address %x\n", req->pub_addr);
2097                 return BLUETOOTH_ERROR_INVALID_PARAM;
2098         }
2099
2100         if (req->pub_addr != MESH_UNASSIGNED_ADDRESS) {
2101                 if (MESH_IS_VIRTUAL(req->pub_addr)) {
2102                         if (!_bt_mesh_network_get_label_uuid_from_sub_addr(
2103                                         net_uuid.uuid, req->pub_addr, label_uuid))
2104                                 return BLUETOOTH_ERROR_INVALID_PARAM;
2105                         opcode = MESH_OPCODE_CONFIG_MODEL_PUB_VIRT_SET;
2106
2107                 } else if (MESH_IS_GROUP(req->pub_addr))
2108                         opcode = MESH_OPCODE_CONFIG_MODEL_PUB_SET;
2109         }
2110
2111         /* Check pending request */
2112         if (_bt_mesh_check_pending_request(opcode,
2113                                 req->primary_unicast, net_uuid.uuid)) {
2114                 BT_ERR("Device is buzy..");
2115                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2116         }
2117
2118         /* Get Subnet index of the remote node for TX encryption */
2119         netkey_idx = _bt_mesh_node_get_subnet_idx(
2120                                 net_uuid.uuid, req->primary_unicast);
2121         if (netkey_idx == MESH_NET_IDX_INVALID)
2122                 return BLUETOOTH_ERROR_INTERNAL;
2123
2124         /* Set opcode */
2125         data_len = _bt_mesh_util_opcode_set(opcode, buffer);
2126
2127         /* Element Address */
2128         l_put_le16((req->primary_unicast + req->elem_index), buffer + data_len);
2129         data_len += 2;
2130
2131         /* Fill Publication Address */
2132         if (MESH_IS_VIRTUAL(req->pub_addr)) {
2133                 memcpy(buffer + data_len, label_uuid, 16);
2134                 data_len += 16;
2135         } else {
2136                 l_put_le16(req->pub_addr, buffer + data_len);
2137                 data_len += 2;
2138         }
2139
2140         /* AppKey index + credential (set to 0) */
2141         l_put_le16(req->appkey_idx, buffer + data_len);
2142         data_len += 2;
2143
2144         /* Fill TTL */
2145         buffer[data_len++] = req->ttl;
2146         /* Publish period  step count and step resolution */
2147         buffer[data_len++] = req->period;
2148         /* Publish retransmit count & interval steps */
2149         buffer[data_len++] = req->retransmit;
2150
2151         /* Insert Model ID */
2152         if (req->model >= 0xFFFF0000) {
2153                 /* 1st 2 octet Company ID is 0xFFFF means, it is BT SIG Model*/
2154                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
2155                 data_len += 2;
2156         } else {
2157                 /* Vendor Model, 1st 2 octetes: Company ID, next 2 octets: Vendor Model ID */
2158                 l_put_le16(req->model & 0xFFFF0000, buffer + data_len);
2159                 data_len += 2;
2160                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
2161                 data_len += 2;
2162         }
2163
2164         ret = mesh_conf_send_message(&net_uuid,
2165                         req->primary_unicast, true,
2166                                 netkey_idx, buffer, data_len);
2167
2168         if (ret != OAL_STATUS_SUCCESS) {
2169                 BT_ERR("ret: %d", ret);
2170                 return BLUETOOTH_ERROR_INTERNAL;
2171         }
2172
2173         /* Queue the request with timeout */
2174         __bt_mesh_add_request(opcode, req->primary_unicast, net_uuid.uuid,
2175                         g_memdup(req, sizeof(bluetooth_mesh_model_configure_t)));
2176
2177         return BLUETOOTH_ERROR_NONE;
2178 }
2179
2180 int _bt_mesh_node_model_get_subscription_list(const char *app_cred, const char *sender,
2181                 bluetooth_mesh_model_configure_t *req)
2182 {
2183         int ret = OAL_STATUS_SUCCESS;
2184         uint16_t netkey_idx;
2185         oal_uuid_t net_uuid;
2186         uint16_t data_len;
2187         uint32_t opcode = 0;
2188         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
2189
2190         /* If Scanning is going on */
2191         if (_bt_mesh_is_provisioning() ||
2192                         _bt_mesh_is_scanning()) {
2193                 BT_ERR("Device is buzy..");
2194                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2195         }
2196
2197         _bt_mesh_util_convert_string_to_hex(req->net_uuid, strlen(req->net_uuid), net_uuid.uuid, 16);
2198
2199         /* Insert Model ID */
2200         if (req->model >= 0xFFFF0000)
2201                 /* 1st 2 octet Company ID is 0xFFFF means, it is BT SIG Model*/
2202                 opcode = MESH_OPCODE_CONFIG_MODEL_SUB_GET;
2203         else
2204                 /* Vendor Model, 1st 2 octetes: Company ID, next 2 octets: Vendor Model ID */
2205                 opcode = MESH_OPCODE_CONFIG_VEND_MODEL_SUB_GET;
2206
2207         /* Check pending request */
2208         if (_bt_mesh_check_pending_request(opcode,
2209                                 req->primary_unicast, net_uuid.uuid)) {
2210                 BT_ERR("Device is buzy..");
2211                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2212         }
2213         /* Get Subnet index of the remote node for TX encryption */
2214         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid, req->primary_unicast);
2215         if (netkey_idx == MESH_NET_IDX_INVALID)
2216                 return BLUETOOTH_ERROR_INTERNAL;
2217
2218         data_len = _bt_mesh_util_opcode_set(opcode, buffer);
2219         /* Element Address */
2220         l_put_le16((req->primary_unicast + req->elem_index), buffer + data_len);
2221         data_len += 2;
2222
2223         /* Insert Model ID */
2224         if (opcode == MESH_OPCODE_CONFIG_MODEL_SUB_GET) {
2225                 BT_INFO("Mesh: Get Subscription List for BT SIG Model");
2226                 /* 1st 2 octet Company ID is 0xFFFF means, it is BT SIG Model*/
2227                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
2228                 data_len += 2;
2229         } else {
2230                 BT_INFO("Mesh: Get Subscription List for Vendor Model");
2231                 /* Vendor Model, 1st 2 octetes: Company ID, next 2 octets: Vendor Model ID */
2232                 l_put_le16(req->model & 0xFFFF0000, buffer + data_len);
2233                 data_len += 2;
2234                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
2235                 data_len += 2;
2236         }
2237
2238         ret = mesh_conf_send_message(&net_uuid,
2239                 req->primary_unicast, true, netkey_idx, buffer, data_len);
2240
2241         if (ret != OAL_STATUS_SUCCESS) {
2242                 BT_ERR("ret: %d", ret);
2243                 return BLUETOOTH_ERROR_INTERNAL;
2244         }
2245
2246         /* Queue the request with timeout */
2247         __bt_mesh_add_request(opcode, req->primary_unicast, net_uuid.uuid,
2248                         g_memdup(req, sizeof(bluetooth_mesh_model_configure_t)));
2249
2250         return BLUETOOTH_ERROR_NONE;
2251 }
2252
2253 int _bt_mesh_node_model_get_appkey_list(const char *app_cred, const char *sender,
2254                 bluetooth_mesh_model_configure_t *req)
2255 {
2256         int ret = OAL_STATUS_SUCCESS;
2257         uint16_t netkey_idx;
2258         oal_uuid_t net_uuid;
2259         uint16_t data_len;
2260         uint32_t opcode = 0;
2261         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
2262
2263         /* If Scanning is going on */
2264         if (_bt_mesh_is_provisioning() ||
2265                         _bt_mesh_is_scanning()) {
2266                 BT_ERR("Device is buzy..");
2267                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2268         }
2269
2270         _bt_mesh_util_convert_string_to_hex(req->net_uuid,
2271                 strlen(req->net_uuid), net_uuid.uuid, 16);
2272
2273         /* Insert Model ID */
2274         if (req->model >= 0xFFFF0000)
2275                 /* 1st 2 octet Company ID is 0xFFFF means, it is BT SIG Model*/
2276                 opcode = MESH_OPCODE_MODEL_APP_GET;
2277         else
2278                 /* Vendor Model, 1st 2 octetes: Company ID, next 2 octets: Vendor Model ID */
2279                 opcode = MESH_OPCODE_VENDOR_MODEL_APP_GET;
2280
2281         /* Check pending request */
2282         if (_bt_mesh_check_pending_request(opcode,
2283                                 req->primary_unicast, net_uuid.uuid)) {
2284                 BT_ERR("Device is buzy..");
2285                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2286         }
2287         /* Get Subnet index of the remote node for TX encryption */
2288         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid, req->primary_unicast);
2289         if (netkey_idx == MESH_NET_IDX_INVALID)
2290                 return BLUETOOTH_ERROR_INTERNAL;
2291
2292         data_len = _bt_mesh_util_opcode_set(opcode, buffer);
2293         /* Element Address */
2294         l_put_le16((req->primary_unicast + req->elem_index), buffer + data_len);
2295         data_len += 2;
2296
2297
2298         /* Insert Model ID */
2299         if (opcode == MESH_OPCODE_MODEL_APP_GET) {
2300                 /* 1st 2 octet Company ID is 0xFFFF means, it is BT SIG Model*/
2301                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
2302                 data_len += 2;
2303         } else {
2304                 /* Vendor Model, 1st 2 octetes: Company ID, next 2 octets: Vendor Model ID */
2305                 l_put_le16(req->model & 0xFFFF0000, buffer + data_len);
2306                 data_len += 2;
2307                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
2308                 data_len += 2;
2309         }
2310
2311         ret = mesh_conf_send_message(&net_uuid, req->primary_unicast, true, netkey_idx, buffer, data_len);
2312
2313         if (ret != OAL_STATUS_SUCCESS) {
2314                 BT_ERR("ret: %d", ret);
2315                 return BLUETOOTH_ERROR_INTERNAL;
2316         }
2317
2318         /* Queue the request with timeout */
2319         __bt_mesh_add_request(opcode, req->primary_unicast, net_uuid.uuid,
2320                         g_memdup(req, sizeof(bluetooth_mesh_model_configure_t)));
2321
2322         return BLUETOOTH_ERROR_NONE;
2323 }
2324
2325 int _bt_mesh_network_reset_node(const char *app_cred, const char *sender,
2326                 bluetooth_mesh_node_info_t *node)
2327 {
2328         int ret = OAL_STATUS_SUCCESS;
2329         uint16_t netkey_idx;
2330         oal_uuid_t net_uuid;
2331         uint16_t data_len;
2332         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
2333
2334         /* If Scanning is going on */
2335         if (_bt_mesh_is_provisioning() ||
2336                         _bt_mesh_is_scanning()) {
2337                 BT_ERR("Device is buzy..");
2338                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2339         }
2340
2341         _bt_mesh_util_convert_string_to_hex(node->net_uuid,
2342                         strlen(node->net_uuid), net_uuid.uuid, 16);
2343
2344         /* Check pending request */
2345         if (_bt_mesh_check_pending_request(MESH_OPCODE_NODE_RESET,
2346                                 node->primary_unicast, net_uuid.uuid)) {
2347                 BT_ERR("Device is buzy..");
2348                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2349         }
2350         BT_INFO("Mesh: Reset a remote Node [0x%2.2x] Elem Cnt [0x%2.2x]",
2351                         node->primary_unicast, node->num_elements);
2352         /* Get Subnet index of the remote node for TX encryption */
2353         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid, node->primary_unicast);
2354         if (netkey_idx == MESH_NET_IDX_INVALID)
2355                 return BLUETOOTH_ERROR_INTERNAL;
2356
2357         data_len = _bt_mesh_util_opcode_set(MESH_OPCODE_NODE_RESET, buffer);
2358
2359         /* Send Node Reset command 5 times to ensure reliability */
2360         for (int i = 0; i < 5; i++)
2361                 ret = mesh_conf_send_message(&net_uuid, node->primary_unicast,
2362                                 true, netkey_idx, buffer, data_len);
2363
2364         if (ret != OAL_STATUS_SUCCESS) {
2365                 BT_ERR("Mesh: Node Reset Failed!: %d", ret);
2366                 return BLUETOOTH_ERROR_INTERNAL;
2367         }
2368
2369         BT_INFO("Mesh: Node reset Done, Send Delete req: Unicast[0x%2.2x]",
2370                         node->primary_unicast);
2371
2372         ret = mesh_delete_remote_node(&net_uuid, node->primary_unicast,
2373                         node->num_elements);
2374         if (ret != OAL_STATUS_SUCCESS) {
2375                 BT_ERR("Mesh: Remote Node Deletion Failed!: %d", ret);
2376                 return BLUETOOTH_ERROR_INTERNAL;
2377         }
2378
2379         return _bt_mesh_network_remove_node_configuration(node);
2380 }
2381
2382 int _bt_mesh_node_model_appkey_execute(const char *app_cred, const char *sender,
2383                 bluetooth_mesh_model_configure_t *req)
2384 {
2385         int ret = OAL_STATUS_SUCCESS;
2386         uint16_t netkey_idx;
2387         oal_uuid_t net_uuid;
2388         uint16_t data_len;
2389         uint32_t opcode = 0;
2390         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
2391
2392         /* If Scanning is going on */
2393         if (_bt_mesh_is_provisioning() ||
2394                         _bt_mesh_is_scanning()) {
2395                 BT_ERR("Device is buzy..");
2396                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2397         }
2398
2399         _bt_mesh_util_convert_string_to_hex(req->net_uuid, strlen(req->net_uuid), net_uuid.uuid, 16);
2400
2401         /* Check pending request */
2402         if (_bt_mesh_check_pending_request(req->is_bind ? MESH_OPCODE_MODEL_APP_BIND : MESH_OPCODE_MODEL_APP_UNBIND,
2403                                 req->primary_unicast, net_uuid.uuid)) {
2404                 BT_ERR("Device is buzy..");
2405                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2406         }
2407         /* Get Subnet index of the remote node for TX encryption */
2408         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid, req->primary_unicast);
2409         if (netkey_idx == MESH_NET_IDX_INVALID)
2410                 return BLUETOOTH_ERROR_INTERNAL;
2411
2412         if (req->is_bind)
2413                 opcode = MESH_OPCODE_MODEL_APP_BIND;
2414         else
2415                 opcode = MESH_OPCODE_MODEL_APP_UNBIND;
2416
2417         data_len = _bt_mesh_util_opcode_set(opcode, buffer);
2418         /* Element Address */
2419         l_put_le16((req->primary_unicast + req->elem_index), buffer + data_len);
2420         data_len += 2;
2421
2422         /* AppKey Index  */
2423         l_put_le16(req->appkey_idx, buffer + data_len);
2424         data_len += 2;
2425
2426         /* Insert Model ID */
2427         if (req->model >= 0xFFFF0000) {
2428                 /* 1st 2 octet Company ID is 0xFFFF means, it is BT SIG Model*/
2429                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
2430                 data_len += 2;
2431         } else {
2432                 /* Vendor Model, 1st 2 octetes: Company ID, next 2 octets: Vendor Model ID */
2433                 l_put_le16(req->model & 0xFFFF0000, buffer + data_len);
2434                 data_len += 2;
2435                 l_put_le16(req->model & 0x0000FFFF, buffer + data_len);
2436                 data_len += 2;
2437         }
2438
2439         ret = mesh_conf_send_message(&net_uuid, req->primary_unicast, true, netkey_idx, buffer, data_len);
2440
2441         if (ret != OAL_STATUS_SUCCESS) {
2442                 BT_ERR("ret: %d", ret);
2443                 return BLUETOOTH_ERROR_INTERNAL;
2444         }
2445
2446         /* Queue the request with timeout */
2447         __bt_mesh_add_request(opcode, req->primary_unicast, net_uuid.uuid,
2448                         g_memdup(req, sizeof(bluetooth_mesh_model_configure_t)));
2449
2450         return BLUETOOTH_ERROR_NONE;
2451 }
2452
2453 int _bt_mesh_ttl_execute_remote_node(const char *app_cred, const char *sender,
2454                 bluetooth_mesh_node_ttl_info_t *req)
2455 {
2456         int ret = OAL_STATUS_SUCCESS;
2457         uint16_t netkey_idx;
2458         uint16_t data_len;
2459         oal_uuid_t net_uuid;
2460         uint32_t opcode = 0;
2461         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
2462
2463         /* If Scanning is going on */
2464         if (_bt_mesh_is_provisioning() ||
2465                         _bt_mesh_is_scanning()) {
2466                 BT_ERR("Device is buzy..");
2467                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2468         }
2469
2470         _bt_mesh_util_convert_string_to_hex(req->net_uuid, strlen(req->net_uuid), net_uuid.uuid, 16);
2471
2472         /* Check pending request */
2473         if (_bt_mesh_check_pending_request(req->is_set ? MESH_OPCODE_CONFIG_DEFAULT_TTL_SET : MESH_OPCODE_CONFIG_DEFAULT_TTL_GET,
2474                                 req->unicast, net_uuid.uuid)) {
2475                 BT_ERR("Device is buzy..");
2476                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2477         }
2478
2479         /* Get Subnet index of the rmeote node for TX encryption */
2480         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid, req->unicast);
2481         if (netkey_idx == MESH_NET_IDX_INVALID)
2482                 return BLUETOOTH_ERROR_INTERNAL;
2483
2484         if (req->is_set) {
2485                 opcode = MESH_OPCODE_CONFIG_DEFAULT_TTL_SET;
2486                 data_len = _bt_mesh_util_opcode_set(MESH_OPCODE_CONFIG_DEFAULT_TTL_SET, buffer);
2487                 buffer[data_len++] = req->ttl;
2488         } else {
2489                 opcode = MESH_OPCODE_CONFIG_DEFAULT_TTL_GET;
2490                 data_len = _bt_mesh_util_opcode_set(MESH_OPCODE_CONFIG_DEFAULT_TTL_GET, buffer);
2491         }
2492
2493         ret = mesh_conf_send_message(&net_uuid, req->unicast, true, netkey_idx, buffer, data_len);
2494
2495         if (ret != OAL_STATUS_SUCCESS) {
2496                 BT_ERR("ret: %d", ret);
2497                 return BLUETOOTH_ERROR_INTERNAL;
2498         }
2499
2500         /* Queue the request with timeout */
2501         __bt_mesh_add_request(opcode, req->unicast, net_uuid.uuid,
2502                         g_memdup(req, sizeof(bluetooth_mesh_node_ttl_info_t)));
2503         return BLUETOOTH_ERROR_NONE;
2504 }
2505
2506 static bool __bt_mesh_check_pending_key_cmd(uint16_t dest, bool is_netkey,
2507                 bluetooth_mesh_node_key_conf_e op,  uint8_t net_uuid[], uint32_t *opcode)
2508 {
2509         const struct mesh_config_cmd *cmd;
2510
2511         if (is_netkey) {
2512                 switch (op) {
2513                 case BLUETOOTH_MESH_NODE_KEY_ADD:
2514                         cmd = __mesh_get_command(MESH_OPCODE_NETKEY_ADD);
2515                         if (!cmd)
2516                                 return false;
2517                         if (__bt_mesh_get_request_by_response(dest, net_uuid, cmd->response)) {
2518                                 BT_ERR("Mesh:Another Key Configuration command is pending\n");
2519                                 return true;
2520                         }
2521                         *opcode = MESH_OPCODE_NETKEY_ADD;
2522                         return false;
2523                 case BLUETOOTH_MESH_NODE_KEY_DELETE:
2524                         cmd = __mesh_get_command(MESH_OPCODE_NETKEY_DELETE);
2525                         if (!cmd)
2526                                 return false;
2527                         if (__bt_mesh_get_request_by_response(dest, net_uuid, cmd->response)) {
2528                                 BT_ERR("Mesh:Another Key Configuration command is pending\n");
2529                                 return true;
2530                         }
2531                         *opcode = MESH_OPCODE_NETKEY_DELETE;
2532                         return false;
2533                 case BLUETOOTH_MESH_NODE_KEY_UPDATE:
2534                         cmd = __mesh_get_command(MESH_OPCODE_NETKEY_UPDATE);
2535                         if (!cmd)
2536                                 return false;
2537                         if (__bt_mesh_get_request_by_response(dest, net_uuid, cmd->response)) {
2538                                 BT_ERR("Mesh:Another Key Configuration command is pending\n");
2539                                 return true;
2540                         }
2541                         *opcode = MESH_OPCODE_NETKEY_UPDATE;
2542                         return false;
2543                 }
2544         } else {
2545                 switch (op) {
2546                 case BLUETOOTH_MESH_NODE_KEY_ADD:
2547                         cmd = __mesh_get_command(MESH_OPCODE_APPKEY_ADD);
2548                         if (!cmd)
2549                                 return false;
2550                         if (__bt_mesh_get_request_by_response(dest, net_uuid, cmd->response)) {
2551                                 BT_ERR("Mesh:Another Key Configuration command is pending\n");
2552                                 return true;
2553                         }
2554                         *opcode = MESH_OPCODE_APPKEY_ADD;
2555                         return false;
2556                 case BLUETOOTH_MESH_NODE_KEY_DELETE:
2557                         cmd = __mesh_get_command(MESH_OPCODE_APPKEY_DELETE);
2558                         if (!cmd)
2559                                 return false;
2560                         if (__bt_mesh_get_request_by_response(dest, net_uuid, cmd->response)) {
2561                                 BT_ERR("Mesh:Another Key Configuration command is pending\n");
2562                                 return true;
2563                         }
2564                         *opcode = MESH_OPCODE_APPKEY_DELETE;
2565                         return false;
2566                 case BLUETOOTH_MESH_NODE_KEY_UPDATE:
2567                         cmd = __mesh_get_command(MESH_OPCODE_APPKEY_UPDATE);
2568                         if (!cmd)
2569                                 return false;
2570                         if (__bt_mesh_get_request_by_response(dest, net_uuid, cmd->response)) {
2571                                 BT_ERR("Mesh:Another Key Configuration command is pending\n");
2572                                 return true;
2573                         }
2574                         *opcode = MESH_OPCODE_APPKEY_UPDATE;
2575                         return false;
2576                 }
2577         }
2578         return false;
2579 }
2580
2581 int _bt_mesh_node_configure_key(const char *app_cred, const char *sender,
2582                 bluetooth_mesh_key_configure_t *req)
2583 {
2584         int ret = OAL_STATUS_SUCCESS;
2585         uint16_t netkey_idx;
2586         uint16_t bound_netkey_idx = 0x0000;
2587         oal_uuid_t net_uuid;
2588         uint32_t opcode = 0;
2589         bool update;
2590         uint16_t data_len;
2591         uint8_t buffer[MESH_CONFIG_BUFFER_MAX_LEN];
2592
2593         /* If Scanning is going on */
2594         if (_bt_mesh_is_provisioning() ||
2595                         _bt_mesh_is_scanning()) {
2596                 BT_ERR("Device is buzy..");
2597                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2598         }
2599
2600         _bt_mesh_util_convert_string_to_hex(req->net_uuid, strlen(req->net_uuid), net_uuid.uuid, 16);
2601
2602         if (req->is_netkey && !_bt_mesh_keys_subnet_exists(net_uuid.uuid, req->netkey_idx)) {
2603                 BT_ERR("Local Subnet not found..");
2604                 return BLUETOOTH_ERROR_INVALID_PARAM;
2605         }
2606
2607         /* For Appkey Configuration, check for available bound netkey */
2608         if (!req->is_netkey) {
2609                 bound_netkey_idx = _bt_mesh_keys_get_bound_key(net_uuid.uuid, req->appkey_idx);
2610                 if (bound_netkey_idx == MESH_NET_IDX_INVALID) {
2611                         BT_ERR("Local AppKey not found..");
2612                         return BLUETOOTH_ERROR_INVALID_PARAM;
2613                 }
2614         }
2615
2616         /* Check pending request */
2617         if (__bt_mesh_check_pending_key_cmd(req->primary_unicast,
2618                                 req->is_netkey, req->op, net_uuid.uuid, &opcode)) {
2619                 BT_ERR("Device is buzy..");
2620                 return BLUETOOTH_ERROR_DEVICE_BUSY;
2621         }
2622
2623         /* Get Subnet index of the rmeote node for TX encryption */
2624         netkey_idx = _bt_mesh_node_get_subnet_idx(net_uuid.uuid, req->primary_unicast);
2625         if (netkey_idx == MESH_NET_IDX_INVALID)
2626                 return BLUETOOTH_ERROR_INTERNAL;
2627
2628         /* Handle Key (App/Net) Delete Commands: Configuration Message  */
2629         if (opcode == MESH_OPCODE_NETKEY_DELETE || opcode == MESH_OPCODE_APPKEY_DELETE) {
2630                 data_len = _bt_mesh_util_opcode_set(opcode, buffer);
2631                 if (req->is_netkey) {
2632                         l_put_le16(req->netkey_idx, buffer + data_len);
2633                         data_len += 2;
2634                 } else {
2635                         buffer[data_len] = bound_netkey_idx;
2636                         buffer[data_len + 1] = ((bound_netkey_idx >> 8) & 0xf) | ((req->appkey_idx << 4) & 0xf0);
2637                         buffer[data_len + 2] = req->appkey_idx >> 4;
2638
2639                         data_len += 3;
2640                 }
2641                 ret = mesh_conf_send_message(&net_uuid, req->primary_unicast, true, netkey_idx, buffer, data_len);
2642         } else {
2643                 /* Handle Key (App/Net) Update & Add Commands: Key Config message  */
2644                 update = (opcode == MESH_OPCODE_NETKEY_UPDATE || opcode == MESH_OPCODE_APPKEY_UPDATE);
2645                 ret = mesh_conf_send_key_message(&net_uuid, req->primary_unicast, req->is_netkey,
2646                                 update, req->is_netkey ? req->netkey_idx : req->appkey_idx, netkey_idx);
2647         }
2648         if (ret != OAL_STATUS_SUCCESS) {
2649                 BT_ERR("ret: %d", ret);
2650                 return BLUETOOTH_ERROR_INTERNAL;
2651         }
2652
2653         /* Queue the request with timeout */
2654         __bt_mesh_add_request(opcode, req->primary_unicast,  net_uuid.uuid,
2655                 g_memdup(req, sizeof(bluetooth_mesh_key_configure_t)));
2656         return BLUETOOTH_ERROR_NONE;
2657 }