Implement ZCL Scene cluster
[platform/core/connectivity/zigbee-manager.git] / zigbee-daemon / zigbee-interface / src / zigbee_service_dbus_interface_zcl_scene.c
1 /*
2  * Copyright (c) 2016 Samsung Electronics Co., Ltd. All rights reserved.
3  *
4  * Contact: Suresh Kumar N (suresh.n@samsung.com)
5  *
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  * http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  */
18
19 #include "zigbee_service_interface_common.h"
20
21 #include <zblib_driver_zcl_scene.h>
22
23 static void *_service_interface_ref_zigbee_zcl_scene(
24         ZigBeeServiceInterface *service_interface)
25 {
26         ZigbeeObjectSkeleton *zigbee_object = NULL;
27         ZigbeeCustomData_t *custom_data = NULL;
28         ZigbeeZcl_scene *scene_object = NULL;
29
30         custom_data = (ZigbeeCustomData_t *)zblib_service_interface_ref_user_data(service_interface);
31         if (NULL == custom_data) {
32                 Z_LOGE("D-BUS service interface custom_data is NULL!");
33                 return NULL;
34         }
35
36         /* Get zigbee object */
37         zigbee_object = g_hash_table_lookup(custom_data->objects, ZIGBEE_SERVICE_PATH);
38         if (NULL == zigbee_object) {
39                 Z_LOGW("Cannot find ZigBee D-BUS interface object!", zigbee_object);
40                 return NULL;
41         }
42
43         scene_object = zigbee_object_get_zcl_scene(ZIGBEE_OBJECT(zigbee_object));
44         return scene_object;
45 }
46
47 static void on_zcl_scene_add_scene_resp(ZigBeeServiceInterface *service_interface,
48         guint request_id, gpointer resp_data, guint resp_data_len, gpointer resp_cb_data)
49 {
50         ZigbeeServiceInterfaceRespCbData_t *cb_data =
51                 (ZigbeeServiceInterfaceRespCbData_t *)resp_cb_data;
52
53         ZigbeeZcl_scene *scene_object = NULL;
54         GDBusMethodInvocation *invocation = NULL;
55
56         ZigbeeGeneralResp_t *payload = (ZigbeeGeneralResp_t *)resp_data;
57
58         NOT_USED(service_interface);
59         NOT_USED(request_id);
60
61         if (NULL == resp_data || 0 == resp_data_len) {
62                 Z_LOGE("resp_data=%p or resp_data_len=%d is null", resp_data, resp_data_len);
63                 g_free(cb_data);
64                 return;
65         }
66
67         scene_object = zigbee_service_dbus_interface_ref_interface_object(cb_data);
68         zblib_check_null_free_and_ret("scene_object", scene_object, cb_data);
69
70         invocation = zigbee_service_dbus_interface_ref_invocation(cb_data);
71         zblib_check_null_free_and_ret("invocation", invocation, cb_data);
72
73         zigbee_zcl_scene_complete_add_scene(scene_object, invocation, payload->result);
74
75         g_free(cb_data);
76 }
77
78 static gboolean on_zcl_scene_add_scene(ZigbeeZcl_scene *zcl_scene_object,
79         GDBusMethodInvocation *invocation,
80         gshort node_id,
81         gchar dest_ep,
82         gshort group_id,
83         gchar scene_id,
84         gshort transition_time,
85         gshort ext_length,
86         GVariant *scene_name,
87         GVariant *ext_field_set,
88         gpointer user_data)
89 {
90         ZigBeeServiceInterface *service_interface = (ZigBeeServiceInterface *)user_data;
91         ZigbeeZclSceneAddScene_t req;
92         ZigbeeServiceInterfaceRespCbData_t *resp_cb_data = NULL;
93
94         GVariantIter *iter = NULL;
95         gint i = 0;
96
97         gboolean ret;
98
99         memset(&req, 0x0, sizeof(ZigbeeZclSceneAddScene_t));
100
101         /* Update request structure */
102         req.node_id = node_id;
103         req.dest_ep = dest_ep;
104         req.group_id = group_id;
105         req.scene_id = scene_id;
106         req.transition_time = transition_time;
107         g_variant_get(scene_name, "a(y)", &iter);
108         while (g_variant_iter_loop(iter, "(y)", req.scene_name[i])) {
109                 i++;
110                 if (i >= ZIGBEE_ZCL_GROUP_NAME_MAX_LEN + 1)
111                         break;
112         }
113
114         i = 0;
115         req.ext_field_set_len = ext_length;
116         req.ext_field_set = g_malloc0(ext_length);
117         g_variant_get(ext_field_set, "a(y)", &iter);
118         while (g_variant_iter_loop(iter, "(y)", req.ext_field_set[i])) {
119                 i++;
120                 if (i >= ext_length)
121                         break;
122         }
123
124         /* Allocate response callback data */
125         resp_cb_data =
126                 zigbee_service_dbus_interface_create_resp_cb_data(zcl_scene_object,
127                         invocation, NULL, 0);
128         if (NULL == resp_cb_data) {
129                 Z_LOGE("zigbee_service_dbus_interface_create_resp_cb_data failed!");
130
131                 /* Send failure response */
132                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
133
134                 return TRUE;
135         }
136
137         /* Dispatch request */
138         ret = zigbee_service_dbus_interface_dispatch_request(service_interface,
139                 ZBLIB_DRIVER_TYPE_ZCL_SCENE,
140                 ZBLIB_ZCL_SCENE_OPS_ADD_SCENE,
141                 &req, sizeof(req),
142                 on_zcl_scene_add_scene_resp, resp_cb_data);
143
144         /* Free resource */
145         g_free(req.ext_field_set);
146
147         if (FALSE == ret) {
148                 Z_LOGE("zigbee_service_dbus_interface_dispatch_request failed!");
149
150                 /* Free response callback data */
151                 zigbee_service_dbus_interface_destroy_resp_cb_data(resp_cb_data);
152
153                 /* Send failure response */
154                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
155
156                 return TRUE;
157         }
158
159         return TRUE;
160 }
161
162 static void on_zcl_scene_view_scene_resp(ZigBeeServiceInterface *service_interface,
163         guint request_id, gpointer resp_data, guint resp_data_len, gpointer resp_cb_data)
164 {
165         ZigbeeServiceInterfaceRespCbData_t *cb_data =
166                 (ZigbeeServiceInterfaceRespCbData_t *)resp_cb_data;
167
168         ZigbeeZcl_scene *scene_object = NULL;
169         GDBusMethodInvocation *invocation = NULL;
170
171         ZigbeeGeneralResp_t *payload = (ZigbeeGeneralResp_t *)resp_data;
172
173         NOT_USED(service_interface);
174         NOT_USED(request_id);
175
176         if (NULL == resp_data || 0 == resp_data_len) {
177                 Z_LOGE("resp_data=%p or resp_data_len=%d is null", resp_data, resp_data_len);
178                 g_free(cb_data);
179                 return;
180         }
181
182         scene_object = zigbee_service_dbus_interface_ref_interface_object(cb_data);
183         zblib_check_null_free_and_ret("scene_object", scene_object, cb_data);
184
185         invocation = zigbee_service_dbus_interface_ref_invocation(cb_data);
186         zblib_check_null_free_and_ret("invocation", invocation, cb_data);
187
188         zigbee_zcl_scene_complete_view_scene(scene_object, invocation, payload->result);
189
190         g_free(cb_data);
191 }
192
193 static gboolean on_zcl_scene_view_scene(ZigbeeZcl_scene *zcl_scene_object,
194         GDBusMethodInvocation *invocation,
195         gshort node_id,
196         gchar dest_ep,
197         gshort group_id,
198         gchar scene_id,
199         gpointer user_data)
200 {
201         ZigBeeServiceInterface *service_interface = (ZigBeeServiceInterface *)user_data;
202         ZigbeeZclSceneViewScene_t req;
203         ZigbeeServiceInterfaceRespCbData_t *resp_cb_data = NULL;
204
205         gboolean ret;
206
207         memset(&req, 0x0, sizeof(ZigbeeZclSceneViewScene_t));
208
209         /* Update request structure */
210         req.node_id = node_id;
211         req.dest_ep = dest_ep;
212         req.group_id = group_id;
213         req.scene_id = scene_id;
214
215         /* Allocate response callback data */
216         resp_cb_data =
217                 zigbee_service_dbus_interface_create_resp_cb_data(zcl_scene_object,
218                         invocation, NULL, 0);
219         if (NULL == resp_cb_data) {
220                 Z_LOGE("zigbee_service_dbus_interface_create_resp_cb_data failed!");
221
222                 /* Send failure response */
223                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
224
225                 return TRUE;
226         }
227
228         /* Dispatch request */
229         ret = zigbee_service_dbus_interface_dispatch_request(service_interface,
230                 ZBLIB_DRIVER_TYPE_ZCL_SCENE,
231                 ZBLIB_ZCL_SCENE_OPS_VIEW_SCENE,
232                 &req, sizeof(req),
233                 on_zcl_scene_view_scene_resp, resp_cb_data);
234         if (FALSE == ret) {
235                 Z_LOGE("zigbee_service_dbus_interface_dispatch_request failed!");
236
237                 /* Free response callback data */
238                 zigbee_service_dbus_interface_destroy_resp_cb_data(resp_cb_data);
239
240                 /* Send failure response */
241                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
242
243                 return TRUE;
244         }
245
246         return TRUE;
247 }
248
249 static void on_zcl_scene_remove_scene_resp(ZigBeeServiceInterface *service_interface,
250         guint request_id, gpointer resp_data, guint resp_data_len, gpointer resp_cb_data)
251 {
252         ZigbeeServiceInterfaceRespCbData_t *cb_data =
253                 (ZigbeeServiceInterfaceRespCbData_t *)resp_cb_data;
254
255         ZigbeeZcl_scene *scene_object = NULL;
256         GDBusMethodInvocation *invocation = NULL;
257
258         ZigbeeGeneralResp_t *payload = (ZigbeeGeneralResp_t *)resp_data;
259
260         NOT_USED(service_interface);
261         NOT_USED(request_id);
262
263         if (NULL == resp_data || 0 == resp_data_len) {
264                 Z_LOGE("resp_data=%p or resp_data_len=%d is null", resp_data, resp_data_len);
265                 g_free(cb_data);
266                 return;
267         }
268
269         scene_object = zigbee_service_dbus_interface_ref_interface_object(cb_data);
270         zblib_check_null_free_and_ret("scene_object", scene_object, cb_data);
271
272         invocation = zigbee_service_dbus_interface_ref_invocation(cb_data);
273         zblib_check_null_free_and_ret("invocation", invocation, cb_data);
274
275         zigbee_zcl_scene_complete_remove_scene(scene_object, invocation, payload->result);
276
277         g_free(cb_data);
278 }
279
280 static gboolean on_zcl_scene_remove_scene(ZigbeeZcl_scene *zcl_scene_object,
281         GDBusMethodInvocation *invocation,
282         gshort node_id,
283         gchar dest_ep,
284         gshort group_id,
285         gchar scene_id,
286         gpointer user_data)
287 {
288         ZigBeeServiceInterface *service_interface = (ZigBeeServiceInterface *)user_data;
289         ZigbeeZclSceneRemoveScene_t req;
290         ZigbeeServiceInterfaceRespCbData_t *resp_cb_data = NULL;
291
292         gboolean ret;
293
294         memset(&req, 0x0, sizeof(ZigbeeZclSceneRemoveScene_t));
295
296         /* Update request structure */
297         req.node_id = node_id;
298         req.dest_ep = dest_ep;
299         req.group_id = group_id;
300         req.scene_id = scene_id;
301
302         /* Allocate response callback data */
303         resp_cb_data =
304                 zigbee_service_dbus_interface_create_resp_cb_data(zcl_scene_object,
305                         invocation, NULL, 0);
306         if (NULL == resp_cb_data) {
307                 Z_LOGE("zigbee_service_dbus_interface_create_resp_cb_data failed!");
308
309                 /* Send failure response */
310                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
311
312                 return TRUE;
313         }
314
315         /* Dispatch request */
316         ret = zigbee_service_dbus_interface_dispatch_request(service_interface,
317                 ZBLIB_DRIVER_TYPE_ZCL_SCENE,
318                 ZBLIB_ZCL_SCENE_OPS_REMOVE_SCENE,
319                 &req, sizeof(req),
320                 on_zcl_scene_remove_scene_resp, resp_cb_data);
321         if (FALSE == ret) {
322                 Z_LOGE("zigbee_service_dbus_interface_dispatch_request failed!");
323
324                 /* Free response callback data */
325                 zigbee_service_dbus_interface_destroy_resp_cb_data(resp_cb_data);
326
327                 /* Send failure response */
328                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
329
330                 return TRUE;
331         }
332
333         return TRUE;
334 }
335
336 static void on_zcl_scene_store_scene_resp(ZigBeeServiceInterface *service_interface,
337         guint request_id, gpointer resp_data, guint resp_data_len, gpointer resp_cb_data)
338 {
339         ZigbeeServiceInterfaceRespCbData_t *cb_data =
340                 (ZigbeeServiceInterfaceRespCbData_t *)resp_cb_data;
341
342         ZigbeeZcl_scene *scene_object = NULL;
343         GDBusMethodInvocation *invocation = NULL;
344
345         ZigbeeGeneralResp_t *payload = (ZigbeeGeneralResp_t *)resp_data;
346
347         NOT_USED(service_interface);
348         NOT_USED(request_id);
349
350         if (NULL == resp_data || 0 == resp_data_len) {
351                 Z_LOGE("resp_data=%p or resp_data_len=%d is null", resp_data, resp_data_len);
352                 g_free(cb_data);
353                 return;
354         }
355
356         scene_object = zigbee_service_dbus_interface_ref_interface_object(cb_data);
357         zblib_check_null_free_and_ret("scene_object", scene_object, cb_data);
358
359         invocation = zigbee_service_dbus_interface_ref_invocation(cb_data);
360         zblib_check_null_free_and_ret("invocation", invocation, cb_data);
361
362         zigbee_zcl_scene_complete_store_scene(scene_object, invocation, payload->result);
363
364         g_free(cb_data);
365 }
366
367 static gboolean on_zcl_scene_store_scene(ZigbeeZcl_scene *zcl_scene_object,
368         GDBusMethodInvocation *invocation,
369         gshort node_id,
370         gchar dest_ep,
371         gshort group_id,
372         gchar scene_id,
373         gpointer user_data)
374 {
375         ZigBeeServiceInterface *service_interface = (ZigBeeServiceInterface *)user_data;
376         ZigbeeZclSceneStoreScene_t req;
377         ZigbeeServiceInterfaceRespCbData_t *resp_cb_data = NULL;
378
379         gboolean ret;
380
381         memset(&req, 0x0, sizeof(ZigbeeZclSceneStoreScene_t));
382
383         /* Update request structure */
384         req.node_id = node_id;
385         req.dest_ep = dest_ep;
386         req.group_id = group_id;
387         req.scene_id = scene_id;
388
389         /* Allocate response callback data */
390         resp_cb_data =
391                 zigbee_service_dbus_interface_create_resp_cb_data(zcl_scene_object,
392                         invocation, NULL, 0);
393         if (NULL == resp_cb_data) {
394                 Z_LOGE("zigbee_service_dbus_interface_create_resp_cb_data failed!");
395
396                 /* Send failure response */
397                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
398
399                 return TRUE;
400         }
401
402         /* Dispatch request */
403         ret = zigbee_service_dbus_interface_dispatch_request(service_interface,
404                 ZBLIB_DRIVER_TYPE_ZCL_SCENE,
405                 ZBLIB_ZCL_SCENE_OPS_STORE_SCENE,
406                 &req, sizeof(req),
407                 on_zcl_scene_store_scene_resp, resp_cb_data);
408         if (FALSE == ret) {
409                 Z_LOGE("zigbee_service_dbus_interface_dispatch_request failed!");
410
411                 /* Free response callback data */
412                 zigbee_service_dbus_interface_destroy_resp_cb_data(resp_cb_data);
413
414                 /* Send failure response */
415                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
416
417                 return TRUE;
418         }
419
420         return TRUE;
421 }
422
423 static void on_zcl_scene_recall_scene_resp(ZigBeeServiceInterface *service_interface,
424         guint request_id, gpointer resp_data, guint resp_data_len, gpointer resp_cb_data)
425 {
426         ZigbeeServiceInterfaceRespCbData_t *cb_data =
427                 (ZigbeeServiceInterfaceRespCbData_t *)resp_cb_data;
428
429         ZigbeeZcl_scene *scene_object = NULL;
430         GDBusMethodInvocation *invocation = NULL;
431
432         ZigbeeGeneralResp_t *payload = (ZigbeeGeneralResp_t *)resp_data;
433
434         NOT_USED(service_interface);
435         NOT_USED(request_id);
436
437         if (NULL == resp_data || 0 == resp_data_len) {
438                 Z_LOGE("resp_data=%p or resp_data_len=%d is null", resp_data, resp_data_len);
439                 g_free(cb_data);
440                 return;
441         }
442
443         scene_object = zigbee_service_dbus_interface_ref_interface_object(cb_data);
444         zblib_check_null_free_and_ret("scene_object", scene_object, cb_data);
445
446         invocation = zigbee_service_dbus_interface_ref_invocation(cb_data);
447         zblib_check_null_free_and_ret("invocation", invocation, cb_data);
448
449         zigbee_zcl_scene_complete_recall_scene(scene_object, invocation, payload->result);
450
451         g_free(cb_data);
452 }
453
454 static gboolean on_zcl_scene_recall_scene(ZigbeeZcl_scene *zcl_scene_object,
455         GDBusMethodInvocation *invocation,
456         gshort node_id,
457         gchar dest_ep,
458         gshort group_id,
459         gchar scene_id,
460         gpointer user_data)
461 {
462         ZigBeeServiceInterface *service_interface = (ZigBeeServiceInterface *)user_data;
463         ZigbeeZclSceneRecallScene_t req;
464         ZigbeeServiceInterfaceRespCbData_t *resp_cb_data = NULL;
465
466         gboolean ret;
467
468         memset(&req, 0x0, sizeof(ZigbeeZclSceneRecallScene_t));
469
470         /* Update request structure */
471         req.node_id = node_id;
472         req.dest_ep = dest_ep;
473         req.group_id = group_id;
474         req.scene_id = scene_id;
475
476         /* Allocate response callback data */
477         resp_cb_data =
478                 zigbee_service_dbus_interface_create_resp_cb_data(zcl_scene_object,
479                         invocation, NULL, 0);
480         if (NULL == resp_cb_data) {
481                 Z_LOGE("zigbee_service_dbus_interface_create_resp_cb_data failed!");
482
483                 /* Send failure response */
484                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
485
486                 return TRUE;
487         }
488
489         /* Dispatch request */
490         ret = zigbee_service_dbus_interface_dispatch_request(service_interface,
491                 ZBLIB_DRIVER_TYPE_ZCL_SCENE,
492                 ZBLIB_ZCL_SCENE_OPS_RECALL_SCENE,
493                 &req, sizeof(req),
494                 on_zcl_scene_recall_scene_resp, resp_cb_data);
495         if (FALSE == ret) {
496                 Z_LOGE("zigbee_service_dbus_interface_dispatch_request failed!");
497
498                 /* Free response callback data */
499                 zigbee_service_dbus_interface_destroy_resp_cb_data(resp_cb_data);
500
501                 /* Send failure response */
502                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
503
504                 return TRUE;
505         }
506
507         return TRUE;
508 }
509
510 static void on_zcl_scene_remove_all_scene_resp(ZigBeeServiceInterface *service_interface,
511         guint request_id, gpointer resp_data, guint resp_data_len, gpointer resp_cb_data)
512 {
513         ZigbeeServiceInterfaceRespCbData_t *cb_data =
514                 (ZigbeeServiceInterfaceRespCbData_t *)resp_cb_data;
515
516         ZigbeeZcl_scene *scene_object = NULL;
517         GDBusMethodInvocation *invocation = NULL;
518
519         ZigbeeGeneralResp_t *payload = (ZigbeeGeneralResp_t *)resp_data;
520
521         NOT_USED(service_interface);
522         NOT_USED(request_id);
523
524         if (NULL == resp_data || 0 == resp_data_len) {
525                 Z_LOGE("resp_data=%p or resp_data_len=%d is null", resp_data, resp_data_len);
526                 g_free(cb_data);
527                 return;
528         }
529
530         scene_object = zigbee_service_dbus_interface_ref_interface_object(cb_data);
531         zblib_check_null_free_and_ret("scene_object", scene_object, cb_data);
532
533         invocation = zigbee_service_dbus_interface_ref_invocation(cb_data);
534         zblib_check_null_free_and_ret("invocation", invocation, cb_data);
535
536         zigbee_zcl_scene_complete_remove_all_scene(scene_object, invocation, payload->result);
537
538         g_free(cb_data);
539 }
540
541 static gboolean on_zcl_scene_remove_all_scene(ZigbeeZcl_scene *zcl_scene_object,
542         GDBusMethodInvocation *invocation,
543         gshort node_id,
544         gchar dest_ep,
545         gshort group_id,
546         gpointer user_data)
547 {
548         ZigBeeServiceInterface *service_interface = (ZigBeeServiceInterface *)user_data;
549         ZigbeeZclSceneRemoveAllScene_t req;
550         ZigbeeServiceInterfaceRespCbData_t *resp_cb_data = NULL;
551
552         gboolean ret;
553
554         memset(&req, 0x0, sizeof(ZigbeeZclSceneRemoveAllScene_t));
555
556         /* Update request structure */
557         req.node_id = node_id;
558         req.dest_ep = dest_ep;
559         req.group_id = group_id;
560
561         /* Allocate response callback data */
562         resp_cb_data =
563                 zigbee_service_dbus_interface_create_resp_cb_data(zcl_scene_object,
564                         invocation, NULL, 0);
565         if (NULL == resp_cb_data) {
566                 Z_LOGE("zigbee_service_dbus_interface_create_resp_cb_data failed!");
567
568                 /* Send failure response */
569                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
570
571                 return TRUE;
572         }
573
574         /* Dispatch request */
575         ret = zigbee_service_dbus_interface_dispatch_request(service_interface,
576                 ZBLIB_DRIVER_TYPE_ZCL_SCENE,
577                 ZBLIB_ZCL_SCENE_OPS_REMOVE_ALL_SCENE,
578                 &req, sizeof(req),
579                 on_zcl_scene_remove_all_scene_resp, resp_cb_data);
580         if (FALSE == ret) {
581                 Z_LOGE("zigbee_service_dbus_interface_dispatch_request failed!");
582
583                 /* Free response callback data */
584                 zigbee_service_dbus_interface_destroy_resp_cb_data(resp_cb_data);
585
586                 /* Send failure response */
587                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
588
589                 return TRUE;
590         }
591
592         return TRUE;
593 }
594
595 static void on_zcl_scene_get_scene_membership_resp(ZigBeeServiceInterface *service_interface,
596         guint request_id, gpointer resp_data, guint resp_data_len, gpointer resp_cb_data)
597 {
598         ZigbeeServiceInterfaceRespCbData_t *cb_data =
599                 (ZigbeeServiceInterfaceRespCbData_t *)resp_cb_data;
600
601         ZigbeeZcl_scene *scene_object = NULL;
602         GDBusMethodInvocation *invocation = NULL;
603
604         ZigbeeGeneralResp_t *payload = (ZigbeeGeneralResp_t *)resp_data;
605
606         NOT_USED(service_interface);
607         NOT_USED(request_id);
608
609         if (NULL == resp_data || 0 == resp_data_len) {
610                 Z_LOGE("resp_data=%p or resp_data_len=%d is null", resp_data, resp_data_len);
611                 g_free(cb_data);
612                 return;
613         }
614
615         scene_object = zigbee_service_dbus_interface_ref_interface_object(cb_data);
616         zblib_check_null_free_and_ret("scene_object", scene_object, cb_data);
617
618         invocation = zigbee_service_dbus_interface_ref_invocation(cb_data);
619         zblib_check_null_free_and_ret("invocation", invocation, cb_data);
620
621         zigbee_zcl_scene_complete_get_scene_membership(scene_object, invocation, payload->result);
622
623         g_free(cb_data);
624 }
625
626 static gboolean on_zcl_scene_get_scene_membership(ZigbeeZcl_scene *zcl_scene_object,
627         GDBusMethodInvocation *invocation,
628         gshort node_id,
629         gchar dest_ep,
630         gshort group_id,
631         gpointer user_data)
632 {
633         ZigBeeServiceInterface *service_interface = (ZigBeeServiceInterface *)user_data;
634         ZigbeeZclSceneGetSceneMembership_t req;
635         ZigbeeServiceInterfaceRespCbData_t *resp_cb_data = NULL;
636
637         gboolean ret;
638
639         memset(&req, 0x0, sizeof(ZigbeeZclSceneGetSceneMembership_t));
640
641         /* Update request structure */
642         req.node_id = node_id;
643         req.dest_ep = dest_ep;
644         req.group_id = group_id;
645
646         /* Allocate response callback data */
647         resp_cb_data =
648                 zigbee_service_dbus_interface_create_resp_cb_data(zcl_scene_object,
649                         invocation, NULL, 0);
650         if (NULL == resp_cb_data) {
651                 Z_LOGE("zigbee_service_dbus_interface_create_resp_cb_data failed!");
652
653                 /* Send failure response */
654                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
655
656                 return TRUE;
657         }
658
659         /* Dispatch request */
660         ret = zigbee_service_dbus_interface_dispatch_request(service_interface,
661                 ZBLIB_DRIVER_TYPE_ZCL_SCENE,
662                 ZBLIB_ZCL_SCENE_OPS_GET_SCENE_MEMBERSHIP,
663                 &req, sizeof(req),
664                 on_zcl_scene_get_scene_membership_resp, resp_cb_data);
665         if (FALSE == ret) {
666                 Z_LOGE("zigbee_service_dbus_interface_dispatch_request failed!");
667
668                 /* Free response callback data */
669                 zigbee_service_dbus_interface_destroy_resp_cb_data(resp_cb_data);
670
671                 /* Send failure response */
672                 ZIGBEE_DBUS_FAIL_RESPONSE(invocation, ZIGBEE_DBUS_DEFAULT_REQ_FAILED_MSG);
673
674                 return TRUE;
675         }
676
677         return TRUE;
678 }
679
680 void zigbee_service_dbus_interface_zcl_scene_notification(ZigBeeServiceInterface *service_interface,
681         guint noti_id, gpointer noti_data, guint noti_data_len, gpointer noti_cb_data)
682 {
683         ZigbeeZcl_scene *scene_object;
684
685         zblib_check_null_ret("service_interface", service_interface);
686
687         if (NULL == noti_data || 0 == noti_data_len) {
688                 Z_LOGE("noti_data=%p or noti_data_len=%d is null", noti_data, noti_data_len);
689                 return;
690         }
691
692         scene_object = _service_interface_ref_zigbee_zcl_scene(service_interface);
693         zblib_check_null_ret("scene_object", scene_object);
694
695         NOT_USED(noti_cb_data);
696
697         switch(noti_id) {
698         case ZBLIB_ZCL_SCENE_NOTI_ADD_SCENE: {
699                 ZigbeeZclSceneAddSceneResp_t *rsp = (ZigbeeZclSceneAddSceneResp_t*)noti_data;
700
701                 Z_LOGD("'add_scene_rsp' from : [0x%X]", rsp->node_id);
702
703                 zigbee_zcl_scene_emit_add_scene_rsp(scene_object, rsp->node_id, rsp->src_ep,
704                         rsp->status, rsp->group_id, rsp->scene_id);
705         }
706         break;
707         case ZBLIB_ZCL_SCENE_NOTI_VIEW_SCENE: {
708                 int i;
709
710                 GVariant* scene_name = NULL;
711                 GVariantBuilder *attr_builder = NULL;
712                 GVariant* ext_field_set = NULL;
713                 GVariantBuilder *attr_builder1 = NULL;
714
715                 ZigbeeZclSceneViewSceneResp_t *rsp = (ZigbeeZclSceneViewSceneResp_t*)noti_data;
716
717                 Z_LOGD("'view_scene_rsp' from : [0x%X]", rsp->node_id);
718
719                 attr_builder = g_variant_builder_new(G_VARIANT_TYPE("a(y)"));
720                 for (i = 0; rsp->scene_name[i] && i < ZIGBEE_ZCL_SCENE_NAME_MAX_LEN; i++)
721                         g_variant_builder_add(attr_builder, "(y)", rsp->scene_name[i]);
722                 scene_name = g_variant_builder_end(attr_builder);
723                 g_variant_builder_unref(attr_builder);
724
725
726                 attr_builder1 = g_variant_builder_new(G_VARIANT_TYPE("a(y)"));
727                 for (i = 0; i < rsp->ext_field_set_len; i++)
728                         g_variant_builder_add(attr_builder1, "(y)", rsp->ext_field_set[i]);
729                 ext_field_set = g_variant_builder_end(attr_builder1);
730                 g_variant_builder_unref(attr_builder1);
731
732                 zigbee_zcl_scene_emit_view_scene_rsp(scene_object, rsp->node_id, rsp->src_ep,
733                         rsp->status, rsp->group_id, rsp->scene_id, rsp->transition_time,
734                         scene_name, rsp->ext_field_set_len, ext_field_set);
735         }
736         break;
737         case ZBLIB_ZCL_SCENE_NOTI_REMOVE_SCENE: {
738                 ZigbeeZclSceneRemoveSceneResp_t *rsp = (ZigbeeZclSceneRemoveSceneResp_t*)noti_data;
739
740                 Z_LOGD("'remove_scene_rsp' from : [0x%X]", rsp->node_id);
741
742                 zigbee_zcl_scene_emit_remove_scene_rsp(scene_object, rsp->node_id, rsp->src_ep,
743                         rsp->status, rsp->group_id, rsp->scene_id);
744         }
745         break;
746         case ZBLIB_ZCL_SCENE_NOTI_REMOVE_ALL_SCENE: {
747                 ZigbeeZclSceneRemoveAllSceneResp_t *rsp =
748                         (ZigbeeZclSceneRemoveAllSceneResp_t*)noti_data;
749
750                 Z_LOGD("'remove_all_scene_rsp' from : [0x%X]", rsp->node_id);
751
752                 zigbee_zcl_scene_emit_remove_all_scene_rsp(scene_object, rsp->node_id, rsp->src_ep,
753                         rsp->status, rsp->group_id);
754         }
755         break;
756         case ZBLIB_ZCL_SCENE_NOTI_STORE_SCENE: {
757                 ZigbeeZclSceneStoreSceneResp_t *rsp =
758                         (ZigbeeZclSceneStoreSceneResp_t*)noti_data;
759
760                 Z_LOGD("'store_scene_rsp' from : [0x%X]", rsp->node_id);
761
762                 zigbee_zcl_scene_emit_store_scene_rsp(scene_object, rsp->node_id, rsp->src_ep,
763                         rsp->status, rsp->group_id, rsp->scene_id);
764         }
765         break;
766         case ZBLIB_ZCL_SCENE_NOTI_GET_SCENE_MEMBERSHIP: {
767                 int i;
768                 GVariant* scene_list = NULL;
769                 GVariantBuilder *attr_builder = NULL;
770
771                 ZigbeeZclSceneGetSceneMembershipResp_t *rsp =
772                         (ZigbeeZclSceneGetSceneMembershipResp_t*)noti_data;
773
774                 Z_LOGD("'get_scene_rsp' from : [0x%X]", rsp->node_id);
775
776                 attr_builder = g_variant_builder_new(G_VARIANT_TYPE("a(y)"));
777                 for (i = 0; i < rsp->scene_count; i++)
778                         g_variant_builder_add(attr_builder, "(y)", rsp->scene_list[i]);
779                 scene_list = g_variant_builder_end(attr_builder);
780                 g_variant_builder_unref(attr_builder);
781
782                 zigbee_zcl_scene_emit_get_scene_membership_rsp(scene_object, rsp->node_id, rsp->src_ep,
783                         rsp->status, rsp->capacity, rsp->group_id, rsp->scene_count, scene_list);
784         }
785         break;
786         default:
787                 Z_LOGE("Unexpected notification [%x]", noti_id);
788         break;
789         }
790
791         /* ZigbeeZcl_scene should be dereferenced */
792         g_object_unref(scene_object);
793 }
794
795 gboolean zigbee_service_dbus_interface_zcl_scene_init(ZigBeeServiceInterface *service_interface,
796         ZigbeeObjectSkeleton *zigbee_object)
797 {
798         ZigbeeZcl_scene *zcl_scene_object;
799
800         if (NULL == service_interface) {
801                 Z_LOGE("service_interface is NULL");
802                 return FALSE;
803         }
804
805         zcl_scene_object = zigbee_zcl_scene_skeleton_new();
806         zigbee_object_skeleton_set_zcl_scene(zigbee_object, zcl_scene_object);
807         g_object_unref(zcl_scene_object);
808
809         Z_LOGI("zcl_scene_object: [%p]", zcl_scene_object);
810
811         /*
812          * Register signal handlers for 'zcl_scene' interface
813          */
814         g_signal_connect(zcl_scene_object,
815                 "handle-add-scene",
816                 G_CALLBACK(on_zcl_scene_add_scene), service_interface);
817
818         g_signal_connect(zcl_scene_object,
819                 "handle-view-scene",
820                 G_CALLBACK(on_zcl_scene_view_scene), service_interface);
821
822         g_signal_connect(zcl_scene_object,
823                 "handle-remove-scene",
824                 G_CALLBACK(on_zcl_scene_remove_scene), service_interface);
825
826         g_signal_connect(zcl_scene_object,
827                 "handle-store-scene",
828                 G_CALLBACK(on_zcl_scene_store_scene), service_interface);
829
830         g_signal_connect(zcl_scene_object,
831                 "handle-recall-scene",
832                 G_CALLBACK(on_zcl_scene_recall_scene), service_interface);
833
834         g_signal_connect(zcl_scene_object,
835                 "handle-remove-all-scene",
836                 G_CALLBACK(on_zcl_scene_remove_all_scene), service_interface);
837
838         g_signal_connect(zcl_scene_object,
839                 "handle-get-scene-membership",
840                 G_CALLBACK(on_zcl_scene_get_scene_membership), service_interface);
841
842         return TRUE;
843 }