Add support for handling multiple wifi interfaces
[platform/upstream/connman.git] / src / main.c
1 /*
2  *
3  *  Connection Manager
4  *
5  *  Copyright (C) 2007-2013  Intel Corporation. All rights reserved.
6  *
7  *  This program is free software; you can redistribute it and/or modify
8  *  it under the terms of the GNU General Public License version 2 as
9  *  published by the Free Software Foundation.
10  *
11  *  This program is distributed in the hope that it will be useful,
12  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  *  GNU General Public License for more details.
15  *
16  *  You should have received a copy of the GNU General Public License
17  *  along with this program; if not, write to the Free Software
18  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
19  *
20  */
21
22 #ifdef HAVE_CONFIG_H
23 #include <config.h>
24 #endif
25
26 #include <errno.h>
27 #include <stdio.h>
28 #include <stdlib.h>
29 #include <unistd.h>
30 #include <string.h>
31 #include <signal.h>
32 #include <sys/signalfd.h>
33 #include <getopt.h>
34 #include <sys/stat.h>
35 #include <net/if.h>
36 #include <netdb.h>
37 #include <sys/time.h>
38 #include <sys/resource.h>
39
40 #include <gdbus.h>
41
42 #include "connman.h"
43
44 #define CONF_ARRAY_SIZE(x) (sizeof(x)/sizeof(x[0]) - 1)
45
46 #define DEFAULT_INPUT_REQUEST_TIMEOUT (120 * 1000)
47 #define DEFAULT_BROWSER_LAUNCH_TIMEOUT (300 * 1000)
48
49 #if defined TIZEN_EXT
50 #define DEFAULT_WIFI_INTERFACE "wlan0"
51 #endif
52
53 #define MAINFILE "main.conf"
54 #define CONFIGMAINFILE CONFIGDIR "/" MAINFILE
55
56 static char *default_auto_connect[] = {
57         "wifi",
58         "ethernet",
59         "cellular",
60         NULL
61 };
62
63 static char *default_favorite_techs[] = {
64         "ethernet",
65         NULL
66 };
67
68 static char *default_blacklist[] = {
69         "vmnet",
70         "vboxnet",
71         "virbr",
72         "ifb",
73         "ve-",
74         "vb-",
75         NULL
76 };
77
78 static struct {
79         bool bg_scan;
80         char **pref_timeservers;
81         unsigned int *auto_connect;
82         unsigned int *favorite_techs;
83         unsigned int *preferred_techs;
84         unsigned int *always_connected_techs;
85         char **fallback_nameservers;
86         unsigned int timeout_inputreq;
87         unsigned int timeout_browserlaunch;
88         char **blacklisted_interfaces;
89         bool allow_hostname_updates;
90         bool allow_domainname_updates;
91         bool single_tech;
92         char **tethering_technologies;
93         bool persistent_tethering_mode;
94         bool enable_6to4;
95         char *vendor_class_id;
96         bool enable_online_check;
97         bool auto_connect_roaming_services;
98         bool acd;
99         bool use_gateways_as_timeservers;
100 #if defined TIZEN_EXT
101         char **cellular_interfaces;
102         bool tizen_tv_extension;
103         bool auto_ip;
104         char *global_nameserver;
105         bool supplicant_debug;
106         char *def_wifi_ifname;
107 #endif
108 } connman_settings  = {
109         .bg_scan = true,
110         .pref_timeservers = NULL,
111         .auto_connect = NULL,
112         .favorite_techs = NULL,
113         .preferred_techs = NULL,
114         .always_connected_techs = NULL,
115         .fallback_nameservers = NULL,
116         .timeout_inputreq = DEFAULT_INPUT_REQUEST_TIMEOUT,
117         .timeout_browserlaunch = DEFAULT_BROWSER_LAUNCH_TIMEOUT,
118         .blacklisted_interfaces = NULL,
119         .allow_hostname_updates = true,
120         .allow_domainname_updates = true,
121         .single_tech = false,
122         .tethering_technologies = NULL,
123         .persistent_tethering_mode = false,
124         .enable_6to4 = false,
125         .vendor_class_id = NULL,
126         .enable_online_check = true,
127         .auto_connect_roaming_services = false,
128         .acd = false,
129         .use_gateways_as_timeservers = false,
130 #if defined TIZEN_EXT
131         .cellular_interfaces = NULL,
132         .tizen_tv_extension = false,
133         .auto_ip = true,
134         .global_nameserver = NULL,
135         .supplicant_debug = false,
136         .def_wifi_ifname = DEFAULT_WIFI_INTERFACE,
137 #endif
138 };
139
140 #if defined TIZEN_EXT
141 static struct {
142         /* BSSID */
143         char *ins_preferred_freq_bssid;
144         bool ins_last_connected_bssid;
145         bool ins_assoc_reject;
146         bool ins_signal_bssid;
147         unsigned int ins_preferred_freq_bssid_score;
148         unsigned int ins_last_connected_bssid_score;
149         unsigned int ins_assoc_reject_score;
150         /* SSID */
151         bool ins_last_user_selection;
152         unsigned int ins_last_user_selection_time;
153         bool ins_last_connected;
154         char *ins_preferred_freq;
155         char **ins_security_priority;
156         unsigned int ins_security_priority_count;
157         bool ins_signal;
158         bool ins_internet;
159         unsigned int ins_last_user_selection_score;
160         unsigned int ins_last_connected_score;
161         unsigned int ins_preferred_freq_score;
162         unsigned int ins_security_priority_score;
163         unsigned int ins_internet_score;
164         /* Common */
165         int ins_signal_level3_5ghz;
166         int ins_signal_level3_24ghz;
167 } connman_ins_settings = {
168         /* BSSID */
169         .ins_preferred_freq_bssid = NULL,
170         .ins_last_connected_bssid = true,
171         .ins_assoc_reject = true,
172         .ins_signal_bssid = true,
173         .ins_preferred_freq_bssid_score = 20,
174         .ins_last_connected_bssid_score = 20,
175         .ins_assoc_reject_score = 10,
176         /* SSID */
177         .ins_last_user_selection = true,
178         .ins_last_user_selection_time = 480,
179         .ins_last_connected = true,
180         .ins_preferred_freq = NULL,
181         .ins_security_priority = NULL,
182         .ins_security_priority_count = 0,
183         .ins_signal = true,
184         .ins_internet = true,
185         .ins_last_user_selection_score = 30,
186         .ins_last_connected_score = 30,
187         .ins_preferred_freq_score = 60,
188         .ins_security_priority_score = 5,
189         .ins_internet_score = 30,
190         /* Common */
191         .ins_signal_level3_5ghz = -76,
192         .ins_signal_level3_24ghz = -74,
193 };
194 #endif
195
196 #define CONF_BG_SCAN                    "BackgroundScanning"
197 #define CONF_PREF_TIMESERVERS           "FallbackTimeservers"
198 #define CONF_AUTO_CONNECT_TECHS         "DefaultAutoConnectTechnologies"
199 #define CONF_FAVORITE_TECHS             "DefaultFavoriteTechnologies"
200 #define CONF_ALWAYS_CONNECTED_TECHS     "AlwaysConnectedTechnologies"
201 #define CONF_PREFERRED_TECHS            "PreferredTechnologies"
202 #define CONF_FALLBACK_NAMESERVERS       "FallbackNameservers"
203 #define CONF_TIMEOUT_INPUTREQ           "InputRequestTimeout"
204 #define CONF_TIMEOUT_BROWSERLAUNCH      "BrowserLaunchTimeout"
205 #define CONF_BLACKLISTED_INTERFACES     "NetworkInterfaceBlacklist"
206 #define CONF_ALLOW_HOSTNAME_UPDATES     "AllowHostnameUpdates"
207 #define CONF_ALLOW_DOMAINNAME_UPDATES   "AllowDomainnameUpdates"
208 #define CONF_SINGLE_TECH                "SingleConnectedTechnology"
209 #define CONF_TETHERING_TECHNOLOGIES      "TetheringTechnologies"
210 #define CONF_PERSISTENT_TETHERING_MODE  "PersistentTetheringMode"
211 #define CONF_ENABLE_6TO4                "Enable6to4"
212 #define CONF_VENDOR_CLASS_ID            "VendorClassID"
213 #define CONF_ENABLE_ONLINE_CHECK        "EnableOnlineCheck"
214 #define CONF_AUTO_CONNECT_ROAMING_SERVICES "AutoConnectRoamingServices"
215 #define CONF_ACD                        "AddressConflictDetection"
216 #define CONF_USE_GATEWAYS_AS_TIMESERVERS "UseGatewaysAsTimeservers"
217 #if defined TIZEN_EXT
218 #define CONF_CELLULAR_INTERFACE         "NetworkCellularInterfaceList"
219 #define CONF_TIZEN_TV_EXT                       "TizenTVExtension"
220 #define CONF_ENABLE_AUTO_IP                     "EnableAutoIp"
221 #define CONF_GLOBAL_NAMESERVER          "GlobalNameserver"
222 #define CONF_CONNMAN_SUPPLICANT_DEBUG   "ConnmanSupplicantDebug"
223 #define CONF_CONNMAN_WIFI_DEF_IFNAME    "DefaultWifiInterface"
224 #endif
225
226 #if defined TIZEN_EXT
227 /* BSSID */
228 #define CONF_INS_PREFERRED_FREQ_BSSID        "INSPreferredFreqBSSID"
229 #define CONF_INS_PREFERRED_FREQ_BSSID_SCORE  "INSPreferredFreqBSSIDScore"
230 #define CONF_INS_LAST_CONNECTED_BSSID        "INSLastConnectedBSSID"
231 #define CONF_INS_LAST_CONNECTED_BSSID_SCORE  "INSLastConnectedBSSIDScore"
232 #define CONF_INS_ASSOC_REJECT                "INSAssocReject"
233 #define CONF_INS_ASSOC_REJECT_SCORE          "INSAssocRejectScore"
234 #define CONF_INS_SIGNAL_BSSID                "INSSignalBSSID"
235 /* SSID */
236 #define CONF_INS_LAST_USER_SELECTION         "INSLastUserSelection"
237 #define CONF_INS_LAST_USER_SELECTION_TIME    "INSLastUserSelectionTime"
238 #define CONF_INS_LAST_USER_SELECTION_SCORE   "INSLastUserSelectionScore"
239 #define CONF_INS_LAST_CONNECTED              "INSLastConnected"
240 #define CONF_INS_LAST_CONNECTED_SCORE        "INSLastConnectedScore"
241 #define CONF_INS_PREFERRED_FREQ              "INSPreferredFreq"
242 #define CONF_INS_PREFERRED_FREQ_SCORE        "INSPreferredFreqScore"
243 #define CONF_INS_SECURITY_PRIORITY           "INSSecurityPriority"
244 #define CONF_INS_SECURITY_PRIORITY_COUNT     "INSSecurityPriorityCount"
245 #define CONF_INS_SECURITY_PRIORITY_SCORE     "INSSecurityPriorityScore"
246 #define CONF_INS_SIGNAL                      "INSSignal"
247 #define CONF_INS_INTERNET                    "INSInternet"
248 #define CONF_INS_INTERNET_SCORE              "INSInternetScore"
249 /* Common */
250 #define CONF_INS_SIGNAL_LEVEL3_5GHZ          "INSSignalLevel3_5GHz"
251 #define CONF_INS_SIGNAL_LEVEL3_24GHZ         "INSSignalLevel3_24GHz"
252 #endif
253
254 static const char *supported_options[] = {
255         CONF_BG_SCAN,
256         CONF_PREF_TIMESERVERS,
257         CONF_AUTO_CONNECT_TECHS,
258         CONF_ALWAYS_CONNECTED_TECHS,
259         CONF_PREFERRED_TECHS,
260         CONF_FALLBACK_NAMESERVERS,
261         CONF_TIMEOUT_INPUTREQ,
262         CONF_TIMEOUT_BROWSERLAUNCH,
263         CONF_BLACKLISTED_INTERFACES,
264         CONF_ALLOW_HOSTNAME_UPDATES,
265         CONF_ALLOW_DOMAINNAME_UPDATES,
266         CONF_SINGLE_TECH,
267         CONF_TETHERING_TECHNOLOGIES,
268         CONF_PERSISTENT_TETHERING_MODE,
269         CONF_ENABLE_6TO4,
270         CONF_VENDOR_CLASS_ID,
271         CONF_ENABLE_ONLINE_CHECK,
272         CONF_AUTO_CONNECT_ROAMING_SERVICES,
273         CONF_ACD,
274         CONF_USE_GATEWAYS_AS_TIMESERVERS,
275 #if defined TIZEN_EXT
276         CONF_CELLULAR_INTERFACE,
277         CONF_TIZEN_TV_EXT,
278         CONF_ENABLE_AUTO_IP,
279         CONF_GLOBAL_NAMESERVER,
280         CONF_CONNMAN_SUPPLICANT_DEBUG,
281         CONF_CONNMAN_WIFI_DEF_IFNAME,
282 #endif
283         NULL
284 };
285
286 #if defined TIZEN_EXT
287 static const char *supported_ins_options[] = {
288         /* BSSID */
289         CONF_INS_PREFERRED_FREQ_BSSID,
290         CONF_INS_PREFERRED_FREQ_BSSID_SCORE,
291         CONF_INS_LAST_CONNECTED_BSSID,
292         CONF_INS_LAST_CONNECTED_BSSID_SCORE,
293         CONF_INS_ASSOC_REJECT,
294         CONF_INS_ASSOC_REJECT_SCORE,
295         CONF_INS_SIGNAL_BSSID,
296         /* SSID */
297         CONF_INS_LAST_USER_SELECTION,
298         CONF_INS_LAST_USER_SELECTION_TIME,
299         CONF_INS_LAST_USER_SELECTION_SCORE,
300         CONF_INS_LAST_CONNECTED,
301         CONF_INS_LAST_CONNECTED_SCORE,
302         CONF_INS_PREFERRED_FREQ,
303         CONF_INS_PREFERRED_FREQ_SCORE,
304         CONF_INS_SECURITY_PRIORITY,
305         CONF_INS_SECURITY_PRIORITY_COUNT,
306         CONF_INS_SECURITY_PRIORITY_SCORE,
307         CONF_INS_SIGNAL,
308         CONF_INS_INTERNET,
309         CONF_INS_INTERNET_SCORE,
310         /* Common */
311         CONF_INS_SIGNAL_LEVEL3_5GHZ,
312         CONF_INS_SIGNAL_LEVEL3_24GHZ,
313         NULL
314 };
315 #endif
316
317 static GKeyFile *load_config(const char *file)
318 {
319         GError *err = NULL;
320         GKeyFile *keyfile;
321
322         keyfile = g_key_file_new();
323
324         g_key_file_set_list_separator(keyfile, ',');
325
326         if (!g_key_file_load_from_file(keyfile, file, 0, &err)) {
327                 if (err->code != G_FILE_ERROR_NOENT) {
328                         connman_error("Parsing %s failed: %s", file,
329                                                                 err->message);
330                 }
331
332                 g_error_free(err);
333                 g_key_file_free(keyfile);
334                 return NULL;
335         }
336
337         return keyfile;
338 }
339
340 static uint *parse_service_types(char **str_list, gsize len)
341 {
342         unsigned int *type_list;
343         int i, j;
344         enum connman_service_type type;
345
346         type_list = g_try_new0(unsigned int, len + 1);
347         if (!type_list)
348                 return NULL;
349
350         i = 0;
351         j = 0;
352         while (str_list[i]) {
353                 type = __connman_service_string2type(str_list[i]);
354
355                 if (type != CONNMAN_SERVICE_TYPE_UNKNOWN) {
356                         type_list[j] = type;
357                         j += 1;
358                 }
359                 i += 1;
360         }
361
362         type_list[j] = CONNMAN_SERVICE_TYPE_UNKNOWN;
363
364         return type_list;
365 }
366
367 static char **parse_fallback_nameservers(char **nameservers, gsize len)
368 {
369         char **servers;
370         int i, j;
371
372         servers = g_try_new0(char *, len + 1);
373         if (!servers)
374                 return NULL;
375
376         i = 0;
377         j = 0;
378         while (nameservers[i]) {
379                 if (connman_inet_check_ipaddress(nameservers[i]) > 0) {
380                         servers[j] = g_strdup(nameservers[i]);
381                         j += 1;
382                 }
383                 i += 1;
384         }
385
386         return servers;
387 }
388
389 static void check_config(GKeyFile *config)
390 {
391         char **keys;
392         int j;
393
394         if (!config)
395                 return;
396
397         keys = g_key_file_get_groups(config, NULL);
398
399         for (j = 0; keys && keys[j]; j++) {
400 #if defined TIZEN_EXT
401                 if (g_strcmp0(keys[j], "General") != 0 &&
402                         g_strcmp0(keys[j], "INS") != 0)
403 #else
404                 if (g_strcmp0(keys[j], "General") != 0)
405 #endif
406                         connman_warn("Unknown group %s in %s",
407                                                 keys[j], MAINFILE);
408         }
409
410         g_strfreev(keys);
411
412         keys = g_key_file_get_keys(config, "General", NULL, NULL);
413
414         for (j = 0; keys && keys[j]; j++) {
415                 bool found;
416                 int i;
417
418                 found = false;
419                 for (i = 0; supported_options[i]; i++) {
420                         if (g_strcmp0(keys[j], supported_options[i]) == 0) {
421                                 found = true;
422                                 break;
423                         }
424                 }
425                 if (!found && !supported_options[i])
426                         connman_warn("Unknown option %s in %s",
427                                                 keys[j], MAINFILE);
428         }
429
430         g_strfreev(keys);
431
432 #if defined TIZEN_EXT
433         keys = g_key_file_get_keys(config, "INS", NULL, NULL);
434
435         for (j = 0; keys && keys[j]; j++) {
436                 bool found;
437                 int i;
438
439                 found = false;
440                 for (i = 0; supported_ins_options[i]; i++) {
441                         if (g_strcmp0(keys[j], supported_ins_options[i]) == 0) {
442                                 found = true;
443                                 break;
444                         }
445                 }
446                 if (!found && !supported_ins_options[i])
447                         connman_warn("Unknown option %s in %s",
448                                                 keys[j], MAINFILE);
449         }
450
451         g_strfreev(keys);
452 #endif
453 }
454
455 #if defined TIZEN_EXT
456 static void check_Tizen_INS_configuration(GKeyFile *config)
457 {
458         GError *error = NULL;
459         char *ins_preferred_freq_bssid;
460         char *ins_preferred_freq;
461         char **ins_security_priority;
462         bool boolean;
463         int integer;
464         gsize len;
465
466         ins_preferred_freq_bssid = __connman_config_get_string(config, "INS",
467                                         CONF_INS_PREFERRED_FREQ_BSSID, &error);
468         if (!error)
469                 connman_ins_settings.ins_preferred_freq_bssid = ins_preferred_freq_bssid;
470
471         g_clear_error(&error);
472
473         integer = g_key_file_get_integer(config, "INS",
474                         CONF_INS_PREFERRED_FREQ_BSSID_SCORE, &error);
475         if (!error && integer >= 0)
476                 connman_ins_settings.ins_preferred_freq_bssid_score = integer;
477
478         g_clear_error(&error);
479
480         boolean = __connman_config_get_bool(config, "INS",
481                         CONF_INS_LAST_CONNECTED_BSSID, &error);
482         if (!error)
483                 connman_ins_settings.ins_last_connected_bssid = boolean;
484
485         g_clear_error(&error);
486
487         integer = g_key_file_get_integer(config, "INS",
488                         CONF_INS_LAST_CONNECTED_BSSID_SCORE, &error);
489         if (!error && integer >= 0)
490                 connman_ins_settings.ins_last_connected_bssid_score = integer;
491
492         g_clear_error(&error);
493
494         boolean = __connman_config_get_bool(config, "INS",
495                         CONF_INS_ASSOC_REJECT, &error);
496         if (!error)
497                 connman_ins_settings.ins_assoc_reject = boolean;
498
499         g_clear_error(&error);
500
501         integer = g_key_file_get_integer(config, "INS",
502                         CONF_INS_ASSOC_REJECT_SCORE, &error);
503         if (!error && integer >= 0)
504                 connman_ins_settings.ins_assoc_reject_score = integer;
505
506         g_clear_error(&error);
507
508         boolean = __connman_config_get_bool(config, "INS",
509                         CONF_INS_SIGNAL_BSSID, &error);
510         if (!error)
511                 connman_ins_settings.ins_signal_bssid = boolean;
512
513         g_clear_error(&error);
514
515         boolean = __connman_config_get_bool(config, "INS",
516                         CONF_INS_LAST_USER_SELECTION, &error);
517         if (!error)
518                 connman_ins_settings.ins_last_user_selection = boolean;
519
520         g_clear_error(&error);
521
522         integer = g_key_file_get_integer(config, "INS",
523                         CONF_INS_LAST_USER_SELECTION_TIME, &error);
524         if (!error && integer >= 0)
525                 connman_ins_settings.ins_last_user_selection_time = integer;
526
527         g_clear_error(&error);
528
529         integer = g_key_file_get_integer(config, "INS",
530                         CONF_INS_LAST_USER_SELECTION_SCORE, &error);
531         if (!error && integer >= 0)
532                 connman_ins_settings.ins_last_user_selection_score = integer;
533
534         g_clear_error(&error);
535
536         boolean = __connman_config_get_bool(config, "INS",
537                         CONF_INS_LAST_CONNECTED, &error);
538         if (!error)
539                 connman_ins_settings.ins_last_connected = boolean;
540
541         g_clear_error(&error);
542
543         integer = g_key_file_get_integer(config, "INS",
544                         CONF_INS_LAST_CONNECTED_SCORE, &error);
545         if (!error && integer >= 0)
546                 connman_ins_settings.ins_last_connected_score = integer;
547
548         g_clear_error(&error);
549
550         ins_preferred_freq = __connman_config_get_string(config, "INS",
551                                         CONF_INS_PREFERRED_FREQ, &error);
552         if (!error)
553                 connman_ins_settings.ins_preferred_freq = ins_preferred_freq;
554
555         g_clear_error(&error);
556
557         integer = g_key_file_get_integer(config, "INS",
558                         CONF_INS_PREFERRED_FREQ_SCORE, &error);
559         if (!error && integer >= 0)
560                 connman_ins_settings.ins_preferred_freq_score = integer;
561
562         g_clear_error(&error);
563
564         ins_security_priority = g_key_file_get_string_list(config, "INS",
565                         CONF_INS_SECURITY_PRIORITY, &len, &error);
566
567         if (error == NULL) {
568                 connman_ins_settings.ins_security_priority = ins_security_priority;
569                 connman_ins_settings.ins_security_priority_count = len;
570         }
571
572         g_clear_error(&error);
573
574         integer = g_key_file_get_integer(config, "INS",
575                         CONF_INS_SECURITY_PRIORITY_SCORE, &error);
576         if (!error && integer >= 0)
577                 connman_ins_settings.ins_security_priority_score = integer;
578
579         g_clear_error(&error);
580
581         boolean = __connman_config_get_bool(config, "INS",
582                         CONF_INS_SIGNAL, &error);
583         if (!error)
584                 connman_ins_settings.ins_signal = boolean;
585
586         g_clear_error(&error);
587
588         boolean = __connman_config_get_bool(config, "INS",
589                         CONF_INS_INTERNET, &error);
590         if (!error)
591                 connman_ins_settings.ins_internet = boolean;
592
593         g_clear_error(&error);
594
595         integer = g_key_file_get_integer(config, "INS",
596                         CONF_INS_INTERNET_SCORE, &error);
597         if (!error && integer >= 0)
598                 connman_ins_settings.ins_internet_score = integer;
599
600         g_clear_error(&error);
601
602         integer = g_key_file_get_integer(config, "INS",
603                         CONF_INS_SIGNAL_LEVEL3_5GHZ, &error);
604         if (!error)
605                 connman_ins_settings.ins_signal_level3_5ghz = integer;
606
607         g_clear_error(&error);
608
609         integer = g_key_file_get_integer(config, "INS",
610                         CONF_INS_SIGNAL_LEVEL3_24GHZ, &error);
611         if (!error)
612                 connman_ins_settings.ins_signal_level3_24ghz = integer;
613
614         g_clear_error(&error);
615 }
616
617 static void check_Tizen_configuration(GKeyFile *config)
618 {
619         GError *error = NULL;
620         char **cellular_interfaces;
621         char *global_nameserver;
622         char *default_wifi_ifname;
623         bool boolean;
624         gsize len;
625
626         cellular_interfaces = g_key_file_get_string_list(config, "General",
627                         CONF_CELLULAR_INTERFACE, &len, &error);
628
629         if (error == NULL)
630                 connman_settings.cellular_interfaces = cellular_interfaces;
631
632         g_clear_error(&error);
633
634         boolean = __connman_config_get_bool(config, "General",
635                         CONF_TIZEN_TV_EXT, &error);
636         if (!error)
637                 connman_settings.tizen_tv_extension = boolean;
638
639         g_clear_error(&error);
640
641         boolean = __connman_config_get_bool(config, "General",
642                         CONF_ENABLE_AUTO_IP, &error);
643         if (!error)
644                 connman_settings.auto_ip = boolean;
645
646         g_clear_error(&error);
647
648         global_nameserver = __connman_config_get_string(config, "General",
649                                         CONF_GLOBAL_NAMESERVER, &error);
650         if (!error)
651                 connman_settings.global_nameserver = global_nameserver;
652
653         g_clear_error(&error);
654
655         boolean = __connman_config_get_bool(config, "General",
656                         CONF_CONNMAN_SUPPLICANT_DEBUG, &error);
657         if (!error)
658                 connman_settings.supplicant_debug = boolean;
659
660         g_clear_error(&error);
661
662         default_wifi_ifname = __connman_config_get_string(config, "General",
663                         CONF_CONNMAN_WIFI_DEF_IFNAME, &error);
664         if (!error)
665                 connman_settings.def_wifi_ifname = default_wifi_ifname;
666
667         g_clear_error(&error);
668
669         check_Tizen_INS_configuration(config);
670 }
671
672 static void set_nofile_inc(void)
673 {
674         int err;
675         struct rlimit rlim;
676
677         rlim.rlim_cur = 8192;
678         rlim.rlim_max = 8192;
679
680         err = setrlimit(RLIMIT_NOFILE, &rlim);
681         if (err)
682                 DBG("fail to increase FILENO err(%d)", err);
683
684         return;
685 }
686 #endif
687
688 static void parse_config(GKeyFile *config)
689 {
690         GError *error = NULL;
691         bool boolean;
692         char **timeservers;
693         char **interfaces;
694         char **str_list;
695         char **tethering;
696         char *vendor_class_id;
697         gsize len;
698         int timeout;
699
700         if (!config) {
701                 connman_settings.auto_connect =
702                         parse_service_types(default_auto_connect, CONF_ARRAY_SIZE(default_auto_connect));
703                 connman_settings.favorite_techs =
704                         parse_service_types(default_favorite_techs, CONF_ARRAY_SIZE(default_favorite_techs));
705                 connman_settings.blacklisted_interfaces =
706                         g_strdupv(default_blacklist);
707                 return;
708         }
709
710         DBG("parsing %s", MAINFILE);
711
712         boolean = g_key_file_get_boolean(config, "General",
713                                                 CONF_BG_SCAN, &error);
714         if (!error)
715                 connman_settings.bg_scan = boolean;
716
717         g_clear_error(&error);
718
719         timeservers = __connman_config_get_string_list(config, "General",
720                                         CONF_PREF_TIMESERVERS, NULL, &error);
721         if (!error)
722                 connman_settings.pref_timeservers = timeservers;
723
724         g_clear_error(&error);
725
726         str_list = __connman_config_get_string_list(config, "General",
727                         CONF_AUTO_CONNECT_TECHS, &len, &error);
728
729         if (!error)
730                 connman_settings.auto_connect =
731                         parse_service_types(str_list, len);
732         else
733                 connman_settings.auto_connect =
734                         parse_service_types(default_auto_connect, CONF_ARRAY_SIZE(default_auto_connect));
735
736         g_clear_error(&error);
737
738         str_list = __connman_config_get_string_list(config, "General",
739                         CONF_FAVORITE_TECHS, &len, &error);
740
741         if (!error)
742                 connman_settings.favorite_techs =
743                         parse_service_types(str_list, len);
744         else
745                 connman_settings.favorite_techs =
746                         parse_service_types(default_favorite_techs, CONF_ARRAY_SIZE(default_favorite_techs));
747
748         g_strfreev(str_list);
749
750         g_clear_error(&error);
751
752         str_list = __connman_config_get_string_list(config, "General",
753                         CONF_PREFERRED_TECHS, &len, &error);
754
755         if (!error)
756                 connman_settings.preferred_techs =
757                         parse_service_types(str_list, len);
758
759         g_strfreev(str_list);
760
761         g_clear_error(&error);
762
763         str_list = __connman_config_get_string_list(config, "General",
764                         CONF_ALWAYS_CONNECTED_TECHS, &len, &error);
765
766         if (!error)
767                 connman_settings.always_connected_techs =
768                         parse_service_types(str_list, len);
769
770         g_strfreev(str_list);
771
772         g_clear_error(&error);
773
774         str_list = __connman_config_get_string_list(config, "General",
775                         CONF_FALLBACK_NAMESERVERS, &len, &error);
776
777         if (!error)
778                 connman_settings.fallback_nameservers =
779                         parse_fallback_nameservers(str_list, len);
780
781         g_strfreev(str_list);
782
783         g_clear_error(&error);
784
785         timeout = g_key_file_get_integer(config, "General",
786                         CONF_TIMEOUT_INPUTREQ, &error);
787         if (!error && timeout >= 0)
788                 connman_settings.timeout_inputreq = timeout * 1000;
789
790         g_clear_error(&error);
791
792         timeout = g_key_file_get_integer(config, "General",
793                         CONF_TIMEOUT_BROWSERLAUNCH, &error);
794         if (!error && timeout >= 0)
795                 connman_settings.timeout_browserlaunch = timeout * 1000;
796
797         g_clear_error(&error);
798
799         interfaces = __connman_config_get_string_list(config, "General",
800                         CONF_BLACKLISTED_INTERFACES, &len, &error);
801
802         if (!error)
803                 connman_settings.blacklisted_interfaces = interfaces;
804         else
805                 connman_settings.blacklisted_interfaces =
806                         g_strdupv(default_blacklist);
807
808         g_clear_error(&error);
809
810         boolean = __connman_config_get_bool(config, "General",
811                                         CONF_ALLOW_HOSTNAME_UPDATES,
812                                         &error);
813         if (!error)
814                 connman_settings.allow_hostname_updates = boolean;
815
816         g_clear_error(&error);
817
818         boolean = __connman_config_get_bool(config, "General",
819                                         CONF_ALLOW_DOMAINNAME_UPDATES,
820                                         &error);
821         if (!error)
822                 connman_settings.allow_domainname_updates = boolean;
823
824         g_clear_error(&error);
825
826         boolean = __connman_config_get_bool(config, "General",
827                         CONF_SINGLE_TECH, &error);
828         if (!error)
829                 connman_settings.single_tech = boolean;
830
831         g_clear_error(&error);
832
833         tethering = __connman_config_get_string_list(config, "General",
834                         CONF_TETHERING_TECHNOLOGIES, &len, &error);
835
836         if (!error)
837                 connman_settings.tethering_technologies = tethering;
838
839         g_clear_error(&error);
840
841         boolean = __connman_config_get_bool(config, "General",
842                                         CONF_PERSISTENT_TETHERING_MODE,
843                                         &error);
844         if (!error)
845                 connman_settings.persistent_tethering_mode = boolean;
846
847         g_clear_error(&error);
848
849         boolean = __connman_config_get_bool(config, "General",
850                                         CONF_ENABLE_6TO4, &error);
851         if (!error)
852                 connman_settings.enable_6to4 = boolean;
853
854         g_clear_error(&error);
855
856         vendor_class_id = __connman_config_get_string(config, "General",
857                                         CONF_VENDOR_CLASS_ID, &error);
858         if (!error)
859                 connman_settings.vendor_class_id = vendor_class_id;
860
861         g_clear_error(&error);
862
863         boolean = __connman_config_get_bool(config, "General",
864                                         CONF_ENABLE_ONLINE_CHECK, &error);
865         if (!error) {
866                 connman_settings.enable_online_check = boolean;
867                 if (!boolean)
868                         connman_info("Online check disabled by main config.");
869         }
870
871         g_clear_error(&error);
872
873         boolean = __connman_config_get_bool(config, "General",
874                                 CONF_AUTO_CONNECT_ROAMING_SERVICES, &error);
875         if (!error)
876                 connman_settings.auto_connect_roaming_services = boolean;
877
878         g_clear_error(&error);
879
880         boolean = __connman_config_get_bool(config, "General", CONF_ACD, &error);
881         if (!error)
882                 connman_settings.acd = boolean;
883
884         g_clear_error(&error);
885
886         boolean = __connman_config_get_bool(config, "General",
887                                 CONF_USE_GATEWAYS_AS_TIMESERVERS, &error);
888         if (!error)
889                 connman_settings.use_gateways_as_timeservers = boolean;
890
891         g_clear_error(&error);
892
893 #if defined TIZEN_EXT
894         check_Tizen_configuration(config);
895 #endif
896 }
897
898 static int config_init(const char *file)
899 {
900         GKeyFile *config;
901
902 #if defined TIZEN_EXT
903         set_nofile_inc();
904 #endif
905         config = load_config(file);
906         check_config(config);
907         parse_config(config);
908         if (config)
909                 g_key_file_free(config);
910
911         return 0;
912 }
913
914 static GMainLoop *main_loop = NULL;
915
916 static unsigned int __terminated = 0;
917
918 static gboolean signal_handler(GIOChannel *channel, GIOCondition cond,
919                                                         gpointer user_data)
920 {
921         struct signalfd_siginfo si;
922         ssize_t result;
923         int fd;
924
925         if (cond & (G_IO_NVAL | G_IO_ERR | G_IO_HUP))
926                 return FALSE;
927
928         fd = g_io_channel_unix_get_fd(channel);
929
930         result = read(fd, &si, sizeof(si));
931         if (result != sizeof(si))
932                 return FALSE;
933
934         switch (si.ssi_signo) {
935         case SIGINT:
936         case SIGTERM:
937                 if (__terminated == 0) {
938                         connman_info("Terminating");
939                         g_main_loop_quit(main_loop);
940                 }
941
942                 __terminated = 1;
943                 break;
944         }
945
946         return TRUE;
947 }
948
949 static guint setup_signalfd(void)
950 {
951         GIOChannel *channel;
952         guint source;
953         sigset_t mask;
954         int fd;
955
956         sigemptyset(&mask);
957         sigaddset(&mask, SIGINT);
958         sigaddset(&mask, SIGTERM);
959
960         if (sigprocmask(SIG_BLOCK, &mask, NULL) < 0) {
961                 perror("Failed to set signal mask");
962                 return 0;
963         }
964
965         fd = signalfd(-1, &mask, 0);
966         if (fd < 0) {
967                 perror("Failed to create signal descriptor");
968                 return 0;
969         }
970
971         channel = g_io_channel_unix_new(fd);
972
973         g_io_channel_set_close_on_unref(channel, TRUE);
974         g_io_channel_set_encoding(channel, NULL, NULL);
975         g_io_channel_set_buffered(channel, FALSE);
976
977         source = g_io_add_watch(channel,
978                                 G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL,
979                                 signal_handler, NULL);
980
981         g_io_channel_unref(channel);
982
983         return source;
984 }
985
986 static void disconnect_callback(DBusConnection *conn, void *user_data)
987 {
988         connman_error("D-Bus disconnect");
989
990         g_main_loop_quit(main_loop);
991 }
992
993 static gchar *option_config = NULL;
994 static gchar *option_debug = NULL;
995 static gchar *option_device = NULL;
996 static gchar *option_plugin = NULL;
997 static gchar *option_nodevice = NULL;
998 static gchar *option_noplugin = NULL;
999 static gchar *option_wifi = NULL;
1000 static gboolean option_detach = TRUE;
1001 static gboolean option_dnsproxy = TRUE;
1002 static gboolean option_backtrace = TRUE;
1003 static gboolean option_version = FALSE;
1004
1005 static bool parse_debug(const char *key, const char *value,
1006                                         gpointer user_data, GError **error)
1007 {
1008         if (value) {
1009                 if (option_debug) {
1010                         char *prev = option_debug;
1011
1012                         option_debug = g_strconcat(prev, ",", value, NULL);
1013                         g_free(prev);
1014                 } else {
1015                         option_debug = g_strdup(value);
1016                 }
1017         } else {
1018                 g_free(option_debug);
1019                 option_debug = g_strdup("*");
1020         }
1021
1022         return true;
1023 }
1024
1025 static bool parse_noplugin(const char *key, const char *value,
1026                                         gpointer user_data, GError **error)
1027 {
1028         if (option_noplugin) {
1029                 char *prev = option_noplugin;
1030
1031                 option_noplugin = g_strconcat(prev, ",", value, NULL);
1032                 g_free(prev);
1033         } else {
1034                 option_noplugin = g_strdup(value);
1035         }
1036
1037         return true;
1038 }
1039
1040 static GOptionEntry options[] = {
1041         { "config", 'c', 0, G_OPTION_ARG_STRING, &option_config,
1042                                 "Load the specified configuration file "
1043                                 "instead of " CONFIGMAINFILE, "FILE" },
1044         { "debug", 'd', G_OPTION_FLAG_OPTIONAL_ARG,
1045                                 G_OPTION_ARG_CALLBACK, parse_debug,
1046                                 "Specify debug options to enable", "DEBUG" },
1047         { "device", 'i', 0, G_OPTION_ARG_STRING, &option_device,
1048                         "Specify networking devices or interfaces", "DEV,..." },
1049         { "nodevice", 'I', 0, G_OPTION_ARG_STRING, &option_nodevice,
1050                         "Specify networking interfaces to ignore", "DEV,..." },
1051         { "plugin", 'p', 0, G_OPTION_ARG_STRING, &option_plugin,
1052                                 "Specify plugins to load", "NAME,..." },
1053         { "noplugin", 'P', 0, G_OPTION_ARG_CALLBACK, &parse_noplugin,
1054                                 "Specify plugins not to load", "NAME,..." },
1055         { "wifi", 'W', 0, G_OPTION_ARG_STRING, &option_wifi,
1056                                 "Specify driver for WiFi/Supplicant", "NAME" },
1057         { "nodaemon", 'n', G_OPTION_FLAG_REVERSE,
1058                                 G_OPTION_ARG_NONE, &option_detach,
1059                                 "Don't fork daemon to background" },
1060         { "nodnsproxy", 'r', G_OPTION_FLAG_REVERSE,
1061                                 G_OPTION_ARG_NONE, &option_dnsproxy,
1062                                 "Don't support DNS resolving" },
1063         { "nobacktrace", 0, G_OPTION_FLAG_REVERSE,
1064                                 G_OPTION_ARG_NONE, &option_backtrace,
1065                                 "Don't print out backtrace information" },
1066         { "version", 'v', 0, G_OPTION_ARG_NONE, &option_version,
1067                                 "Show version information and exit" },
1068         { NULL },
1069 };
1070
1071 const char *connman_option_get_string(const char *key)
1072 {
1073         if (g_str_equal(key, CONF_VENDOR_CLASS_ID))
1074                 return connman_settings.vendor_class_id;
1075
1076         if (g_strcmp0(key, "wifi") == 0) {
1077                 if (!option_wifi)
1078                         return "nl80211,wext";
1079                 else
1080                         return option_wifi;
1081         }
1082
1083 #if defined TIZEN_EXT
1084         if (g_str_equal(key, CONF_GLOBAL_NAMESERVER))
1085                 return connman_settings.global_nameserver;
1086
1087         if (g_str_equal(key, CONF_INS_PREFERRED_FREQ_BSSID))
1088                 return connman_ins_settings.ins_preferred_freq_bssid;
1089
1090         if (g_str_equal(key, CONF_INS_PREFERRED_FREQ))
1091                 return connman_ins_settings.ins_preferred_freq;
1092
1093         if (g_str_equal(key, CONF_CONNMAN_WIFI_DEF_IFNAME))
1094                 return connman_settings.def_wifi_ifname;
1095 #endif
1096         return NULL;
1097 }
1098
1099 bool connman_setting_get_bool(const char *key)
1100 {
1101         if (g_str_equal(key, CONF_BG_SCAN))
1102                 return connman_settings.bg_scan;
1103
1104         if (g_str_equal(key, CONF_ALLOW_HOSTNAME_UPDATES))
1105                 return connman_settings.allow_hostname_updates;
1106
1107         if (g_str_equal(key, CONF_ALLOW_DOMAINNAME_UPDATES))
1108                 return connman_settings.allow_domainname_updates;
1109
1110         if (g_str_equal(key, CONF_SINGLE_TECH))
1111                 return connman_settings.single_tech;
1112
1113         if (g_str_equal(key, CONF_PERSISTENT_TETHERING_MODE))
1114                 return connman_settings.persistent_tethering_mode;
1115
1116         if (g_str_equal(key, CONF_ENABLE_6TO4))
1117                 return connman_settings.enable_6to4;
1118
1119         if (g_str_equal(key, CONF_ENABLE_ONLINE_CHECK))
1120                 return connman_settings.enable_online_check;
1121
1122         if (g_str_equal(key, CONF_AUTO_CONNECT_ROAMING_SERVICES))
1123                 return connman_settings.auto_connect_roaming_services;
1124
1125         if (g_str_equal(key, CONF_ACD))
1126                 return connman_settings.acd;
1127
1128         if (g_str_equal(key, CONF_USE_GATEWAYS_AS_TIMESERVERS))
1129                 return connman_settings.use_gateways_as_timeservers;
1130
1131 #if defined TIZEN_EXT
1132         if (g_str_equal(key, CONF_ENABLE_AUTO_IP))
1133                 return connman_settings.auto_ip;
1134
1135         if (g_str_equal(key, CONF_CONNMAN_SUPPLICANT_DEBUG))
1136                 return connman_settings.supplicant_debug;
1137 #endif
1138
1139 #if defined TIZEN_EXT
1140         if (g_str_equal(key, CONF_INS_LAST_CONNECTED_BSSID))
1141                 return connman_ins_settings.ins_last_connected_bssid;
1142
1143         if (g_str_equal(key, CONF_INS_ASSOC_REJECT))
1144                 return connman_ins_settings.ins_assoc_reject;
1145
1146         if (g_str_equal(key, CONF_INS_SIGNAL_BSSID))
1147                 return connman_ins_settings.ins_signal_bssid;
1148
1149         if (g_str_equal(key, CONF_INS_LAST_USER_SELECTION))
1150                 return connman_ins_settings.ins_last_user_selection;
1151
1152         if (g_str_equal(key, CONF_INS_LAST_CONNECTED))
1153                 return connman_ins_settings.ins_last_connected;
1154
1155         if (g_str_equal(key, CONF_INS_SIGNAL))
1156                 return connman_ins_settings.ins_signal;
1157
1158         if (g_str_equal(key, CONF_INS_INTERNET))
1159                 return connman_ins_settings.ins_internet;
1160 #endif
1161
1162         return false;
1163 }
1164
1165 #if defined TIZEN_EXT
1166 unsigned int connman_setting_get_uint(const char *key)
1167 {
1168         if (g_str_equal(key, CONF_INS_PREFERRED_FREQ_BSSID_SCORE))
1169                 return connman_ins_settings.ins_preferred_freq_bssid_score;
1170
1171         if (g_str_equal(key, CONF_INS_LAST_CONNECTED_BSSID_SCORE))
1172                 return connman_ins_settings.ins_last_connected_bssid_score;
1173
1174         if (g_str_equal(key, CONF_INS_ASSOC_REJECT_SCORE))
1175                 return connman_ins_settings.ins_assoc_reject_score;
1176
1177         if (g_str_equal(key, CONF_INS_LAST_USER_SELECTION_TIME))
1178                 return connman_ins_settings.ins_last_user_selection_time;
1179
1180         if (g_str_equal(key, CONF_INS_SECURITY_PRIORITY_COUNT))
1181                 return connman_ins_settings.ins_security_priority_count;
1182
1183         if (g_str_equal(key, CONF_INS_LAST_USER_SELECTION_SCORE))
1184                 return connman_ins_settings.ins_last_user_selection_score;
1185
1186         if (g_str_equal(key, CONF_INS_LAST_CONNECTED_SCORE))
1187                 return connman_ins_settings.ins_last_connected_score;
1188
1189         if (g_str_equal(key, CONF_INS_PREFERRED_FREQ_SCORE))
1190                 return connman_ins_settings.ins_preferred_freq_score;
1191
1192         if (g_str_equal(key, CONF_INS_SECURITY_PRIORITY_SCORE))
1193                 return connman_ins_settings.ins_security_priority_score;
1194
1195         if (g_str_equal(key, CONF_INS_INTERNET_SCORE))
1196                 return connman_ins_settings.ins_internet_score;
1197
1198         return 0;
1199 }
1200
1201 int connman_setting_get_int(const char *key)
1202 {
1203         if (g_str_equal(key, CONF_INS_SIGNAL_LEVEL3_5GHZ))
1204                 return connman_ins_settings.ins_signal_level3_5ghz;
1205
1206         if (g_str_equal(key, CONF_INS_SIGNAL_LEVEL3_24GHZ))
1207                 return connman_ins_settings.ins_signal_level3_24ghz;
1208
1209         return 0;
1210 }
1211 #endif
1212
1213 char **connman_setting_get_string_list(const char *key)
1214 {
1215         if (g_str_equal(key, CONF_PREF_TIMESERVERS))
1216                 return connman_settings.pref_timeservers;
1217
1218         if (g_str_equal(key, CONF_FALLBACK_NAMESERVERS))
1219                 return connman_settings.fallback_nameservers;
1220
1221         if (g_str_equal(key, CONF_BLACKLISTED_INTERFACES))
1222                 return connman_settings.blacklisted_interfaces;
1223
1224         if (g_str_equal(key, CONF_TETHERING_TECHNOLOGIES))
1225                 return connman_settings.tethering_technologies;
1226
1227 #if defined TIZEN_EXT
1228         if (g_str_equal(key, CONF_CELLULAR_INTERFACE))
1229                 return connman_settings.cellular_interfaces;
1230 #endif
1231
1232 #if defined TIZEN_EXT
1233         if (g_str_equal(key, CONF_INS_SECURITY_PRIORITY))
1234                 return connman_ins_settings.ins_security_priority;
1235 #endif
1236
1237         return NULL;
1238 }
1239
1240 unsigned int *connman_setting_get_uint_list(const char *key)
1241 {
1242         if (g_str_equal(key, CONF_AUTO_CONNECT_TECHS))
1243                 return connman_settings.auto_connect;
1244
1245         if (g_str_equal(key, CONF_FAVORITE_TECHS))
1246                 return connman_settings.favorite_techs;
1247
1248         if (g_str_equal(key, CONF_PREFERRED_TECHS))
1249                 return connman_settings.preferred_techs;
1250
1251         if (g_str_equal(key, CONF_ALWAYS_CONNECTED_TECHS))
1252                 return connman_settings.always_connected_techs;
1253
1254         return NULL;
1255 }
1256
1257 unsigned int connman_timeout_input_request(void)
1258 {
1259         return connman_settings.timeout_inputreq;
1260 }
1261
1262 unsigned int connman_timeout_browser_launch(void)
1263 {
1264         return connman_settings.timeout_browserlaunch;
1265 }
1266
1267 int main(int argc, char *argv[])
1268 {
1269         GOptionContext *context;
1270         GError *error = NULL;
1271         DBusConnection *conn;
1272         DBusError err;
1273         guint signal;
1274
1275         context = g_option_context_new(NULL);
1276         g_option_context_add_main_entries(context, options, NULL);
1277
1278         if (!g_option_context_parse(context, &argc, &argv, &error)) {
1279                 if (error) {
1280                         g_printerr("%s\n", error->message);
1281                         g_error_free(error);
1282                 } else
1283                         g_printerr("An unknown error occurred\n");
1284                 exit(1);
1285         }
1286
1287         g_option_context_free(context);
1288
1289         if (option_version) {
1290                 printf("%s\n", VERSION);
1291                 exit(0);
1292         }
1293
1294         if (option_detach) {
1295                 if (daemon(0, 0)) {
1296                         perror("Can't start daemon");
1297                         exit(1);
1298                 }
1299         }
1300
1301         if (mkdir(STORAGEDIR, S_IRUSR | S_IWUSR | S_IXUSR |
1302                                 S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH) < 0) {
1303                 if (errno != EEXIST)
1304                         perror("Failed to create storage directory");
1305         }
1306
1307         umask(0077);
1308
1309         main_loop = g_main_loop_new(NULL, FALSE);
1310
1311         signal = setup_signalfd();
1312
1313         dbus_error_init(&err);
1314
1315         conn = g_dbus_setup_bus(DBUS_BUS_SYSTEM, CONNMAN_SERVICE, &err);
1316         if (!conn) {
1317                 if (dbus_error_is_set(&err)) {
1318                         fprintf(stderr, "%s\n", err.message);
1319                         dbus_error_free(&err);
1320                 } else
1321                         fprintf(stderr, "Can't register with system bus\n");
1322                 exit(1);
1323         }
1324
1325         g_dbus_set_disconnect_function(conn, disconnect_callback, NULL, NULL);
1326
1327         __connman_log_init(argv[0], option_debug, option_detach,
1328                         option_backtrace, "Connection Manager", VERSION);
1329
1330         __connman_dbus_init(conn);
1331
1332         if (!option_config)
1333                 config_init(CONFIGMAINFILE);
1334         else
1335                 config_init(option_config);
1336
1337         __connman_util_init();
1338         __connman_inotify_init();
1339         __connman_technology_init();
1340         __connman_notifier_init();
1341         __connman_agent_init();
1342         __connman_service_init();
1343         __connman_peer_service_init();
1344         __connman_peer_init();
1345 #if defined TIZEN_EXT_WIFI_MESH
1346         __connman_mesh_init();
1347 #endif /* TIZEN_EXT_WIFI_MESH */
1348         __connman_provider_init();
1349         __connman_network_init();
1350         __connman_config_init();
1351         __connman_device_init(option_device, option_nodevice);
1352
1353         __connman_ippool_init();
1354         __connman_firewall_init();
1355         __connman_nat_init();
1356         __connman_tethering_init();
1357         __connman_counter_init();
1358         __connman_manager_init();
1359         __connman_stats_init();
1360         __connman_clock_init();
1361
1362         __connman_ipconfig_init();
1363         __connman_rtnl_init();
1364         __connman_task_init();
1365         __connman_proxy_init();
1366         __connman_detect_init();
1367         __connman_session_init();
1368         __connman_timeserver_init();
1369         __connman_connection_init();
1370
1371         __connman_plugin_init(option_plugin, option_noplugin);
1372
1373         __connman_resolver_init(option_dnsproxy);
1374         __connman_rtnl_start();
1375         __connman_dhcp_init();
1376         __connman_dhcpv6_init();
1377         __connman_wpad_init();
1378         __connman_wispr_init();
1379 #if !defined TIZEN_EXT
1380         __connman_rfkill_init();
1381         __connman_machine_init();
1382 #endif
1383
1384         g_free(option_config);
1385         g_free(option_device);
1386         g_free(option_plugin);
1387         g_free(option_nodevice);
1388         g_free(option_noplugin);
1389
1390         g_main_loop_run(main_loop);
1391
1392         g_source_remove(signal);
1393
1394 #if !defined TIZEN_EXT
1395         __connman_machine_cleanup();
1396         __connman_rfkill_cleanup();
1397 #endif
1398         __connman_wispr_cleanup();
1399         __connman_wpad_cleanup();
1400         __connman_dhcpv6_cleanup();
1401         __connman_session_cleanup();
1402         __connman_plugin_cleanup();
1403         __connman_provider_cleanup();
1404         __connman_connection_cleanup();
1405         __connman_timeserver_cleanup();
1406         __connman_detect_cleanup();
1407         __connman_proxy_cleanup();
1408         __connman_task_cleanup();
1409         __connman_rtnl_cleanup();
1410         __connman_resolver_cleanup();
1411
1412         __connman_clock_cleanup();
1413         __connman_stats_cleanup();
1414         __connman_config_cleanup();
1415         __connman_manager_cleanup();
1416         __connman_counter_cleanup();
1417         __connman_tethering_cleanup();
1418         __connman_nat_cleanup();
1419         __connman_firewall_cleanup();
1420         __connman_peer_service_cleanup();
1421         __connman_peer_cleanup();
1422 #if defined TIZEN_EXT_WIFI_MESH
1423         __connman_mesh_cleanup();
1424 #endif /* TIZEN_EXT_WIFI_MESH */
1425         __connman_ippool_cleanup();
1426         __connman_device_cleanup();
1427         __connman_network_cleanup();
1428         __connman_dhcp_cleanup();
1429         __connman_service_cleanup();
1430         __connman_agent_cleanup();
1431         __connman_ipconfig_cleanup();
1432         __connman_notifier_cleanup();
1433         __connman_technology_cleanup();
1434         __connman_inotify_cleanup();
1435
1436         __connman_util_cleanup();
1437         __connman_dbus_cleanup();
1438
1439         __connman_log_cleanup(option_backtrace);
1440
1441         dbus_connection_unref(conn);
1442
1443         g_main_loop_unref(main_loop);
1444
1445         if (connman_settings.pref_timeservers)
1446                 g_strfreev(connman_settings.pref_timeservers);
1447
1448         g_free(connman_settings.auto_connect);
1449         g_free(connman_settings.favorite_techs);
1450         g_free(connman_settings.preferred_techs);
1451         g_strfreev(connman_settings.fallback_nameservers);
1452         g_strfreev(connman_settings.blacklisted_interfaces);
1453         g_strfreev(connman_settings.tethering_technologies);
1454
1455 #if defined TIZEN_EXT
1456         g_free(connman_ins_settings.ins_preferred_freq_bssid);
1457         g_free(connman_ins_settings.ins_preferred_freq);
1458         if (connman_ins_settings.ins_security_priority)
1459                 g_strfreev(connman_ins_settings.ins_security_priority);
1460 #endif
1461
1462         g_free(option_debug);
1463         g_free(option_wifi);
1464
1465         return 0;
1466 }