5 * Copyright (C) 2012-2013 Intel Corporation. All rights reserved.
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
36 #include "dbus_helpers.h"
42 static DBusConnection *connection;
44 struct connman_option {
50 static char *ipv4[] = {
58 static char *ipv6[] = {
66 static int cmd_help(char *args[], int num, struct connman_option *options);
68 static bool check_dbus_name(const char *name)
71 * Valid dbus chars should be [A-Z][a-z][0-9]_
72 * and should not start with number.
76 if (name == NULL || (name[0] >= '0' && name[0] <= '9'))
79 for (i = 0; i < strlen(name); i++)
80 if (!((name[i] >= 'A' && name[i] <= 'Z') ||
81 (name[i] >= 'a' && name[i] <= 'z') ||
82 (name[i] >= '0' && name[i] <= '9') ||
89 static int parse_boolean(char *arg)
94 if (strcasecmp(arg, "no") == 0 ||
95 strcasecmp(arg, "false") == 0 ||
96 strcasecmp(arg, "off" ) == 0 ||
97 strcasecmp(arg, "disable" ) == 0 ||
98 strcasecmp(arg, "n") == 0 ||
99 strcasecmp(arg, "f") == 0 ||
100 strcasecmp(arg, "0") == 0)
103 if (strcasecmp(arg, "yes") == 0 ||
104 strcasecmp(arg, "true") == 0 ||
105 strcasecmp(arg, "on") == 0 ||
106 strcasecmp(arg, "enable" ) == 0 ||
107 strcasecmp(arg, "y") == 0 ||
108 strcasecmp(arg, "t") == 0 ||
109 strcasecmp(arg, "1") == 0)
115 static int parse_args(char *arg, struct connman_option *options)
122 for (i = 0; options[i].name != NULL; i++) {
123 if (strcmp(options[i].name, arg) == 0 ||
124 (strncmp(arg, "--", 2) == 0 &&
125 strcmp(&arg[2], options[i].name) == 0))
126 return options[i].val;
132 static int enable_return(DBusMessageIter *iter, const char *error,
135 char *tech = user_data;
138 str = strrchr(tech, '/');
145 fprintf(stdout, "Enabled %s\n", str);
147 fprintf(stderr, "Error %s: %s\n", str, error);
154 static int cmd_enable(char *args[], int num, struct connman_option *options)
157 dbus_bool_t b = TRUE;
165 if (check_dbus_name(args[1]) == false)
168 if (strcmp(args[1], "offlinemode") == 0) {
169 tech = g_strdup(args[1]);
170 return __connmanctl_dbus_set_property(connection, "/",
171 "net.connman.Manager", enable_return, tech,
172 "OfflineMode", DBUS_TYPE_BOOLEAN, &b);
175 tech = g_strdup_printf("/net/connman/technology/%s", args[1]);
176 return __connmanctl_dbus_set_property(connection, tech,
177 "net.connman.Technology", enable_return, tech,
178 "Powered", DBUS_TYPE_BOOLEAN, &b);
181 static int disable_return(DBusMessageIter *iter, const char *error,
184 char *tech = user_data;
187 str = strrchr(tech, '/');
194 fprintf(stdout, "Disabled %s\n", str);
196 fprintf(stderr, "Error %s: %s\n", str, error);
203 static int cmd_disable(char *args[], int num, struct connman_option *options)
206 dbus_bool_t b = FALSE;
214 if (check_dbus_name(args[1]) == false)
217 if (strcmp(args[1], "offlinemode") == 0) {
218 tech = g_strdup(args[1]);
219 return __connmanctl_dbus_set_property(connection, "/",
220 "net.connman.Manager", disable_return, tech,
221 "OfflineMode", DBUS_TYPE_BOOLEAN, &b);
224 tech = g_strdup_printf("/net/connman/technology/%s", args[1]);
225 return __connmanctl_dbus_set_property(connection, tech,
226 "net.connman.Technology", disable_return, tech,
227 "Powered", DBUS_TYPE_BOOLEAN, &b);
230 static int state_print(DBusMessageIter *iter, const char *error,
233 DBusMessageIter entry;
236 fprintf(stderr, "Error: %s", error);
240 dbus_message_iter_recurse(iter, &entry);
241 __connmanctl_dbus_print(&entry, " ", " = ", "\n");
242 fprintf(stdout, "\n");
247 static int cmd_state(char *args[], int num, struct connman_option *options)
252 return __connmanctl_dbus_method_call(connection, "/",
253 "net.connman.Manager", "GetProperties",
254 state_print, NULL, DBUS_TYPE_INVALID);
257 static int services_list(DBusMessageIter *iter, const char *error,
261 __connmanctl_services_list(iter);
262 fprintf(stdout, "\n");
264 fprintf(stderr, "Error: %s\n", error);
270 static int services_properties(DBusMessageIter *iter, const char *error,
273 char *path = user_data;
275 DBusMessageIter dict;
278 fprintf(stdout, "%s\n", path);
280 dbus_message_iter_recurse(iter, &dict);
281 __connmanctl_dbus_print(&dict, " ", " = ", "\n");
283 fprintf(stdout, "\n");
286 str = strrchr(path, '/');
292 fprintf(stderr, "Error %s: %s\n", str, error);
300 static int cmd_services(char *args[], int num, struct connman_option *options)
302 char *service_name = NULL;
309 c = parse_args(args[1], options);
316 service_name = args[2];
321 service_name = args[1];
325 if (service_name == NULL) {
326 return __connmanctl_dbus_method_call(connection, "/",
327 "net.connman.Manager", "GetServices",
328 services_list, NULL, DBUS_TYPE_INVALID);
331 if (check_dbus_name(service_name) == false)
334 path = g_strdup_printf("/net/connman/service/%s", service_name);
335 return __connmanctl_dbus_method_call(connection, path,
336 "net.connman.Service", "GetProperties",
337 services_properties, path, DBUS_TYPE_INVALID);
340 static int technology_print(DBusMessageIter *iter, const char *error,
343 DBusMessageIter array;
346 fprintf(stderr, "Error: %s\n", error);
350 dbus_message_iter_recurse(iter, &array);
351 while (dbus_message_iter_get_arg_type(&array) == DBUS_TYPE_STRUCT) {
352 DBusMessageIter entry, dict;
355 dbus_message_iter_recurse(&array, &entry);
356 dbus_message_iter_get_basic(&entry, &path);
357 fprintf(stdout, "%s\n", path);
359 dbus_message_iter_next(&entry);
361 dbus_message_iter_recurse(&entry, &dict);
362 __connmanctl_dbus_print(&dict, " ", " = ", "\n");
363 fprintf(stdout, "\n");
365 dbus_message_iter_next(&array);
371 static int cmd_technologies(char *args[], int num,
372 struct connman_option *options)
377 return __connmanctl_dbus_method_call(connection, "/",
378 "net.connman.Manager", "GetTechnologies",
379 technology_print, NULL, DBUS_TYPE_INVALID);
382 struct tether_enable {
387 static int tether_set_return(DBusMessageIter *iter, const char *error,
390 struct tether_enable *tether = user_data;
393 str = strrchr(tether->path, '/');
400 fprintf(stdout, "%s tethering for %s\n",
401 tether->enable == TRUE ? "Enabled": "Disabled",
404 fprintf(stderr, "Error %s %s tethering: %s\n",
405 tether->enable == TRUE ?
406 "enabling": "disabling", str, error);
408 g_free(tether->path);
414 static int tether_set(char *technology, int set_tethering)
416 struct tether_enable *tether = g_new(struct tether_enable, 1);
418 switch(set_tethering) {
420 tether->enable = TRUE;
423 tether->enable = FALSE;
430 tether->path = g_strdup_printf("/net/connman/technology/%s",
433 return __connmanctl_dbus_set_property(connection, tether->path,
434 "net.connman.Technology", tether_set_return,
435 tether, "Tethering", DBUS_TYPE_BOOLEAN,
439 struct tether_properties {
441 int passphrase_result;
445 static int tether_update(struct tether_properties *tether)
447 printf("%d %d %d\n", tether->ssid_result, tether->passphrase_result,
448 tether->set_tethering);
450 if (tether->ssid_result == 0 && tether->passphrase_result == 0)
451 return tether_set("wifi", tether->set_tethering);
453 if (tether->ssid_result != -EINPROGRESS &&
454 tether->passphrase_result != -EINPROGRESS) {
462 static int tether_set_ssid_return(DBusMessageIter *iter, const char *error,
465 struct tether_properties *tether = user_data;
468 fprintf(stdout, "Wifi SSID set\n");
469 tether->ssid_result = 0;
471 fprintf(stderr, "Error setting wifi SSID: %s\n", error);
472 tether->ssid_result = -EINVAL;
475 return tether_update(tether);
478 static int tether_set_passphrase_return(DBusMessageIter *iter,
479 const char *error, void *user_data)
481 struct tether_properties *tether = user_data;
484 fprintf(stdout, "Wifi passphrase set\n");
485 tether->passphrase_result = 0;
487 fprintf(stderr, "Error setting wifi passphrase: %s\n", error);
488 tether->passphrase_result = -EINVAL;
491 return tether_update(tether);
494 static int tether_set_ssid(char *ssid, char *passphrase, int set_tethering)
496 struct tether_properties *tether = g_new(struct tether_properties, 1);
498 tether->set_tethering = set_tethering;
500 tether->ssid_result = __connmanctl_dbus_set_property(connection,
501 "/net/connman/technology/wifi",
502 "net.connman.Technology",
503 tether_set_ssid_return, tether,
504 "TetheringIdentifier", DBUS_TYPE_STRING, &ssid);
506 tether->passphrase_result =__connmanctl_dbus_set_property(connection,
507 "/net/connman/technology/wifi",
508 "net.connman.Technology",
509 tether_set_passphrase_return, tether,
510 "TetheringPassphrase", DBUS_TYPE_STRING, &passphrase);
512 if (tether->ssid_result != -EINPROGRESS &&
513 tether->passphrase_result != -EINPROGRESS) {
521 static int cmd_tether(char *args[], int num, struct connman_option *options)
523 char *ssid, *passphrase;
529 passphrase = args[num - 1];
530 ssid = args[num - 2];
532 set_tethering = parse_boolean(args[2]);
534 if (strcmp(args[1], "wifi") == 0) {
539 if (num == 5 && set_tethering == -1)
546 return tether_set_ssid(ssid, passphrase, set_tethering);
552 if (set_tethering == -1)
555 if (check_dbus_name(args[1]) == false)
558 return tether_set(args[1], set_tethering);
561 static int scan_return(DBusMessageIter *iter, const char *error,
564 char *path = user_data;
567 char *str = strrchr(path, '/');
569 fprintf(stdout, "Scan completed for %s\n", str);
571 fprintf(stderr, "Error %s: %s\n", path, error);
578 static int cmd_scan(char *args[], int num, struct connman_option *options)
588 if (check_dbus_name(args[1]) == false)
591 path = g_strdup_printf("/net/connman/technology/%s", args[1]);
592 return __connmanctl_dbus_method_call(connection, path,
593 "net.connman.Technology", "Scan",
594 scan_return, path, DBUS_TYPE_INVALID);
597 static int connect_return(DBusMessageIter *iter, const char *error,
600 char *path = user_data;
603 char *str = strrchr(path, '/');
605 fprintf(stdout, "Connected %s\n", str);
607 fprintf(stderr, "Error %s: %s\n", path, error);
614 static int cmd_connect(char *args[], int num, struct connman_option *options)
624 if (check_dbus_name(args[1]) == false)
627 path = g_strdup_printf("/net/connman/service/%s", args[1]);
628 return __connmanctl_dbus_method_call(connection, path,
629 "net.connman.Service", "Connect",
630 connect_return, path, DBUS_TYPE_INVALID);
633 static int disconnect_return(DBusMessageIter *iter, const char *error,
636 char *path = user_data;
639 char *str = strrchr(path, '/');
641 fprintf(stdout, "Disconnected %s\n", str);
643 fprintf(stderr, "Error %s: %s\n", path, error);
650 static int cmd_disconnect(char *args[], int num, struct connman_option *options)
660 if (check_dbus_name(args[1]) == false)
663 path = g_strdup_printf("/net/connman/service/%s", args[1]);
664 return __connmanctl_dbus_method_call(connection, path,
665 "net.connman.Service", "Disconnect",
666 disconnect_return, path, DBUS_TYPE_INVALID);
669 static int config_return(DBusMessageIter *iter, const char *error,
672 char *service_name = user_data;
675 fprintf(stderr, "Error %s: %s\n", service_name, error);
682 struct config_append {
687 static void config_append_ipv4(DBusMessageIter *iter,
690 struct config_append *append = user_data;
691 char **opts = append->opts;
697 while (opts[i] != NULL && ipv4[i] != NULL) {
698 __connmanctl_dbus_append_dict_entry(iter, ipv4[i],
699 DBUS_TYPE_STRING, &opts[i]);
706 static void config_append_ipv6(DBusMessageIter *iter, void *user_data)
708 struct config_append *append = user_data;
709 char **opts = append->opts;
716 if (g_strcmp0(opts[0], "auto") == 0) {
719 switch (parse_boolean(opts[1])) {
724 __connmanctl_dbus_append_dict_entry(iter, "Privacy",
725 DBUS_TYPE_STRING, &str);
732 __connmanctl_dbus_append_dict_entry(iter, "Privacy",
733 DBUS_TYPE_STRING, &str);
737 if (opts[1] != NULL) {
740 if (g_strcmp0(opts[0], "prefered") != 0) {
741 fprintf(stderr, "Error %s: %s\n",
748 __connmanctl_dbus_append_dict_entry(iter,
749 "Privacy", DBUS_TYPE_STRING,
754 } else if (g_strcmp0(opts[0], "manual") == 0) {
757 while (opts[i] != NULL && ipv6[i] != NULL) {
759 int value = atoi(opts[i]);
760 __connmanctl_dbus_append_dict_entry(iter,
761 ipv6[i], DBUS_TYPE_BYTE,
764 __connmanctl_dbus_append_dict_entry(iter,
765 ipv6[i], DBUS_TYPE_STRING,
773 } else if (g_strcmp0(opts[0], "off") != 0) {
774 fprintf(stderr, "Error %s: %s\n", opts[0], strerror(-EINVAL));
779 __connmanctl_dbus_append_dict_entry(iter, "Method", DBUS_TYPE_STRING,
783 static void config_append_str(DBusMessageIter *iter, void *user_data)
785 struct config_append *append = user_data;
786 char **opts = append->opts;
792 while (opts[i] != NULL) {
793 dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING,
801 static void append_servers(DBusMessageIter *iter, void *user_data)
803 struct config_append *append = user_data;
804 char **opts = append->opts;
810 while (opts[i] != NULL && g_strcmp0(opts[i], "--excludes") != 0) {
811 dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING,
819 static void append_excludes(DBusMessageIter *iter, void *user_data)
821 struct config_append *append = user_data;
822 char **opts = append->opts;
823 int i = append->values;
825 if (opts == NULL || opts[i] == NULL ||
826 g_strcmp0(opts[i], "--excludes") != 0)
830 while (opts[i] != NULL) {
831 dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING,
839 static void config_append_proxy(DBusMessageIter *iter, void *user_data)
841 struct config_append *append = user_data;
842 char **opts = append->opts;
847 if (g_strcmp0(opts[0], "manual") == 0) {
848 __connmanctl_dbus_append_dict_string_array(iter, "Servers",
849 append_servers, append);
851 __connmanctl_dbus_append_dict_string_array(iter, "Excludes",
852 append_excludes, append);
854 } else if (g_strcmp0(opts[0], "auto") == 0) {
855 if (opts[1] != NULL) {
856 __connmanctl_dbus_append_dict_entry(iter, "URL",
857 DBUS_TYPE_STRING, &opts[1]);
861 } else if (g_strcmp0(opts[0], "direct") != 0)
864 __connmanctl_dbus_append_dict_entry(iter, "Method",DBUS_TYPE_STRING,
870 static int cmd_config(char *args[], int num, struct connman_option *options)
872 int result = 0, res = 0, index = 2, oldindex = 0;
874 char *service_name, *path;
877 struct config_append append;
879 service_name = args[1];
880 if (service_name == NULL)
883 if (check_dbus_name(service_name) == false)
886 while (index < num && args[index] != NULL) {
887 c = parse_args(args[index], options);
888 opt_start = &args[index + 1];
889 append.opts = opt_start;
895 path = g_strdup_printf("/net/connman/service/%s", service_name);
899 switch (parse_boolean(*opt_start)) {
914 res = __connmanctl_dbus_set_property(connection,
915 path, "net.connman.Service",
917 g_strdup(service_name),
919 DBUS_TYPE_BOOLEAN, &val);
923 res = __connmanctl_dbus_set_property_dict(connection,
924 path, "net.connman.Service",
925 config_return, g_strdup(service_name),
926 "IPv4.Configuration", DBUS_TYPE_STRING,
927 config_append_ipv4, &append);
928 index += append.values;
932 res = __connmanctl_dbus_set_property_dict(connection,
933 path, "net.connman.Service",
934 config_return, g_strdup(service_name),
935 "IPv6.Configuration", DBUS_TYPE_STRING,
936 config_append_ipv6, &append);
937 index += append.values;
941 res = __connmanctl_dbus_set_property_array(connection,
942 path, "net.connman.Service",
943 config_return, g_strdup(service_name),
944 "Nameservers.Configuration",
945 DBUS_TYPE_STRING, config_append_str,
947 index += append.values;
951 res = __connmanctl_dbus_set_property_array(connection,
952 path, "net.connman.Service",
953 config_return, g_strdup(service_name),
954 "Timeservers.Configuration",
955 DBUS_TYPE_STRING, config_append_str,
957 index += append.values;
961 res = __connmanctl_dbus_set_property_array(connection,
962 path, "net.connman.Service",
963 config_return, g_strdup(service_name),
964 "Domains.Configuration",
965 DBUS_TYPE_STRING, config_append_str,
967 index += append.values;
971 res = __connmanctl_dbus_set_property_dict(connection,
972 path, "net.connman.Service",
973 config_return, g_strdup(service_name),
974 "Proxy.Configuration",
975 DBUS_TYPE_STRING, config_append_proxy,
977 index += append.values;
980 res = __connmanctl_dbus_method_call(connection,
981 path, "net.connman.Service", "Remove",
982 config_return, g_strdup(service_name),
993 if (res == -EINPROGRESS)
994 result = -EINPROGRESS;
996 printf("Error '%s': %s\n", args[oldindex],
1007 static DBusHandlerResult monitor_changed(DBusConnection *connection,
1008 DBusMessage *message, void *user_data)
1010 DBusMessageIter iter;
1011 const char *interface, *path;
1013 interface = dbus_message_get_interface(message);
1014 if (strncmp(interface, "net.connman.", 12) != 0)
1015 return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
1017 interface = strrchr(interface, '.');
1018 if (interface != NULL && *interface != '\0')
1021 path = strrchr(dbus_message_get_path(message), '/');
1022 if (path != NULL && *path != '\0')
1025 __connmanctl_save_rl();
1027 if (dbus_message_is_signal(message, "net.connman.Manager",
1028 "ServicesChanged") == TRUE) {
1030 fprintf(stdout, "%-12s %-20s = {\n", interface,
1032 dbus_message_iter_init(message, &iter);
1033 __connmanctl_services_list(&iter);
1034 fprintf(stdout, "\n}\n");
1036 __connmanctl_redraw_rl();
1038 return DBUS_HANDLER_RESULT_HANDLED;
1041 if (dbus_message_is_signal(message, "net.connman.Manager",
1042 "TechnologyAdded") == TRUE)
1043 path = "TechnologyAdded";
1045 if (dbus_message_is_signal(message, "net.connman.Manager",
1046 "TechnologyRemoved") == TRUE)
1047 path = "TechnologyRemoved";
1049 fprintf(stdout, "%-12s %-20s ", interface, path);
1050 dbus_message_iter_init(message, &iter);
1052 __connmanctl_dbus_print(&iter, "", " = ", " = ");
1053 fprintf(stdout, "\n");
1055 __connmanctl_redraw_rl();
1057 return DBUS_HANDLER_RESULT_HANDLED;
1060 static bool monitor_s = false;
1061 static bool monitor_t = false;
1062 static bool monitor_m = false;
1064 static void monitor_add(char *interface)
1069 if (monitor_s == false && monitor_t == false && monitor_m == false)
1070 dbus_connection_add_filter(connection, monitor_changed,
1073 if (g_strcmp0(interface, "Service") == 0) {
1074 if (monitor_s == true)
1077 } else if (g_strcmp0(interface, "Technology") == 0) {
1078 if (monitor_t == true)
1081 } else if (g_strcmp0(interface, "Manager") == 0) {
1082 if (monitor_m == true)
1088 dbus_error_init(&err);
1089 rule = g_strdup_printf("type='signal',interface='net.connman.%s'",
1091 dbus_bus_add_match(connection, rule, &err);
1094 if (dbus_error_is_set(&err))
1095 fprintf(stderr, "Error: %s\n", err.message);
1098 static void monitor_del(char *interface)
1102 if (g_strcmp0(interface, "Service") == 0) {
1103 if (monitor_s == false)
1106 } else if (g_strcmp0(interface, "Technology") == 0) {
1107 if (monitor_t == false)
1110 } else if (g_strcmp0(interface, "Manager") == 0) {
1111 if (monitor_m == false)
1117 rule = g_strdup_printf("type='signal',interface='net.connman.%s'",
1119 dbus_bus_remove_match(connection, rule, NULL);
1122 if (monitor_s == false && monitor_t == false && monitor_m == false)
1123 dbus_connection_remove_filter(connection, monitor_changed,
1127 static int cmd_monitor(char *args[], int num, struct connman_option *options)
1136 switch (parse_boolean(args[2])) {
1146 c = parse_args(args[1], options);
1149 monitor_add("Service");
1150 monitor_add("Technology");
1151 monitor_add("Manager");
1156 monitor_add("Service");
1158 monitor_del("Service");
1163 monitor_add("Technology");
1165 monitor_del("Technology");
1170 monitor_add("Manager");
1172 monitor_del("Manager");
1176 switch(parse_boolean(args[1])) {
1178 monitor_del("Service");
1179 monitor_del("Technology");
1180 monitor_del("Manager");
1184 monitor_add("Service");
1185 monitor_add("Technology");
1186 monitor_add("Manager");
1195 return -EINPROGRESS;
1200 static int cmd_agent(char *args[], int num, struct connman_option *options)
1208 switch(parse_boolean(args[1])) {
1210 __connmanctl_agent_unregister(connection);
1214 if (__connmanctl_agent_register(connection) == -EINPROGRESS)
1215 return -EINPROGRESS;
1227 static int cmd_exit(char *args[], int num, struct connman_option *options)
1232 static struct connman_option service_options[] = {
1233 {"properties", 'p', "[<service>] (obsolete)"},
1237 static struct connman_option config_options[] = {
1238 {"nameservers", 'n', "<dns1> [<dns2>] [<dns3>]"},
1239 {"timeservers", 't', "<ntp1> [<ntp2>] [...]"},
1240 {"domains", 'd', "<domain1> [<domain2>] [...]"},
1241 {"ipv6", 'v', "off|auto [enable|disable|prefered]|\n"
1242 "\t\t\tmanual <address> <prefixlength> <gateway>"},
1243 {"proxy", 'x', "direct|auto <URL>|manual <URL1> [<URL2>] [...]\n"
1244 "\t\t\t[exclude <exclude1> [<exclude2>] [...]]"},
1245 {"autoconnect", 'a', "yes|no"},
1246 {"ipv4", 'i', "off|dhcp|manual <address> <netmask> <gateway>"},
1247 {"remove", 'r', " Remove service"},
1251 static struct connman_option monitor_options[] = {
1252 {"services", 's', "[off] Monitor only services"},
1253 {"tech", 'c', "[off] Monitor only technologies"},
1254 {"manager", 'm', "[off] Monitor only manager interface"},
1258 static const struct {
1260 const char *argument;
1261 struct connman_option *options;
1262 int (*func) (char *args[], int num, struct connman_option *options);
1265 { "state", NULL, NULL, cmd_state,
1266 "Shows if the system is online or offline" },
1267 { "technologies", NULL, NULL, cmd_technologies,
1268 "Display technologies" },
1269 { "enable", "<technology>|offline", NULL, cmd_enable,
1270 "Enables given technology or offline mode" },
1271 { "disable", "<technology>|offline", NULL, cmd_disable,
1272 "Disables given technology or offline mode"},
1273 { "tether", "<technology> on|off\n"
1274 " wifi [on|off] <ssid> <passphrase> ",
1276 "Enable, disable tethering, set SSID and passphrase for wifi" },
1277 { "services", "[<service>]", service_options, cmd_services,
1278 "Display services" },
1279 { "scan", "<technology>", NULL, cmd_scan,
1280 "Scans for new services for given technology" },
1281 { "connect", "<service>", NULL, cmd_connect,
1282 "Connect a given service" },
1283 { "disconnect", "<service>", NULL, cmd_disconnect,
1284 "Disconnect a given service" },
1285 { "config", "<service>", config_options, cmd_config,
1286 "Set service configuration options" },
1287 { "monitor", "[off]", monitor_options, cmd_monitor,
1288 "Monitor signals from interfaces" },
1289 { "agent", "on|off", NULL, cmd_agent,
1291 { "help", NULL, NULL, cmd_help,
1293 { "exit", NULL, NULL, cmd_exit,
1295 { "quit", NULL, NULL, cmd_exit,
1300 static int cmd_help(char *args[], int num, struct connman_option *options)
1302 bool interactive = __connmanctl_is_interactive();
1305 if (interactive == false)
1306 fprintf(stdout, "Usage: connmanctl [[command] [args]]\n");
1308 for (i = 0; cmd_table[i].cmd != NULL; i++) {
1309 const char *cmd = cmd_table[i].cmd;
1310 const char *argument = cmd_table[i].argument;
1311 const char *desc = cmd_table[i].desc;
1313 printf("%-12s%-22s%s\n", cmd != NULL? cmd: "",
1314 argument != NULL? argument: "",
1315 desc != NULL? desc: "");
1317 if (cmd_table[i].options != NULL) {
1318 for (j = 0; cmd_table[i].options[j].name != NULL;
1320 const char *options_desc =
1321 cmd_table[i].options[j].desc != NULL ?
1322 cmd_table[i].options[j].desc: "";
1324 printf(" --%-12s%s\n",
1325 cmd_table[i].options[j].name,
1331 if (interactive == false)
1332 fprintf(stdout, "\nNote: arguments and output are considered "
1333 "EXPERIMENTAL for now.\n");
1338 int __connmanctl_commands(DBusConnection *dbus_conn, char *argv[], int argc)
1342 connection = dbus_conn;
1344 for (i = 0; cmd_table[i].cmd != NULL; i++) {
1345 if (g_strcmp0(cmd_table[i].cmd, argv[0]) == 0 &&
1346 cmd_table[i].func != NULL) {
1347 result = cmd_table[i].func(argv, argc,
1348 cmd_table[i].options);
1349 if (result < 0 && result != -EINPROGRESS)
1350 fprintf(stderr, "Error '%s': %s\n", argv[0],
1356 fprintf(stderr, "Error '%s': Unknown command\n", argv[0]);
1360 char *__connmanctl_lookup_command(const char *text, int state)
1370 while (cmd_table[i].cmd != NULL) {
1371 const char *command = cmd_table[i].cmd;
1375 if (strncmp(text, command, len) == 0)
1376 return strdup(command);