2 * Copyright (c) 2016 Samsung Electronics Co., Ltd.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
17 /*****************************************************************************
19 *****************************************************************************/
26 /*****************************************************************************
28 *****************************************************************************/
34 /*****************************************************************************
35 * Application Service Platform Daemon headers
36 *****************************************************************************/
37 #include "asp-manager.h"
38 #include "asp-manager-util.h"
39 #include "asp-service.h"
40 #include "asp-session.h"
42 #include "asp-tech-p2p.h"
44 /*****************************************************************************
46 *****************************************************************************/
48 #define ASP_TECH_P2P_ROLE_NEW 1
49 #define ASP_TECH_P2P_ROLE_GC 2
50 #define ASP_TECH_P2P_ROLE_GO 4
52 #define WFD_MANAGER_SERVICE "net.wifidirect"
53 #define WFD_MANAGER_PATH "/net/wifidirect"
54 #define WFD_MANAGER_MANAGE_INTERFACE WFD_MANAGER_SERVICE
55 #define WFD_MANAGER_CONFIG_INTERFACE WFD_MANAGER_SERVICE ".config"
56 #define WFD_MANAGER_GROUP_INTERFACE WFD_MANAGER_SERVICE ".group"
57 #define WFD_MANAGER_ASP_INTERFACE WFD_MANAGER_SERVICE ".asp"
59 #define DBUS_REPLY_TIMEOUT_SYNC 10 * 1000
60 #define DBUS_OBJECT_PATH_MAX 150
62 #define WFD_MANAGER_QUARK (g_quark_from_string("wifi-direct-manager"))
64 #define asp_tech_p2p_dbus_method_call_sync(interface_name, method, params, error) \
65 __asp_tech_p2p_dbus_method_call_sync_debug(interface_name, method, params, error, __func__)
67 #define DBUS_DEBUG_VARIANT(parameters) \
69 gchar *parameters_debug_str = NULL;\
71 parameters_debug_str = g_variant_print(parameters, TRUE);\
72 ASP_LOGD("signal params [%s]", parameters_debug_str ? parameters_debug_str : "NULL");\
73 g_free(parameters_debug_str);\
76 asp_tech_ops_s asp_tech_p2p_ops;
78 void asp_tech_p2p_process_activation(GDBusConnection *connection,
79 const gchar *object_path, GVariant *parameters);
81 void asp_tech_p2p_process_deactivation(GDBusConnection *connection,
82 const gchar *object_path, GVariant *parameters);
84 void asp_tech_p2p_process_search_result(GDBusConnection *connection,
85 const gchar *object_path, GVariant *parameters);
87 void asp_tech_p2p_process_session_request(GDBusConnection *connection,
88 const gchar *object_path, GVariant *parameters);
90 void asp_tech_p2p_process_session_config_request(GDBusConnection *connection,
91 const gchar *object_path, GVariant *parameters);
93 void asp_tech_p2p_process_connect_status(GDBusConnection *connection,
94 const gchar *object_path, GVariant *parameters);
96 void asp_tech_p2p_process_session_peer_ip(GDBusConnection *connection,
97 const gchar *object_path, GVariant *parameters);
99 /*****************************************************************************
101 *****************************************************************************/
103 static GDBusConnection *g_wfd_gdbus_conn;
104 static guint g_wfd_signal_id;
107 const gchar *interface;
109 void (*function) (GDBusConnection *connection,
110 const gchar *object_path,
111 GVariant *parameters);
112 } asp_tech_p2p_dbus_signal_map[] = {
114 WFD_MANAGER_MANAGE_INTERFACE,
116 asp_tech_p2p_process_activation
119 WFD_MANAGER_MANAGE_INTERFACE,
121 asp_tech_p2p_process_deactivation
124 WFD_MANAGER_ASP_INTERFACE,
126 asp_tech_p2p_process_search_result
129 WFD_MANAGER_ASP_INTERFACE,
131 asp_tech_p2p_process_session_request
134 WFD_MANAGER_ASP_INTERFACE,
135 "SessionConfigRequest",
136 asp_tech_p2p_process_session_config_request
139 WFD_MANAGER_ASP_INTERFACE,
141 asp_tech_p2p_process_connect_status
144 WFD_MANAGER_ASP_INTERFACE,
145 "SessionPeerIPAssigned",
146 asp_tech_p2p_process_session_peer_ip
155 /*****************************************************************************
156 * Local Functions Definition
157 *****************************************************************************/
159 static gint32 __net_wifidirect_gerror_to_enum(GError* error)
163 ASP_LOGI("GError is NULL!!");
167 ASP_LOGE("wifi_direct_dbus_method_call_sync() failed. error [%d: %s]",
168 error->code, error->message);
172 if (NULL == strstr(error->message, "net.wifidirect.Error")) {
173 if (NULL != strstr(error->message, ".AccessDenied")) {
174 ASP_LOGE("Client doesn't have wifidirect privilege");
177 ASP_LOGE("DBus failure");
181 if (NULL != strstr(error->message, "InvalidParameter"))
183 else if (NULL != strstr(error->message, "NotPermitted"))
185 else if (NULL != strstr(error->message, "OperationFailed"))
187 else if (NULL != strstr(error->message, "TooManyClient"))
197 static void __asp_tech_p2p_dbus_signal_cb(GDBusConnection *connection,
198 const gchar *sender, const gchar *object_path,
199 const gchar *interface, const gchar *signal,
200 GVariant *parameters, gpointer user_data)
204 ASP_LOGD("Signal Name [%s]", signal);
205 DBUS_DEBUG_VARIANT(parameters);
207 for (i = 0; asp_tech_p2p_dbus_signal_map[i].member != NULL; i++) {
208 if (!g_strcmp0(signal, asp_tech_p2p_dbus_signal_map[i].member) &&
209 !g_strcmp0(interface, asp_tech_p2p_dbus_signal_map[i].interface) &&
210 asp_tech_p2p_dbus_signal_map[i].function != NULL) {
211 asp_tech_p2p_dbus_signal_map[i].function(connection, object_path, parameters);
217 static GVariant *__g_hash_table_to_g_variant(GHashTable *hash)
219 GVariantBuilder builder;
221 g_variant_builder_init(&builder, G_VARIANT_TYPE("a{sv}"));
226 g_hash_table_iter_init(&iter, hash);
227 while (g_hash_table_iter_next(&iter, &key, &value)) {
228 ASP_LOGD("%s %s", key, value);
229 g_variant_builder_add(&builder, "{sv}", key, g_variant_new_string(value));
232 return g_variant_builder_end(&builder);
235 static GVariant *__g_hash_keys_to_g_variant(GHashTable *hash)
237 GVariantBuilder builder;
239 g_variant_builder_init(&builder, G_VARIANT_TYPE("as"));
244 g_hash_table_iter_init(&iter, hash);
245 while (g_hash_table_iter_next(&iter, &key, &value))
246 g_variant_builder_add(&builder, "s", key);
248 return g_variant_builder_end(&builder);
251 GVariant *__asp_tech_p2p_dbus_method_call_sync_debug(const gchar* interface_name,
255 const gchar *calling_func)
257 GVariant *reply = NULL;
259 if (g_wfd_gdbus_conn == NULL) {
260 ASP_LOGE("GDBusconnection is NULL");
264 ASP_LOGD("[%s][%s.%s]", calling_func, interface_name, method);
265 DBUS_DEBUG_VARIANT(params);
267 reply = g_dbus_connection_call_sync(g_wfd_gdbus_conn,
268 WFD_MANAGER_SERVICE, /* bus name */
269 WFD_MANAGER_PATH, /* object path */
270 interface_name, /* interface name */
271 method, /* method name */
272 params, /* GVariant *params */
273 NULL, /* reply_type */
274 G_DBUS_CALL_FLAGS_NONE, /* flags */
275 DBUS_REPLY_TIMEOUT_SYNC, /* timeout */
276 NULL, /* cancellable */
278 DBUS_DEBUG_VARIANT(reply);
282 void asp_tech_p2p_process_activation(GDBusConnection *connection,
283 const gchar *object_path, GVariant *parameters)
285 __ASP_LOG_FUNC_ENTER__;
287 ASP_LOGE("Wi-Fi Direct activated");
289 __ASP_LOG_FUNC_EXIT__;
293 void asp_tech_p2p_process_deactivation(GDBusConnection *connection,
294 const gchar *object_path, GVariant *parameters)
296 __ASP_LOG_FUNC_ENTER__;
298 ASP_LOGE("Wi-Fi Direct deactivated");
300 __ASP_LOG_FUNC_EXIT__;
304 static void __service_info_to_g_hash(const gchar *service_info,
305 GHashTable *service_info_map)
307 const gchar *key = NULL;
308 const gchar *value = NULL;
310 gsize key_length = 0;
311 gsize value_length = 0;
312 gsize info_length = 0;
314 info_length = strlen(service_info);
316 while (service_info[pos] != '\0' && pos < info_length) {
317 key = &service_info[pos];
318 while (service_info[pos] != '=' && pos < info_length) {
323 if (pos >= info_length - 1) {
324 g_hash_table_replace(service_info_map, g_strndup(key, key_length),
330 value = &service_info[pos];
331 while (service_info[pos] != ',' && pos < info_length) {
336 g_hash_table_replace(service_info_map, g_strndup(key, key_length),
337 g_strndup(value, value_length));
338 ASP_LOGD("Insert (%s, %s) to hash.", key, value);
340 if (service_info[pos] == ',' && pos == info_length)
346 void asp_tech_p2p_process_search_result(GDBusConnection *connection,
347 const gchar *object_path, GVariant *parameters)
349 __ASP_LOG_FUNC_ENTER__;
351 GVariantIter *iter = NULL;
352 GVariant *var = NULL;
353 GHashTable *service_info_map = NULL;
354 asp_event_data event;
355 const gchar *service_mac = NULL;
356 const gchar *key = NULL;
357 const gchar *str = NULL;
358 long long unsigned search_id = 0;
359 gchar *device_name = NULL;
360 guint32 advertisement_id = 0;
361 guint32 config_method = 0;
362 gchar *instance_name = NULL;
366 __ASP_LOG_FUNC_EXIT__;
370 g_variant_get(parameters, "(a{sv})", &iter);
371 while (g_variant_iter_loop(iter, "{sv}", &key, &var)) {
372 if (!g_strcmp0(key, "search_id")) {
373 g_variant_get(var, "t", &search_id);
374 } else if (!g_strcmp0(key, "service_mac")) {
375 g_variant_get(var, "&s", &service_mac);
376 } else if (!g_strcmp0(key, "device_name")) {
377 g_variant_get(var, "&s", &str);
378 device_name = g_strndup(str, ASP_SERVICE_DEVICE_NAME_LEN);
379 } else if (!g_strcmp0(key, "advertisement_id")) {
380 g_variant_get(var, "u", &advertisement_id);
381 } else if (!g_strcmp0(key, "config_method")) {
382 g_variant_get(var, "u", &config_method);
383 } else if (!g_strcmp0(key, "instance_name")) {
384 g_variant_get(var, "&s", &str);
385 instance_name = g_strdup(str);
386 } else if (!g_strcmp0(key, "status")) {
387 g_variant_get(var, "y", &status);
388 } else if (!g_strcmp0(key, "service_info")) {
389 g_variant_get(var, "&s", &str);
390 service_info_map = g_hash_table_new_full(g_str_hash,
391 g_str_equal, g_free, g_free);
392 __service_info_to_g_hash(str, service_info_map);
398 memset(&event, 0x0, sizeof(asp_event_data));
399 event.search_result.tech = ASP_TECH_P2P;
400 event.search_result.search_id = search_id;
401 event.search_result.advertisement_id = advertisement_id;
402 event.search_result.service_status = status;
404 memcpy(event.search_result.service_mac, service_mac, MACSTR_LEN + 1);
405 event.search_result.device_name = device_name;
406 event.search_result.instance_name = instance_name;
407 event.search_result.service_info = service_info_map;
408 asp_manager_event(NULL, ASP_EVENT_SEARCH_RESULT, &event);
411 g_free(instance_name);
412 g_hash_table_unref(service_info_map);
413 g_variant_iter_free(iter);
415 __ASP_LOG_FUNC_EXIT__;
419 void asp_tech_p2p_process_session_request(GDBusConnection *connection,
420 const gchar *object_path, GVariant *parameters)
422 __ASP_LOG_FUNC_ENTER__;
424 GVariantIter *iter = NULL;
425 GVariant *var = NULL;
426 const gchar *key = NULL;
427 const gchar *str = NULL;
428 guint8 session_mac[MAC_LEN] = {0,};
429 guint32 session_id = 0;
431 gchar *device_name = NULL;
432 size_t name_length = 0;
433 guint8 *session_info = NULL;
434 size_t info_length = 0;
435 gboolean get_pin = FALSE;
439 __ASP_LOG_FUNC_EXIT__;
443 g_variant_get(parameters, "(a{sv})", &iter);
444 while (g_variant_iter_loop(iter, "{sv}", &key, &var)) {
445 if (!g_strcmp0(key, "adv_id")) {
446 g_variant_get(var, "u", &adv_id);
447 } else if (!g_strcmp0(key, "session_mac")) {
448 if (asp_dbus_unpack_ay(session_mac, var, MAC_LEN) < 0) {
450 g_free(session_info);
451 g_variant_iter_free(iter);
454 } else if (!g_strcmp0(key, "session_id")) {
455 g_variant_get(var, "u", &session_id);
456 } else if (!g_strcmp0(key, "device_name")) {
457 g_variant_get(var, "&s", &str);
458 device_name = g_strndup(str, ASP_SERVICE_DEVICE_NAME_LEN);
459 name_length = strlen(str);
460 } else if (!g_strcmp0(key, "get_pin")) {
461 g_variant_get(var, "b", &get_pin);
462 } else if (!g_strcmp0(key, "pin")) {
463 g_variant_get(var, "&s", &str);
464 pin = (guint32)atoi(str);
465 } else if (!g_strcmp0(key, "session_info")) {
467 g_variant_get(var, "&s", &str);
470 info_length = strlen(str);
471 g_free(session_info);
472 session_info = g_try_malloc0(info_length + 1);
473 memcpy(session_info, str, info_length);
479 if (asp_tech_p2p_ops.session_request_cb) {
480 asp_tech_p2p_ops.session_request_cb(0, session_mac, session_id,
481 adv_id, device_name, name_length,
482 session_info, info_length, get_pin, pin,
483 asp_tech_p2p_ops.session_request_cb_user_data);
486 g_variant_iter_free(iter);
488 g_free(session_info);
490 __ASP_LOG_FUNC_EXIT__;
494 void asp_tech_p2p_process_session_config_request(GDBusConnection *connection,
495 const gchar *object_path, GVariant *parameters)
497 __ASP_LOG_FUNC_ENTER__;
499 GVariantIter *iter = NULL;
500 GVariant *var = NULL;
501 const gchar *key = NULL;
502 const gchar *str = NULL;
503 const guint8 session_mac[MAC_LEN] = {0,};
504 guint32 session_id = 0;
505 gboolean get_pin = FALSE;
509 __ASP_LOG_FUNC_EXIT__;
513 g_variant_get(parameters, "(a{sv})", &iter);
514 while (g_variant_iter_loop(iter, "{sv}", &key, &var)) {
515 if (!g_strcmp0(key, "session_id")) {
516 g_variant_get(var, "u", &session_id);
517 } else if (!g_strcmp0(key, "get_pin")) {
518 g_variant_get(var, "b", &get_pin);
519 } else if (!g_strcmp0(key, "pin")) {
520 g_variant_get(var, "&s", &str);
521 pin = (guint32)atoi(str);
527 if (asp_tech_p2p_ops.session_config_request_cb) {
528 asp_tech_p2p_ops.session_config_request_cb(0,
529 session_mac, session_id, get_pin, pin,
530 asp_tech_p2p_ops.session_config_request_cb_user_data);
532 g_variant_iter_free(iter);
534 __ASP_LOG_FUNC_EXIT__;
538 void asp_tech_p2p_process_connect_status(GDBusConnection *connection,
539 const gchar *object_path, GVariant *parameters)
541 __ASP_LOG_FUNC_ENTER__;
543 GVariantIter *iter = NULL;
544 GVariant *var = NULL;
545 const gchar *key = NULL;
546 const gchar *str = NULL;
547 guint8 session_mac[MAC_LEN] = {0,};
548 guint32 session_id = 0;
550 gchar *deferred = NULL;
553 __ASP_LOG_FUNC_EXIT__;
557 g_variant_get(parameters, "(a{sv})", &iter);
558 while (g_variant_iter_loop(iter, "{sv}", &key, &var)) {
559 if (!g_strcmp0(key, "session_mac")) {
560 if (asp_dbus_unpack_ay(session_mac, var, MAC_LEN) < 0) {
561 g_variant_iter_free(iter);
565 } else if (!g_strcmp0(key, "session_id")) {
566 g_variant_get(var, "u", &session_id);
567 } else if (!g_strcmp0(key, "status")) {
568 g_variant_get(var, "i", &status);
569 } else if (!g_strcmp0(key, "deferred")) {
570 g_variant_get(var, "&s", &str);
572 deferred = g_strdup(str);
578 if (asp_tech_p2p_ops.connect_status_cb) {
579 asp_tech_p2p_ops.connect_status_cb(0,
580 session_mac, session_id, status,
581 asp_tech_p2p_ops.connect_status_cb_user_data);
584 g_variant_iter_free(iter);
587 __ASP_LOG_FUNC_EXIT__;
591 void asp_tech_p2p_process_session_peer_ip(GDBusConnection *connection,
592 const gchar *object_path, GVariant *parameters)
594 __ASP_LOG_FUNC_ENTER__;
596 GVariantIter *iter = NULL;
597 GVariant *var = NULL;
598 const gchar *key = NULL;
599 guint8 session_mac[MAC_LEN] = {0,};
600 guint8 service_mac[MAC_LEN] = {0,};
601 guint32 session_id = 0;
602 gchar *peer_ip = NULL;
605 __ASP_LOG_FUNC_EXIT__;
609 g_variant_get(parameters, "(a{sv})", &iter);
610 while (g_variant_iter_loop(iter, "{sv}", &key, &var)) {
611 if (!g_strcmp0(key, "session_mac")) {
612 if (asp_dbus_unpack_ay(session_mac, var, MAC_LEN) < 0) {
613 g_variant_iter_free(iter);
616 } else if (!g_strcmp0(key, "session_id")) {
617 g_variant_get(var, "u", &session_id);
618 } else if (!g_strcmp0(key, "service_mac")) {
619 if (asp_dbus_unpack_ay(service_mac, var, MAC_LEN) < 0) {
620 g_variant_iter_free(iter);
624 } else if (!g_strcmp0(key, "assigned_ip_address")) {
625 g_variant_get(var, "&s", &peer_ip);
631 if (peer_ip == NULL) {
632 ASP_LOGE("Invalid peer IP address");
633 g_variant_iter_free(iter);
637 if (asp_tech_p2p_ops.ip_assigned_cb) {
638 asp_tech_p2p_ops.ip_assigned_cb(0,
639 session_mac, session_id, service_mac, peer_ip,
640 strlen(peer_ip), asp_tech_p2p_ops.ip_assigned_cb_user_data);
643 g_variant_iter_free(iter);
645 __ASP_LOG_FUNC_EXIT__;
649 gint32 asp_tech_p2p_advertise(asp_service_advertise_s *service, gint32 replace)
651 __ASP_LOG_FUNC_ENTER__;
652 GVariantBuilder *builder = NULL;
653 GVariant *params = NULL;
654 GError *error = NULL;
655 GVariant *reply = NULL;
658 if (!service || !g_wfd_gdbus_conn) {
659 ASP_LOGE("Invalid parameter!");
660 __ASP_LOG_FUNC_EXIT__;
664 builder = g_variant_builder_new(G_VARIANT_TYPE("a{sv}"));
665 g_variant_builder_add(builder, "{sv}", "adv_id", g_variant_new("u", service->adv_id));
666 g_variant_builder_add(builder, "{sv}", "discovery_tech", g_variant_new("i", service->discovery_tech));
667 g_variant_builder_add(builder, "{sv}", "preferred_connection", g_variant_new("y", service->preferred_connection));
668 g_variant_builder_add(builder, "{sv}", "auto_accept", g_variant_new("i", service->auto_accept));
669 g_variant_builder_add(builder, "{sv}", "status", g_variant_new("y", service->status));
670 g_variant_builder_add(builder, "{sv}", "role", g_variant_new("y", service->role));
671 g_variant_builder_add(builder, "{sv}", "replace", g_variant_new("i", replace));
672 g_variant_builder_add(builder, "{sv}", "config_method", g_variant_new("u", service->config_method));
674 if (service->instance_name)
675 g_variant_builder_add(builder, "{sv}", "instance_name", g_variant_new("s", service->instance_name));
676 if (service->service_type)
677 g_variant_builder_add(builder, "{sv}", "service_type", g_variant_new("s", service->service_type));
678 if (service->service_info_map != NULL)
679 g_variant_builder_add(builder, "{sv}", "service_info",
680 __g_hash_table_to_g_variant(service->service_info_map));
681 if (service->rsp_info)
682 g_variant_builder_add(builder, "{sv}", "rsp_info", g_variant_new("s", service->rsp_info));
683 params = g_variant_new("(a{sv})", builder);
684 g_variant_builder_unref(builder);
686 reply = asp_tech_p2p_dbus_method_call_sync(WFD_MANAGER_ASP_INTERFACE,
687 "AdvertiseService", params, &error);
689 result = __net_wifidirect_gerror_to_enum(error);
691 __ASP_LOG_FUNC_EXIT__;
695 g_variant_get(reply, "(i)", &result);
696 g_variant_unref(reply);
698 ASP_LOGD("%s() return : [%d]", __func__, result);
700 __ASP_LOG_FUNC_EXIT__;
704 gint32 asp_tech_p2p_cancel_advertise(asp_service_advertise_s *service)
706 __ASP_LOG_FUNC_ENTER__;
707 GVariant *params = NULL;
708 GError *error = NULL;
709 GVariant *reply = NULL;
712 if (!service || !g_wfd_gdbus_conn) {
713 ASP_LOGE("Invalid parameter!");
714 __ASP_LOG_FUNC_EXIT__;
718 params = g_variant_new("(u)", service->adv_id);
719 reply = asp_tech_p2p_dbus_method_call_sync(WFD_MANAGER_ASP_INTERFACE,
720 "CancelAdvertiseService", params, &error);
722 result = __net_wifidirect_gerror_to_enum(error);
724 __ASP_LOG_FUNC_EXIT__;
728 g_variant_get(reply, "(i)", &result);
729 g_variant_unref(reply);
731 ASP_LOGD("%s() return : [%d]", __func__, result);
733 __ASP_LOG_FUNC_EXIT__;
737 gint32 asp_tech_p2p_seek(asp_service_seek_s *service)
739 __ASP_LOG_FUNC_ENTER__;
740 GVariantBuilder *builder = NULL;
741 GVariant *params = NULL;
742 GError *error = NULL;
743 GVariant *reply = NULL;
746 if (!service || !g_wfd_gdbus_conn) {
747 ASP_LOGE("Invalid parameter!");
748 __ASP_LOG_FUNC_EXIT__;
753 builder = g_variant_builder_new(G_VARIANT_TYPE("a{sv}"));
754 g_variant_builder_add(builder, "{sv}", "discovery_tech", g_variant_new("i", service->discovery_tech));
755 g_variant_builder_add(builder, "{sv}", "preferred_connection", g_variant_new("y", service->preferred_connection));
756 g_variant_builder_add(builder, "{sv}", "search_id", g_variant_new("t", service->search_id));
757 g_variant_builder_add(builder, "{sv}", "service_type", g_variant_new("s", service->service_type));
758 if (service->service_info_map != NULL)
759 g_variant_builder_add(builder, "{sv}", "service_info", __g_hash_keys_to_g_variant(service->service_info_map));
760 params = g_variant_new("(a{sv})", builder);
761 g_variant_builder_unref(builder);
762 ASP_LOGI("instance name (%s)", service->instance_name);
764 reply = asp_tech_p2p_dbus_method_call_sync(WFD_MANAGER_ASP_INTERFACE,
765 "SeekService", params, &error);
767 result = __net_wifidirect_gerror_to_enum(error);
769 __ASP_LOG_FUNC_EXIT__;
773 g_variant_get(reply, "(i)", &result);
774 g_variant_unref(reply);
776 ASP_LOGD("%s() return : [%d]", __func__, result);
778 __ASP_LOG_FUNC_EXIT__;
782 gint32 asp_tech_p2p_cancel_seek(asp_service_seek_s *service)
784 __ASP_LOG_FUNC_ENTER__;
785 GVariant *params = NULL;
786 GError *error = NULL;
787 GVariant *reply = NULL;
790 if (!service || !g_wfd_gdbus_conn) {
791 ASP_LOGE("Invalid parameter!");
792 __ASP_LOG_FUNC_EXIT__;
796 params = g_variant_new("(t)", service->search_id);
797 reply = asp_tech_p2p_dbus_method_call_sync(WFD_MANAGER_ASP_INTERFACE,
798 "CancelSeekService", params, &error);
800 result = __net_wifidirect_gerror_to_enum(error);
802 __ASP_LOG_FUNC_EXIT__;
806 g_variant_get(reply, "(i)", &result);
807 g_variant_unref(reply);
809 ASP_LOGD("%s() return : [%d]", __func__, result);
811 __ASP_LOG_FUNC_EXIT__;
815 gint32 asp_tech_p2p_init()
817 __ASP_LOG_FUNC_ENTER__;
818 GError* error = NULL;
819 GVariant *reply = NULL;
820 g_wfd_gdbus_conn = NULL;
822 const gchar *str = NULL;
825 asp = asp_get_manager();
827 ASP_LOGE("Failed to get asp");
828 __ASP_LOG_FUNC_EXIT__;
832 g_wfd_gdbus_conn = g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, &error);
833 if (g_wfd_gdbus_conn == NULL) {
834 ASP_LOGE("Failed to get connection, Error[%s]", error->message);
836 __ASP_LOG_FUNC_EXIT__;
840 /* subscribe signal handler */
841 g_wfd_signal_id = g_dbus_connection_signal_subscribe(g_wfd_gdbus_conn,
842 WFD_MANAGER_SERVICE, /* bus name */
843 NULL, /* interface */
845 WFD_MANAGER_PATH, /* object_path */
847 G_DBUS_SIGNAL_FLAGS_NONE,
848 __asp_tech_p2p_dbus_signal_cb,
851 ASP_LOGI("Subscribed dbus signals [%d]", g_wfd_signal_id);
853 /* Get local P2P device address*/
854 reply = asp_tech_p2p_dbus_method_call_sync(WFD_MANAGER_CONFIG_INTERFACE,
855 "GetMacAddress", NULL, &error);
857 result = __net_wifidirect_gerror_to_enum(error);
859 __ASP_LOG_FUNC_EXIT__;
862 g_variant_get(reply, "(i&s)", &result, &str);
863 g_strlcpy(asp->p2p_local_address_str, str, MACSTR_LEN + 1);
864 macaddr_atoe(str, asp->p2p_local_address);
866 g_variant_unref(reply);
868 /* Get local P2P Device Name*/
869 reply = asp_tech_p2p_dbus_method_call_sync(WFD_MANAGER_CONFIG_INTERFACE,
870 "GetDeviceName", NULL, &error);
872 result = __net_wifidirect_gerror_to_enum(error);
874 __ASP_LOG_FUNC_EXIT__;
877 g_variant_get(reply, "(i&s)", &result, &str);
878 g_strlcpy(asp->p2p_device_name, str, DEVICE_NAME_LEN + 1);
880 g_variant_unref(reply);
882 __ASP_LOG_FUNC_EXIT__;
886 gint32 asp_tech_p2p_deinit()
888 __ASP_LOG_FUNC_ENTER__;
891 if (g_wfd_gdbus_conn == NULL)
894 /* unsubscribe signal handler */
895 g_dbus_connection_signal_unsubscribe(g_wfd_gdbus_conn, g_wfd_signal_id);
898 /* unref gdbus connection */
899 g_object_unref(g_wfd_gdbus_conn);
900 g_wfd_gdbus_conn = NULL;
902 __ASP_LOG_FUNC_EXIT__;
906 gint32 asp_tech_p2p_get_peer_role(const guint8 *mac_addr, gint32 *is_connected, gint32 *role)
908 __ASP_LOG_FUNC_ENTER__;
909 GVariant *params = NULL;
910 GVariant *reply = NULL;
911 GError* error = NULL;
913 GVariantIter *iter_peer = NULL;
914 GVariant *var = NULL;
916 gchar mac_address[18] = {0,};
917 gboolean is_group_client = FALSE;
918 gboolean is_group_owner = FALSE;
919 gboolean is_in_group = FALSE;
922 /* Get P2P peer info*/
923 g_snprintf(mac_address, MACSTR_LEN + 1, MACSTR, MAC2STR(mac_addr));
924 params = g_variant_new("(s)", mac_address);
925 reply = asp_tech_p2p_dbus_method_call_sync(WFD_MANAGER_MANAGE_INTERFACE,
926 "GetPeerInfo", params, &error);
928 result = __net_wifidirect_gerror_to_enum(error);
930 __ASP_LOG_FUNC_EXIT__;
934 g_variant_get(reply, "(ia{sv})", &result, &iter_peer);
936 __ASP_LOG_FUNC_EXIT__;
940 while (g_variant_iter_loop(iter_peer, "{sv}", &key, &var)) {
941 if (!g_strcmp0(key, "IsConnected"))
942 is_group_client = g_variant_get_boolean(var);
944 else if (!g_strcmp0(key, "IsGroupOwner"))
945 is_group_owner = g_variant_get_boolean(var);
947 else if (!g_strcmp0(key, "IsInGroup"))
948 is_in_group = g_variant_get_boolean(var);
954 g_variant_iter_free(iter_peer);
955 g_variant_unref(reply);
957 *role = ASP_TECH_P2P_ROLE_GO;
959 *role = ASP_TECH_P2P_ROLE_GC;
962 *is_connected = is_in_group;
964 __ASP_LOG_FUNC_EXIT__;
968 gint32 __asp_tech_p2p_send_prov(asp_tech_session_request_params_s *params)
970 GVariantBuilder *builder = NULL;
971 GVariant *variant_params = NULL;
972 GVariant *reply = NULL;
973 GError* error = NULL;
974 gchar mac_str[MACSTR_LEN + 1] = {0, };
977 builder = g_variant_builder_new(G_VARIANT_TYPE("a{sv}"));
979 g_snprintf(mac_str, MACSTR_LEN + 1, MACSTR, MAC2STR(params->service_mac));
980 g_variant_builder_add(builder, "{sv}", "service_mac", g_variant_new("s", mac_str));
981 g_variant_builder_add(builder, "{sv}", "adv_id", g_variant_new("u", params->advertisement_id));
983 g_snprintf(mac_str, MACSTR_LEN + 1, MACSTR, MAC2STR(params->session_mac));
984 g_variant_builder_add(builder, "{sv}", "session_mac", g_variant_new("s", mac_str));
985 g_variant_builder_add(builder, "{sv}", "session_id", g_variant_new("u", params->session_id));
986 g_variant_builder_add(builder, "{sv}", "role", g_variant_new("y", params->network_role));
987 g_variant_builder_add(builder, "{sv}", "config_method", g_variant_new("u", params->network_config));
988 if (params->session_information)
989 g_variant_builder_add(builder, "{sv}", "session _info", g_variant_new("s", params->session_information));
991 variant_params = g_variant_new("(a{sv})", builder);
992 g_variant_builder_unref(builder);
994 /* Connect ASP session via P2P group */
995 reply = asp_tech_p2p_dbus_method_call_sync(WFD_MANAGER_ASP_INTERFACE,
996 "ConnectSession", variant_params, &error);
998 result = __net_wifidirect_gerror_to_enum(error);
1000 __ASP_LOG_FUNC_EXIT__;
1004 g_variant_get(reply, "(i)", &result);
1005 g_variant_unref(reply);
1007 __ASP_LOG_FUNC_EXIT__;
1011 gint32 asp_tech_p2p_connect_session(asp_tech_session_request_params_s *params)
1013 __ASP_LOG_FUNC_ENTER__;
1014 gint32 is_connected = 0;
1015 gint32 role = ASP_TECH_P2P_ROLE_NEW;
1018 result = asp_tech_p2p_get_peer_role(params->service_mac, &is_connected, &role);
1020 ASP_LOGE("get peer role failed");
1021 __ASP_LOG_FUNC_EXIT__;
1022 return ASP_ERROR_OPERATION_FAILED;
1025 if (params->network_role != ASP_TECH_P2P_ROLE_NEW &&
1026 params->network_role == role) {
1027 ASP_LOGE("Device can't be requested role");
1028 __ASP_LOG_FUNC_EXIT__;
1029 return ASP_ERROR_NETWORK_ROLE_REJECTED;
1031 result = __asp_tech_p2p_send_prov(params);
1033 __ASP_LOG_FUNC_EXIT__;
1037 gint32 asp_tech_p2p_confirm_session(const guint8 *session_mac, gint32 session_id, gint32 confirm, guint32 pin)
1039 __ASP_LOG_FUNC_ENTER__;
1040 GVariantBuilder *builder = NULL;
1041 GVariant *params = NULL;
1042 GVariant *reply = NULL;
1043 GError* error = NULL;
1044 guint8 *service_mac = NULL;
1046 gchar mac_str[MACSTR_LEN + 1] = {0, };
1047 gchar pin_str[PINSTR_LEN + 1] = {0, };
1050 builder = g_variant_builder_new(G_VARIANT_TYPE("a{sv}"));
1052 g_snprintf(mac_str, MACSTR_LEN + 1, MACSTR, MAC2STR(session_mac));
1053 g_variant_builder_add(builder, "{sv}", "session_mac", g_variant_new("s", mac_str));
1054 g_variant_builder_add(builder, "{sv}", "session_id", g_variant_new("u", session_id));
1055 g_variant_builder_add(builder, "{sv}", "confirm", g_variant_new("i", confirm));
1057 g_snprintf(pin_str, PINSTR_LEN + 1, "%u", pin);
1058 g_variant_builder_add(builder, "{sv}", "pin", g_variant_new("s", pin_str));
1060 if (asp_session_get_advertisement_mac(session_mac, session_id, &service_mac)) {
1061 g_snprintf(mac_str, MACSTR_LEN + 1, MACSTR, MAC2STR(service_mac));
1062 g_variant_builder_add(builder, "{sv}", "service_mac", g_variant_new("s", mac_str));
1064 if (asp_session_get_advertisement_id(session_mac, session_id, &adv_id))
1065 g_variant_builder_add(builder, "{sv}", "adv_id", g_variant_new("u", adv_id));
1067 params = g_variant_new("(a{sv})", builder);
1068 g_variant_builder_unref(builder);
1070 /* Confirm session requested via P2P */
1071 reply = asp_tech_p2p_dbus_method_call_sync(WFD_MANAGER_ASP_INTERFACE,
1072 "ConfirmSession", params, &error);
1073 if (error != NULL) {
1074 result = __net_wifidirect_gerror_to_enum(error);
1075 g_error_free(error);
1076 __ASP_LOG_FUNC_EXIT__;
1080 g_variant_get(reply, "(i)", &result);
1081 g_variant_unref(reply);
1083 __ASP_LOG_FUNC_EXIT__;
1087 gint32 asp_tech_p2p_destroy_connection(const guint8 *peer_id, gint32 peer_id_length)
1089 __ASP_LOG_FUNC_ENTER__;
1090 GVariant *reply = NULL;
1091 GError* error = NULL;
1092 gchar mac_str[MACSTR_LEN + 1] = {0, };
1095 g_snprintf(mac_str, MACSTR_LEN + 1, MACSTR, MAC2STR(peer_id));
1096 /* Destroy ASP P2P Group */
1097 reply = asp_tech_p2p_dbus_method_call_sync(WFD_MANAGER_GROUP_INTERFACE,
1098 "DestroyGroup", NULL, &error);
1099 if (error != NULL) {
1100 result = __net_wifidirect_gerror_to_enum(error);
1101 g_error_free(error);
1102 __ASP_LOG_FUNC_EXIT__;
1106 g_variant_get(reply, "(i)", &result);
1107 g_variant_unref(reply);
1109 __ASP_LOG_FUNC_EXIT__;
1113 gint32 asp_tech_p2p_is_peer_connected(const guint8 *peer_id, gint32 peer_id_length, gint32 *is_connected)
1115 __ASP_LOG_FUNC_ENTER__;
1119 result = asp_tech_p2p_get_peer_role(peer_id, is_connected, &role);
1121 __ASP_LOG_FUNC_EXIT__;
1125 asp_tech_ops_s asp_tech_p2p_ops = {
1126 .init = asp_tech_p2p_init,
1127 .deinit = asp_tech_p2p_deinit,
1128 .advertise = asp_tech_p2p_advertise,
1129 .cancel_advertise = asp_tech_p2p_cancel_advertise,
1130 .seek = asp_tech_p2p_seek,
1131 .cancel_seek = asp_tech_p2p_cancel_seek,
1132 .connect_session = asp_tech_p2p_connect_session,
1133 .confirm_session = asp_tech_p2p_confirm_session,
1134 .destroy_connection = asp_tech_p2p_destroy_connection,
1135 .is_peer_connected = asp_tech_p2p_is_peer_connected,
1136 .session_request_cb = NULL,
1137 .session_request_cb_user_data = NULL,
1138 .session_config_request_cb = NULL,
1139 .connect_status_cb = NULL,
1140 .connect_status_cb_user_data = NULL,
1141 .ip_assigned_cb = NULL,
1142 .ip_assigned_cb_user_data = NULL,