182efea4e16d53f4eb0d3d5609b4ec5d23397fa1
[platform/core/connectivity/net-config.git] / src / wifi-tdls.c
1 /*
2  * Network Configuration Module
3  *
4  * Copyright (c) 2012-2013 Samsung Electronics Co., Ltd. All rights reserved.
5  *
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  * http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  *
18  */
19
20 #include <stdio.h>
21 #include <time.h>
22 #include <stdlib.h>
23 #include <sys/time.h>
24 #include <unistd.h>
25 #include <string.h>
26 #include "neterror.h"
27 #include "netdbus.h"
28 #include "netsupplicant.h"
29 #include "network-state.h"
30 #include <vconf.h>
31 #include <vconf-keys.h>
32 #include <arpa/inet.h>
33 #include <log.h>
34 #include "util.h"
35 #include "neterror.h"
36 #include "wifi-tdls.h"
37 #include <glib.h>
38
39 char *peer_mac = NULL;
40 int is_connected = 0;
41
42 void __netconfig_wifi_notify_tdls_event(const char *sig_name, const char *peer_mac)
43 {
44         GVariantBuilder *builder;
45         GVariant *params;
46         builder = g_variant_builder_new(G_VARIANT_TYPE("a{sv}"));
47         g_variant_builder_add(builder, "{sv}", "peermac", g_variant_new_string(peer_mac));
48
49         params = g_variant_new("(@a{sv})", g_variant_builder_end(builder));
50         g_variant_builder_unref(builder);
51
52         netconfig_dbus_emit_signal(NULL,
53                                 NETCONFIG_WIFI_PATH,
54                                 NETCONFIG_WIFI_INTERFACE,
55                                 sig_name,
56                                 params);
57
58         INFO("Sent signal (%s) Peer Mac (%s)", sig_name, peer_mac);
59 }
60
61 static GVariant * __netconfig_wifi_tdls_send_dbus_str(const char* method, const char *str)
62 {
63         GVariant *message = NULL;
64         const char *if_path = NULL;
65         GVariant *params = NULL;
66
67         if_path = netconfig_wifi_get_supplicant_interface();
68         if (if_path == NULL) {
69                 ERR("Fail to get wpa_supplicant DBus path");
70                 return NULL;
71         }
72
73         params = g_variant_new("(s)", str);
74         INFO("[TizenMW-->WPAS] Sent Dbus Method :[%s],value[%s]", method, str);
75         message = netconfig_invoke_dbus_method(SUPPLICANT_SERVICE,
76                         if_path, SUPPLICANT_INTERFACE ".Interface", method, params);
77
78         INFO("TDLS Returned from Blocking method for Send DBUS Command");
79         return message;
80 }
81
82 gboolean handle_tdls_connect(Wifi *wifi, GDBusMethodInvocation *context,
83                         gchar *peer_mac_Addr)
84 {
85         DBG("[TizenMW-->WPAS]: TDLS Setup Request: [%s]", peer_mac_Addr);
86
87         if (is_connected) {
88                 ERR(" Already TDLS Connection !!!");
89         } else {
90                 GVariant *message = NULL;
91                 message = __netconfig_wifi_tdls_send_dbus_str("TDLSSetup", (const char*)peer_mac_Addr);
92
93                 if (message == NULL) {
94                         ERR(" TDLS : failed to connect !!!");
95                         netconfig_error_dbus_method_return(context, NETCONFIG_ERROR_INTERNAL, "FailTdlsConnect");
96                         return FALSE;
97                 }
98
99                 DBG("[TizenMW<--WPAS] TDLS DBUS Command sent successfully");
100                 g_variant_unref(message);
101                 is_connected = 1;
102         }
103
104         wifi_complete_tdls_connect(wifi, context, 1);
105         return TRUE;
106 }
107
108 gboolean handle_tdls_discover(Wifi *wifi, GDBusMethodInvocation *context,
109                         gchar *peer_mac_Addr)
110 {
111         DBG("[TizenMW-->WPAS]: TDLS Discover Request: [%s], peer_mac_Addr");
112
113         if (is_connected) {
114                 ERR(" Already TDLS Connection !!!");
115         } else {
116                 GVariant *message = NULL;
117                 message = __netconfig_wifi_tdls_send_dbus_str("TDLSDiscover", (const char*)peer_mac_Addr);
118
119                 if (message == NULL) {
120                         ERR(" TDLS : failed to discover !!!");
121                         netconfig_error_dbus_method_return(context, NETCONFIG_ERROR_INTERNAL, "FailTdlsDiscover");
122                         return FALSE;
123                 }
124
125                 DBG("[TizenMW<--WPAS] TDLS DBUS Command sent successfully");
126                 g_variant_unref(message);
127         }
128
129         wifi_complete_tdls_discover(wifi, context, 1);
130         return TRUE;
131 }
132
133 gboolean handle_tdls_disconnect(Wifi *wifi, GDBusMethodInvocation *context,
134                         gchar *peer_mac_Addr)
135 {
136         DBG("[TizenMW-->WPAS]: TDLS Teardown Request: [%s]", peer_mac_Addr);
137
138         if (!is_connected) {
139                 ERR(" Already TDLS discnnection !!!");
140         } else {
141                 GVariant *message = NULL;
142                 message = __netconfig_wifi_tdls_send_dbus_str("TDLSTeardown", (const char*)peer_mac_Addr);
143
144                 if (message == NULL) {
145                         ERR(" TDLS : failed to disconnect !!!");
146                         netconfig_error_dbus_method_return(context, NETCONFIG_ERROR_INTERNAL, "FailTdlsDisconnect");
147                         return FALSE;
148                 }
149
150                 DBG("[TizenMW<--WPAS] TDLS DBUS Command sent successfully");
151                 g_variant_unref(message);
152                 is_connected = 0;
153         }
154
155         wifi_complete_tdls_disconnect(wifi, context, 1);
156         return TRUE;
157 }
158
159 gboolean handle_tdls_connected_peer(Wifi *wifi, GDBusMethodInvocation *context)
160 {
161         DBG("[TizenMW-->WPAS]: TDLS Connected Peer Request: ");
162
163         GVariant *message = NULL;
164         const gchar* reply_str = NULL;
165
166         if (peer_mac == NULL) {
167                 INFO("TDLS: No Active Connection");
168                 wifi_complete_tdls_connected_peer(wifi, context, "00.00.00.00.00.00");
169                 return TRUE;
170         }
171         message = __netconfig_wifi_tdls_send_dbus_str("TDLSStatus", (const char*)peer_mac);
172         if (message == NULL) {
173                 ERR(" TDLS : No active TDLS Link Setup !!!");
174                 wifi_complete_tdls_connected_peer(wifi, context, "00.00.00.00.00.00");
175                 return TRUE;
176         }
177
178         g_variant_get(message, "(&s)", &reply_str);
179         INFO("TDLS reply: [%s]", reply_str);
180         INFO("TDLS :peer_mac [%s]", peer_mac);
181
182         if (g_strcmp0("connected", reply_str) != 0) {
183                 ERR("[TizenMW<--WPAS] TDLS Connection not available");
184                 wifi_complete_tdls_connected_peer(wifi, context, "00.00.00.00.00.00");
185                 g_variant_unref(message);
186                 return TRUE;
187         }
188
189         INFO("[TizenMW<--WPAS] TDLS Connection available, Peer Mac address %s", peer_mac);
190         wifi_complete_tdls_connected_peer(wifi, context, peer_mac);
191
192         g_variant_unref(message);
193         return TRUE;
194 }
195
196 void netconfig_wifi_tdls_connected_event(GVariant *message)
197 {
198
199         DBG("[TizenMW<--WPAS] WiFi TDLS Connected EVENT");
200         if (is_connected == 1) {
201                 INFO("TDLS Peer already connected");
202                 g_free(peer_mac);
203         }
204
205         g_variant_get(message, "(s)", &peer_mac);
206         INFO("Peer Mac Address: [%s]", peer_mac);
207
208         is_connected = 1;
209         __netconfig_wifi_notify_tdls_event("TDLSConnect", peer_mac);
210 }
211
212 void netconfig_wifi_tdls_disconnected_event(GVariant *message)
213 {
214         DBG("[TizenMW<--WPAS]: WiFi TDLS Disconnected EVENT");
215         const gchar *peer_mac_addr = NULL;
216
217         g_variant_get(message, "(&s)", &peer_mac_addr);
218         if (g_strcmp0(peer_mac, peer_mac_addr) == 0) {
219                 INFO("TDLS Peer Disconnected Mac Address: [%s]", peer_mac);
220                 is_connected = 0;
221                 __netconfig_wifi_notify_tdls_event("TDLSDisconnect", peer_mac);
222         } else
223                 INFO("TDLS Peer Disconnected peer_mac(%s) != peer_mac_address(%s)", peer_mac, peer_mac_addr);
224 }
225
226
227 void netconfig_wifi_tdls_peer_found_event(GVariant *message)
228 {
229         DBG("[TizenMW<--WPAS]: WiFi TDLS Discovery EVENT");
230         const gchar *peer_mac_addr = NULL;
231
232         g_variant_get(message, "(s)", &peer_mac_addr);
233         INFO("Discover Peer Mac Address: [%s]", peer_mac_addr);
234
235         __netconfig_wifi_notify_tdls_event("TDLSPeerFound", peer_mac_addr);
236 }
237