Deinitialize gatt server properly
[platform/core/connectivity/bluetooth-frwk.git] / plugin / headed.c
1 /*
2  * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
3  *
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
7  *
8  *              http://www.apache.org/licenses/LICENSE-2.0
9  *
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.
15  *
16  */
17
18 #include <stdio.h>
19 #include <stdbool.h>
20 #include <stdlib.h>
21 #include <string.h>
22 #include <unistd.h>
23 #include <syspopup_caller.h>
24 #include <bundle.h>
25 #include <bundle_internal.h>
26 #include <tethering.h>
27 #include <mime_type.h>
28 #include <app_control.h>
29
30 #include "plugin.h"
31 #include "bluetooth-api.h"
32
33 #define BT_AGENT_SYSPOPUP_MAX_ATTEMPT 3
34 #define BT_MAX_EVENT_STR_LENGTH 50
35 #define BT_AGENT_SYSPOPUP_TIMEOUT_FOR_MULTIPLE_POPUPS 200
36
37 #ifdef TIZEN_FEATURE_BT_DPM
38 int bt_launch_dpm_popup(char *mode)
39 {
40         int ret = 0;
41         bundle *b;
42
43         b = bundle_create();
44         retv_if(b == NULL, BLUETOOTH_ERROR_INTERNAL);
45
46         bundle_add(b, "mode", mode);
47
48         ret = syspopup_launch(BT_DPM_SYSPOPUP, b);
49
50         if (ret < 0)
51                 BT_ERR("Popup launch failed: %d\n", ret);
52
53         bundle_free(b);
54
55         return ret;
56 }
57 #endif
58
59 static gboolean _bt_syspopup_timer_cb(gpointer user_data)
60 {
61         int ret;
62         bundle *b;
63         retv_if(user_data == NULL, FALSE);
64
65         b = (bundle *)user_data;
66
67         ret = syspopup_launch("bt-syspopup", b);
68         if (ret < 0) {
69                 BT_ERR("Sorry!! Cannot launch popup return = %d, Retrying...", ret);
70         } else {
71                 BT_DBG("Hurray!!! Finally Popup launched");
72                 bundle_free(b);
73         }
74         return (ret < 0) ? TRUE : FALSE;
75 }
76
77
78 static gboolean _bt_agent_system_popup_timer_cb(gpointer user_data)
79 {
80         int ret;
81         static int retry_count;
82         bundle *b = (bundle *)user_data;
83         retv_if(user_data == NULL, FALSE);
84
85         ++retry_count;
86
87         ret = syspopup_launch("bt-syspopup", b);
88         if (ret < 0) {
89                 BT_ERR("Sorry! Can't launch popup, ret=%d, Re-try[%d] time..",
90                                                         ret, retry_count);
91                 if (retry_count >= BT_AGENT_SYSPOPUP_MAX_ATTEMPT) {
92                         BT_ERR("Sorry!! Max retry %d reached", retry_count);
93                         bundle_free(b);
94                         retry_count = 0;
95                         return FALSE;
96                 }
97         } else {
98                 BT_DBG("Hurray!! Finally Popup launched");
99                 retry_count = 0;
100                 bundle_free(b);
101         }
102
103         return (ret < 0) ? TRUE : FALSE;
104 }
105
106 int bt_launch_system_popup(bt_agent_event_type_t event_type,
107                                                         const char *device_name,
108                                                         const unsigned char *auth_info,
109                                                         char *passkey,
110                                                         const char *filename,
111                                                         const char *agent_path)
112 {
113         int ret;
114         bundle *b;
115         char event_str[BT_MAX_EVENT_STR_LENGTH + 1];
116
117         b = bundle_create();
118         if (!b) {
119                 BT_ERR("Launching system popup failed");
120                 return -1;
121         }
122
123         bundle_add(b, "device-name", device_name);
124         bundle_add(b, "auth-info", (const char *)auth_info);
125         bundle_add(b, "passkey", passkey);
126         bundle_add(b, "file", filename);
127         bundle_add(b, "agent-path", agent_path);
128
129         switch (event_type) {
130         case BT_AGENT_EVENT_PIN_REQUEST:
131                 g_strlcpy(event_str, "pin-request", sizeof(event_str));
132                 break;
133
134         case BT_AGENT_EVENT_PASSKEY_CONFIRM_REQUEST:
135                 g_strlcpy(event_str, "passkey-confirm-request",
136                                                 sizeof(event_str));
137                 break;
138
139         case BT_AGENT_EVENT_PASSKEY_REQUEST:
140                 g_strlcpy(event_str, "passkey-request", sizeof(event_str));
141                 break;
142
143         case BT_AGENT_EVENT_PASSKEY_DISPLAY_REQUEST:
144                 g_strlcpy(event_str, "passkey-display-request",
145                                                 sizeof(event_str));
146                 break;
147
148         case BT_AGENT_EVENT_AUTHORIZE_REQUEST:
149                 g_strlcpy(event_str, "authorize-request",
150                                                 sizeof(event_str));
151                 break;
152
153         case BT_AGENT_EVENT_CONFIRM_MODE_REQUEST:
154                 g_strlcpy(event_str, "confirm-mode-request",
155                                                 sizeof(event_str));
156                 break;
157
158         case BT_AGENT_EVENT_FILE_RECEIVED:
159                 g_strlcpy(event_str, "file-received", sizeof(event_str));
160                 break;
161
162         case BT_AGENT_EVENT_KEYBOARD_PASSKEY_REQUEST:
163                 g_strlcpy(event_str, "keyboard-passkey-request",
164                                                 sizeof(event_str));
165                 break;
166
167         case BT_AGENT_EVENT_TERMINATE:
168                 g_strlcpy(event_str, "terminate", sizeof(event_str));
169                 break;
170
171         case BT_AGENT_EVENT_EXCHANGE_REQUEST:
172                 g_strlcpy(event_str, "exchange-request", sizeof(event_str));
173                 break;
174
175         case BT_AGENT_EVENT_PBAP_REQUEST:
176                 g_strlcpy(event_str, "phonebook-request", sizeof(event_str));
177                 break;
178
179         case BT_AGENT_EVENT_MAP_REQUEST:
180                 g_strlcpy(event_str, "message-request", sizeof(event_str));
181                 break;
182
183         case BT_AGENT_EVENT_LEGACY_PAIR_FAILED_FROM_REMOTE:
184                 g_strlcpy(event_str, "remote-legacy-pair-failed", sizeof(event_str));
185                 break;
186
187         default:
188                 BT_ERR("Invalid event type");
189                 bundle_free(b);
190                 return -1;
191
192         }
193
194         bundle_add(b, "event-type", event_str);
195
196         ret = syspopup_launch("bt-syspopup", b);
197         if (0 > ret) {
198                 BT_ERR("Popup launch failed...retry %d", ret);
199
200                 g_timeout_add(BT_AGENT_SYSPOPUP_TIMEOUT_FOR_MULTIPLE_POPUPS,
201                               (GSourceFunc)_bt_agent_system_popup_timer_cb, b);
202         } else {
203                 bundle_free(b);
204         }
205
206         BT_INFO("_bt_agent_launch_system_popup");
207         return 0;
208 }
209
210 bool bt_launch_unable_to_pairing_syspopup(int result)
211 {
212         BT_DBG("+");
213         int ret = 0;
214         bundle *b = NULL;
215
216         b = bundle_create();
217         if (b == NULL)
218                 return false;
219
220         bundle_add(b, "event-type", "unable-to-pairing");
221
222         if (result == BLUETOOTH_ERROR_TIMEOUT)
223                 bundle_add(b, "error", "timeout");
224         else if (result == BLUETOOTH_ERROR_AUTHENTICATION_FAILED)
225                 bundle_add(b, "error", "authfailed");
226         else
227                 bundle_add(b, "error", "error");
228
229         ret = syspopup_launch("bt-syspopup", b);
230         if (0 > ret) {
231                 BT_ERR("Popup launch failed...retry %d \n", ret);
232                 g_timeout_add(200, (GSourceFunc) _bt_syspopup_timer_cb,
233                                 b);
234         } else {
235                 bundle_free(b);
236         }
237
238         BT_DBG("-");
239         return true;
240 }
241
242
243 bool bt_is_tethering_enabled(void)
244 {
245         BT_DBG("+");
246
247         tethering_h tethering = NULL;
248         bool enabled = FALSE;
249         int ret;
250
251         ret = tethering_create(&tethering);
252
253         if (ret != TETHERING_ERROR_NONE) {
254                 BT_ERR("Fail to create tethering: %d", ret);
255                 return FALSE;
256         }
257
258         enabled = tethering_is_enabled(tethering, TETHERING_TYPE_BT);
259
260         if (enabled != true)
261                 BT_ERR("BT tethering is not enabled");
262
263         ret = tethering_destroy(tethering);
264
265         if (ret != TETHERING_ERROR_NONE)
266                 BT_ERR("Fail to destroy tethering: %d", ret);
267
268         return enabled;
269 }
270
271 int bt_get_mime_type(char *file_name, char **mime_type)
272 {
273         BT_DBG("+");
274
275         int ret = MIME_TYPE_ERROR_NONE;
276
277         if (file_name == NULL)
278                 return BLUETOOTH_ERROR_INVALID_PARAM;
279
280         ret = mime_type_get_mime_type(file_name, (gchar **)mime_type);
281
282         if (ret != MIME_TYPE_ERROR_NONE) {
283                 BT_ERR("Fail to get mime type: %d", ret);
284                 return BLUETOOTH_ERROR_INTERNAL;
285         }
286
287         return BLUETOOTH_ERROR_NONE;
288 }
289
290 void bt_destroy_popup_all(void)
291 {
292         syspopup_destroy_all();
293 }
294
295 int bt_app_control_send_launch_request(char *absolute_path)
296 {
297         BT_DBG("+");
298
299         app_control_h app_control;
300         int ret;
301
302         app_control_create(&app_control);
303         app_control_set_operation(app_control, APP_CONTROL_OPERATION_VIEW);
304         app_control_set_uri(app_control, absolute_path);
305         app_control_set_mime(app_control, "*/*");
306
307         if (app_control_send_launch_request(app_control, NULL, NULL) == APP_CONTROL_ERROR_NONE)
308                 ret = BLUETOOTH_ERROR_NONE;
309         else
310                 ret = BLUETOOTH_ERROR_INTERNAL;
311
312         app_control_destroy(app_control);
313
314         return ret;
315 }
316
317 extern struct bluetooth_headed_plugin_t headed_plugin
318 __attribute__ ((visibility("default")));
319 struct bluetooth_headed_plugin_t headed_plugin = {
320 #ifdef TIZEN_FEATURE_BT_DPM
321         bt_launch_dpm_popup,
322 #else
323                 NULL,
324 #endif
325         bt_launch_system_popup,
326         bt_destroy_popup_all,
327         bt_launch_unable_to_pairing_syspopup,
328         bt_is_tethering_enabled,
329         bt_get_mime_type
330 };
331