2 * WPA Supplicant - command line interface for wpa_supplicant daemon
3 * Copyright (c) 2004-2015, Jouni Malinen <j@w1.fi>
5 * This software may be distributed under the terms of the BSD license.
6 * See README for more details.
11 #ifdef CONFIG_CTRL_IFACE
13 #ifdef CONFIG_CTRL_IFACE_UNIX
15 #endif /* CONFIG_CTRL_IFACE_UNIX */
17 #include "common/wpa_ctrl.h"
18 #include "utils/common.h"
19 #include "utils/eloop.h"
20 #include "utils/edit.h"
21 #include "utils/list.h"
22 #include "common/version.h"
23 #include "common/ieee802_11_defs.h"
25 #include <cutils/properties.h>
29 static const char *const wpa_cli_version =
30 "wpa_cli v" VERSION_STR "\n"
31 "Copyright (c) 2004-2015, Jouni Malinen <j@w1.fi> and contributors";
34 static const char *const wpa_cli_license =
35 "This software may be distributed under the terms of the BSD license.\n"
36 "See README for more details.\n";
38 static const char *const wpa_cli_full_license =
39 "This software may be distributed under the terms of the BSD license.\n"
41 "Redistribution and use in source and binary forms, with or without\n"
42 "modification, are permitted provided that the following conditions are\n"
45 "1. Redistributions of source code must retain the above copyright\n"
46 " notice, this list of conditions and the following disclaimer.\n"
48 "2. Redistributions in binary form must reproduce the above copyright\n"
49 " notice, this list of conditions and the following disclaimer in the\n"
50 " documentation and/or other materials provided with the distribution.\n"
52 "3. Neither the name(s) of the above-listed copyright holder(s) nor the\n"
53 " names of its contributors may be used to endorse or promote products\n"
54 " derived from this software without specific prior written permission.\n"
56 "THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n"
57 "\"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n"
58 "LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\n"
59 "A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT\n"
60 "OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,\n"
61 "SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT\n"
62 "LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,\n"
63 "DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY\n"
64 "THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n"
65 "(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE\n"
66 "OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n"
69 static struct wpa_ctrl *ctrl_conn;
70 static struct wpa_ctrl *mon_conn;
71 static int wpa_cli_quit = 0;
72 static int wpa_cli_attached = 0;
73 static int wpa_cli_connected = -1;
74 static int wpa_cli_last_id = 0;
75 #ifndef CONFIG_CTRL_IFACE_DIR
76 #define CONFIG_CTRL_IFACE_DIR "/var/run/wpa_supplicant"
77 #endif /* CONFIG_CTRL_IFACE_DIR */
78 static const char *ctrl_iface_dir = CONFIG_CTRL_IFACE_DIR;
79 static const char *client_socket_dir = NULL;
80 static char *ctrl_ifname = NULL;
81 static const char *pid_file = NULL;
82 static const char *action_file = NULL;
83 static int ping_interval = 5;
84 static int interactive = 0;
85 static char *ifname_prefix = NULL;
87 struct cli_txt_entry {
92 static DEFINE_DL_LIST(bsses); /* struct cli_txt_entry */
93 static DEFINE_DL_LIST(p2p_peers); /* struct cli_txt_entry */
94 static DEFINE_DL_LIST(p2p_groups); /* struct cli_txt_entry */
95 static DEFINE_DL_LIST(ifnames); /* struct cli_txt_entry */
96 static DEFINE_DL_LIST(networks); /* struct cli_txt_entry */
99 static void print_help(const char *cmd);
100 static void wpa_cli_mon_receive(int sock, void *eloop_ctx, void *sock_ctx);
101 static void wpa_cli_close_connection(void);
102 static char * wpa_cli_get_default_ifname(void);
103 static char ** wpa_list_cmd_list(void);
104 static void update_networks(struct wpa_ctrl *ctrl);
107 static void usage(void)
109 printf("wpa_cli [-p<path to ctrl sockets>] [-i<ifname>] [-hvB] "
110 "[-a<action file>] \\\n"
111 " [-P<pid file>] [-g<global ctrl>] [-G<ping interval>] "
113 " [-s<wpa_client_socket_file_path>] "
115 " -h = help (show this usage text)\n"
116 " -v = shown version information\n"
117 " -a = run in daemon mode executing the action file based on "
120 " -B = run a daemon in the background\n"
121 " default path: " CONFIG_CTRL_IFACE_DIR "\n"
122 " default interface: first interface found in socket path\n");
127 static void cli_txt_list_free(struct cli_txt_entry *e)
129 dl_list_del(&e->list);
135 static void cli_txt_list_flush(struct dl_list *list)
137 struct cli_txt_entry *e;
138 while ((e = dl_list_first(list, struct cli_txt_entry, list)))
139 cli_txt_list_free(e);
143 static struct cli_txt_entry * cli_txt_list_get(struct dl_list *txt_list,
146 struct cli_txt_entry *e;
147 dl_list_for_each(e, txt_list, struct cli_txt_entry, list) {
148 if (os_strcmp(e->txt, txt) == 0)
155 static void cli_txt_list_del(struct dl_list *txt_list, const char *txt)
157 struct cli_txt_entry *e;
158 e = cli_txt_list_get(txt_list, txt);
160 cli_txt_list_free(e);
164 static void cli_txt_list_del_addr(struct dl_list *txt_list, const char *txt)
168 if (hwaddr_aton(txt, addr) < 0)
170 os_snprintf(buf, sizeof(buf), MACSTR, MAC2STR(addr));
171 cli_txt_list_del(txt_list, buf);
176 static void cli_txt_list_del_word(struct dl_list *txt_list, const char *txt,
181 end = os_strchr(txt, separator);
183 end = txt + os_strlen(txt);
184 buf = dup_binstr(txt, end - txt);
187 cli_txt_list_del(txt_list, buf);
190 #endif /* CONFIG_P2P */
193 static int cli_txt_list_add(struct dl_list *txt_list, const char *txt)
195 struct cli_txt_entry *e;
196 e = cli_txt_list_get(txt_list, txt);
199 e = os_zalloc(sizeof(*e));
202 e->txt = os_strdup(txt);
203 if (e->txt == NULL) {
207 dl_list_add(txt_list, &e->list);
213 static int cli_txt_list_add_addr(struct dl_list *txt_list, const char *txt)
217 if (hwaddr_aton(txt, addr) < 0)
219 os_snprintf(buf, sizeof(buf), MACSTR, MAC2STR(addr));
220 return cli_txt_list_add(txt_list, buf);
222 #endif /* CONFIG_P2P */
225 static int cli_txt_list_add_word(struct dl_list *txt_list, const char *txt,
231 end = os_strchr(txt, separator);
233 end = txt + os_strlen(txt);
234 buf = dup_binstr(txt, end - txt);
237 ret = cli_txt_list_add(txt_list, buf);
243 static char ** cli_txt_list_array(struct dl_list *txt_list)
245 unsigned int i, count = dl_list_len(txt_list);
247 struct cli_txt_entry *e;
249 res = os_calloc(count + 1, sizeof(char *));
254 dl_list_for_each(e, txt_list, struct cli_txt_entry, list) {
255 res[i] = os_strdup(e->txt);
265 static int get_cmd_arg_num(const char *str, int pos)
269 for (i = 0; i <= pos; i++) {
272 while (i <= pos && str[i] != ' ')
283 static int str_starts(const char *src, const char *match)
285 return os_strncmp(src, match, os_strlen(match)) == 0;
289 static int wpa_cli_show_event(const char *event)
293 start = os_strchr(event, '>');
299 * Skip BSS added/removed events since they can be relatively frequent
300 * and are likely of not much use for an interactive user.
302 if (str_starts(start, WPA_EVENT_BSS_ADDED) ||
303 str_starts(start, WPA_EVENT_BSS_REMOVED))
310 static int wpa_cli_open_connection(const char *ifname, int attach)
312 #if defined(CONFIG_CTRL_IFACE_UDP) || defined(CONFIG_CTRL_IFACE_NAMED_PIPE)
313 ctrl_conn = wpa_ctrl_open(ifname);
314 if (ctrl_conn == NULL)
317 if (attach && interactive)
318 mon_conn = wpa_ctrl_open(ifname);
321 #else /* CONFIG_CTRL_IFACE_UDP || CONFIG_CTRL_IFACE_NAMED_PIPE */
329 if (access(ctrl_iface_dir, F_OK) < 0) {
330 cfile = os_strdup(ifname);
336 if (client_socket_dir && client_socket_dir[0] &&
337 access(client_socket_dir, F_OK) < 0) {
338 perror(client_socket_dir);
344 flen = os_strlen(ctrl_iface_dir) + os_strlen(ifname) + 2;
345 cfile = os_malloc(flen);
348 res = os_snprintf(cfile, flen, "%s/%s", ctrl_iface_dir,
350 if (os_snprintf_error(flen, res)) {
356 ctrl_conn = wpa_ctrl_open2(cfile, client_socket_dir);
357 if (ctrl_conn == NULL) {
362 if (attach && interactive)
363 mon_conn = wpa_ctrl_open2(cfile, client_socket_dir);
367 #endif /* CONFIG_CTRL_IFACE_UDP || CONFIG_CTRL_IFACE_NAMED_PIPE */
370 if (wpa_ctrl_attach(mon_conn) == 0) {
371 wpa_cli_attached = 1;
373 eloop_register_read_sock(
374 wpa_ctrl_get_fd(mon_conn),
375 wpa_cli_mon_receive, NULL, NULL);
377 printf("Warning: Failed to attach to "
378 "wpa_supplicant.\n");
379 wpa_cli_close_connection();
388 static void wpa_cli_close_connection(void)
390 if (ctrl_conn == NULL)
393 if (wpa_cli_attached) {
394 wpa_ctrl_detach(interactive ? mon_conn : ctrl_conn);
395 wpa_cli_attached = 0;
397 wpa_ctrl_close(ctrl_conn);
400 eloop_unregister_read_sock(wpa_ctrl_get_fd(mon_conn));
401 wpa_ctrl_close(mon_conn);
407 static void wpa_cli_msg_cb(char *msg, size_t len)
413 static int _wpa_ctrl_command(struct wpa_ctrl *ctrl, char *cmd, int print)
419 if (ctrl_conn == NULL) {
420 printf("Not connected to wpa_supplicant - command dropped.\n");
424 os_snprintf(buf, sizeof(buf), "IFNAME=%s %s",
426 buf[sizeof(buf) - 1] = '\0';
429 len = sizeof(buf) - 1;
430 ret = wpa_ctrl_request(ctrl, cmd, os_strlen(cmd), buf, &len,
433 printf("'%s' command timed out.\n", cmd);
435 } else if (ret < 0) {
436 printf("'%s' command failed.\n", cmd);
442 if (interactive && len > 0 && buf[len - 1] != '\n')
449 static int wpa_ctrl_command(struct wpa_ctrl *ctrl, char *cmd)
451 return _wpa_ctrl_command(ctrl, cmd, 1);
455 static int write_cmd(char *buf, size_t buflen, const char *cmd, int argc,
464 res = os_snprintf(pos, end - pos, "%s", cmd);
465 if (os_snprintf_error(end - pos, res))
469 for (i = 0; i < argc; i++) {
470 res = os_snprintf(pos, end - pos, " %s", argv[i]);
471 if (os_snprintf_error(end - pos, res))
476 buf[buflen - 1] = '\0';
480 printf("Too long command\n");
485 static int wpa_cli_cmd(struct wpa_ctrl *ctrl, const char *cmd, int min_args,
486 int argc, char *argv[])
489 if (argc < min_args) {
490 printf("Invalid %s command - at least %d argument%s "
491 "required.\n", cmd, min_args,
492 min_args > 1 ? "s are" : " is");
495 if (write_cmd(buf, sizeof(buf), cmd, argc, argv) < 0)
497 return wpa_ctrl_command(ctrl, buf);
501 static int wpa_cli_cmd_ifname(struct wpa_ctrl *ctrl, int argc, char *argv[])
503 return wpa_ctrl_command(ctrl, "IFNAME");
507 static int wpa_cli_cmd_status(struct wpa_ctrl *ctrl, int argc, char *argv[])
509 if (argc > 0 && os_strcmp(argv[0], "verbose") == 0)
510 return wpa_ctrl_command(ctrl, "STATUS-VERBOSE");
511 if (argc > 0 && os_strcmp(argv[0], "wps") == 0)
512 return wpa_ctrl_command(ctrl, "STATUS-WPS");
513 if (argc > 0 && os_strcmp(argv[0], "driver") == 0)
514 return wpa_ctrl_command(ctrl, "STATUS-DRIVER");
516 if (argc > 0 && os_strcmp(argv[0], "no_events") == 0)
517 return wpa_ctrl_command(ctrl, "STATUS-NO_EVENTS");
519 return wpa_ctrl_command(ctrl, "STATUS");
523 static int wpa_cli_cmd_ping(struct wpa_ctrl *ctrl, int argc, char *argv[])
525 return wpa_ctrl_command(ctrl, "PING");
529 static int wpa_cli_cmd_relog(struct wpa_ctrl *ctrl, int argc, char *argv[])
531 return wpa_ctrl_command(ctrl, "RELOG");
535 static int wpa_cli_cmd_note(struct wpa_ctrl *ctrl, int argc, char *argv[])
537 return wpa_cli_cmd(ctrl, "NOTE", 1, argc, argv);
541 static int wpa_cli_cmd_mib(struct wpa_ctrl *ctrl, int argc, char *argv[])
543 return wpa_ctrl_command(ctrl, "MIB");
547 static int wpa_cli_cmd_pmksa(struct wpa_ctrl *ctrl, int argc, char *argv[])
549 return wpa_ctrl_command(ctrl, "PMKSA");
553 static int wpa_cli_cmd_pmksa_flush(struct wpa_ctrl *ctrl, int argc,
556 return wpa_ctrl_command(ctrl, "PMKSA_FLUSH");
560 static int wpa_cli_cmd_help(struct wpa_ctrl *ctrl, int argc, char *argv[])
562 print_help(argc > 0 ? argv[0] : NULL);
567 static char ** wpa_cli_complete_help(const char *str, int pos)
569 int arg = get_cmd_arg_num(str, pos);
574 res = wpa_list_cmd_list();
582 static int wpa_cli_cmd_license(struct wpa_ctrl *ctrl, int argc, char *argv[])
584 printf("%s\n\n%s\n", wpa_cli_version, wpa_cli_full_license);
589 static int wpa_cli_cmd_quit(struct wpa_ctrl *ctrl, int argc, char *argv[])
598 static int wpa_cli_cmd_set(struct wpa_ctrl *ctrl, int argc, char *argv[])
604 res = os_snprintf(cmd, sizeof(cmd), "SET %s ", argv[0]);
605 if (os_snprintf_error(sizeof(cmd), res)) {
606 printf("Too long SET command.\n");
609 return wpa_ctrl_command(ctrl, cmd);
612 return wpa_cli_cmd(ctrl, "SET", 2, argc, argv);
616 static char ** wpa_cli_complete_set(const char *str, int pos)
618 int arg = get_cmd_arg_num(str, pos);
619 const char *fields[] = {
621 "EAPOL::heldPeriod", "EAPOL::authPeriod", "EAPOL::startPeriod",
622 "EAPOL::maxStart", "dot11RSNAConfigPMKLifetime",
623 "dot11RSNAConfigPMKReauthThreshold", "dot11RSNAConfigSATimeout",
624 "wps_fragment_size", "wps_version_number", "ampdu",
625 "tdls_testing", "tdls_disabled", "pno", "radio_disabled",
626 "uapsd", "ps", "wifi_display", "bssid_filter", "disallow_aps",
628 /* global configuration parameters */
629 #ifdef CONFIG_CTRL_IFACE
630 "ctrl_interface", "no_ctrl_interface", "ctrl_interface_group",
631 #endif /* CONFIG_CTRL_IFACE */
632 "eapol_version", "ap_scan", "bgscan",
634 "user_mpm", "max_peer_links", "mesh_max_inactivity",
635 "dot11RSNASAERetransPeriod",
636 #endif /* CONFIG_MESH */
637 "disable_scan_offload", "fast_reauth", "opensc_engine_path",
638 "pkcs11_engine_path", "pkcs11_module_path", "openssl_ciphers",
639 "pcsc_reader", "pcsc_pin", "external_sim", "driver_param",
640 "dot11RSNAConfigPMKLifetime",
641 "dot11RSNAConfigPMKReauthThreshold",
642 "dot11RSNAConfigSATimeout",
643 #ifndef CONFIG_NO_CONFIG_WRITE
645 #endif /* CONFIG_NO_CONFIG_WRITE */
648 "uuid", "device_name", "manufacturer", "model_name",
649 "model_number", "serial_number", "device_type", "os_version",
650 "config_methods", "wps_cred_processing", "wps_vendor_ext_m1",
651 #endif /* CONFIG_WPS */
654 "p2p_listen_reg_class", "p2p_listen_channel",
655 "p2p_oper_reg_class", "p2p_oper_channel", "p2p_go_intent",
656 "p2p_ssid_postfix", "persistent_reconnect", "p2p_intra_bss",
657 "p2p_group_idle", "p2p_passphrase_len", "p2p_pref_chan",
658 "p2p_no_go_freq", "p2p_add_cli_chan",
659 "p2p_optimize_listen_chan", "p2p_go_ht40", "p2p_go_vht",
660 "p2p_disabled", "p2p_go_ctwindow", "p2p_no_group_iface",
661 "p2p_ignore_shared_freq", "ip_addr_go", "ip_addr_mask",
662 "ip_addr_start", "ip_addr_end",
663 #endif /* CONFIG_P2P */
664 "country", "bss_max_count", "bss_expiration_age",
665 "bss_expiration_scan_count", "filter_ssids", "filter_rssi",
666 "max_num_sta", "disassoc_low_ack",
669 #endif /* CONFIG_HS20 */
670 "interworking", "hessid", "access_network_type", "pbc_in_m1",
671 "autoscan", "wps_nfc_dev_pw_id", "wps_nfc_dh_pubkey",
672 "wps_nfc_dh_privkey", "wps_nfc_dev_pw", "ext_password_backend",
673 "p2p_go_max_inactivity", "auto_interworking", "okc", "pmf",
674 "sae_groups", "dtim_period", "beacon_int",
675 "ap_vendor_elements", "ignore_old_scan_res", "freq_list",
676 "scan_cur_freq", "sched_scan_interval",
677 "tdls_external_control", "osu_dir", "wowlan_triggers",
678 "p2p_search_delay", "mac_addr", "rand_addr_lifetime",
679 "preassoc_mac_addr", "key_mgmt_offload", "passive_scan",
680 "reassoc_same_bss_optim", "wps_priority"
682 int i, num_fields = ARRAY_SIZE(fields);
685 char **res = os_calloc(num_fields + 1, sizeof(char *));
688 for (i = 0; i < num_fields; i++) {
689 res[i] = os_strdup(fields[i]);
696 if (arg > 1 && os_strncasecmp(str, "set bssid_filter ", 17) == 0)
697 return cli_txt_list_array(&bsses);
702 static int wpa_cli_cmd_dump(struct wpa_ctrl *ctrl, int argc, char *argv[])
704 return wpa_ctrl_command(ctrl, "DUMP");
708 static int wpa_cli_cmd_get(struct wpa_ctrl *ctrl, int argc, char *argv[])
710 return wpa_cli_cmd(ctrl, "GET", 1, argc, argv);
714 static char ** wpa_cli_complete_get(const char *str, int pos)
716 int arg = get_cmd_arg_num(str, pos);
717 const char *fields[] = {
718 #ifdef CONFIG_CTRL_IFACE
719 "ctrl_interface", "ctrl_interface_group",
720 #endif /* CONFIG_CTRL_IFACE */
721 "eapol_version", "ap_scan",
723 "user_mpm", "max_peer_links", "mesh_max_inactivity",
724 #endif /* CONFIG_MESH */
725 "disable_scan_offload", "fast_reauth", "opensc_engine_path",
726 "pkcs11_engine_path", "pkcs11_module_path", "openssl_ciphers",
727 "pcsc_reader", "pcsc_pin", "external_sim", "driver_param",
728 "dot11RSNAConfigPMKLifetime",
729 "dot11RSNAConfigPMKReauthThreshold",
730 "dot11RSNAConfigSATimeout",
731 #ifndef CONFIG_NO_CONFIG_WRITE
733 #endif /* CONFIG_NO_CONFIG_WRITE */
735 "device_name", "manufacturer", "model_name", "model_number",
736 "serial_number", "config_methods", "wps_cred_processing",
737 #endif /* CONFIG_WPS */
739 "p2p_listen_reg_class", "p2p_listen_channel",
740 "p2p_oper_reg_class", "p2p_oper_channel", "p2p_go_intent",
741 "p2p_ssid_postfix", "persistent_reconnect", "p2p_intra_bss",
742 "p2p_group_idle", "p2p_passphrase_len", "p2p_add_cli_chan",
743 "p2p_optimize_listen_chan", "p2p_go_ht40", "p2p_go_vht",
744 "p2p_disabled", "p2p_go_ctwindow", "p2p_no_group_iface",
745 "p2p_ignore_shared_freq", "ip_addr_go", "ip_addr_mask",
746 "ip_addr_start", "ip_addr_end",
747 #endif /* CONFIG_P2P */
748 "bss_max_count", "bss_expiration_age",
749 "bss_expiration_scan_count", "filter_ssids", "filter_rssi",
750 "max_num_sta", "disassoc_low_ack",
753 #endif /* CONFIG_HS20 */
754 "interworking", "access_network_type", "pbc_in_m1", "autoscan",
755 "wps_nfc_dev_pw_id", "ext_password_backend",
756 "p2p_go_max_inactivity", "auto_interworking", "okc", "pmf",
757 "dtim_period", "beacon_int", "ignore_old_scan_res",
758 "scan_cur_freq", "sched_scan_interval",
759 "tdls_external_control", "osu_dir", "wowlan_triggers",
760 "p2p_search_delay", "mac_addr", "rand_addr_lifetime",
761 "preassoc_mac_addr", "key_mgmt_offload", "passive_scan",
762 "reassoc_same_bss_optim"
764 int i, num_fields = ARRAY_SIZE(fields);
767 char **res = os_calloc(num_fields + 1, sizeof(char *));
770 for (i = 0; i < num_fields; i++) {
771 res[i] = os_strdup(fields[i]);
782 static int wpa_cli_cmd_logoff(struct wpa_ctrl *ctrl, int argc, char *argv[])
784 return wpa_ctrl_command(ctrl, "LOGOFF");
788 static int wpa_cli_cmd_logon(struct wpa_ctrl *ctrl, int argc, char *argv[])
790 return wpa_ctrl_command(ctrl, "LOGON");
794 static int wpa_cli_cmd_reassociate(struct wpa_ctrl *ctrl, int argc,
797 return wpa_ctrl_command(ctrl, "REASSOCIATE");
801 static int wpa_cli_cmd_reattach(struct wpa_ctrl *ctrl, int argc, char *argv[])
803 return wpa_ctrl_command(ctrl, "REATTACH");
807 static int wpa_cli_cmd_preauthenticate(struct wpa_ctrl *ctrl, int argc,
810 return wpa_cli_cmd(ctrl, "PREAUTH", 1, argc, argv);
814 static int wpa_cli_cmd_ap_scan(struct wpa_ctrl *ctrl, int argc, char *argv[])
816 return wpa_cli_cmd(ctrl, "AP_SCAN", 1, argc, argv);
820 static int wpa_cli_cmd_scan_interval(struct wpa_ctrl *ctrl, int argc,
823 return wpa_cli_cmd(ctrl, "SCAN_INTERVAL", 1, argc, argv);
827 static int wpa_cli_cmd_bss_expire_age(struct wpa_ctrl *ctrl, int argc,
830 return wpa_cli_cmd(ctrl, "BSS_EXPIRE_AGE", 1, argc, argv);
834 static int wpa_cli_cmd_bss_expire_count(struct wpa_ctrl *ctrl, int argc,
837 return wpa_cli_cmd(ctrl, "BSS_EXPIRE_COUNT", 1, argc, argv);
841 static int wpa_cli_cmd_bss_flush(struct wpa_ctrl *ctrl, int argc, char *argv[])
847 res = os_snprintf(cmd, sizeof(cmd), "BSS_FLUSH 0");
849 res = os_snprintf(cmd, sizeof(cmd), "BSS_FLUSH %s", argv[0]);
850 if (os_snprintf_error(sizeof(cmd), res)) {
851 printf("Too long BSS_FLUSH command.\n");
854 return wpa_ctrl_command(ctrl, cmd);
858 static int wpa_cli_cmd_stkstart(struct wpa_ctrl *ctrl, int argc,
861 return wpa_cli_cmd(ctrl, "STKSTART", 1, argc, argv);
865 static int wpa_cli_cmd_ft_ds(struct wpa_ctrl *ctrl, int argc, char *argv[])
867 return wpa_cli_cmd(ctrl, "FT_DS", 1, argc, argv);
871 static int wpa_cli_cmd_wps_pbc(struct wpa_ctrl *ctrl, int argc, char *argv[])
873 return wpa_cli_cmd(ctrl, "WPS_PBC", 0, argc, argv);
877 static int wpa_cli_cmd_wps_pin(struct wpa_ctrl *ctrl, int argc, char *argv[])
880 printf("Invalid WPS_PIN command: need one or two arguments:\n"
881 "- BSSID: use 'any' to select any\n"
882 "- PIN: optional, used only with devices that have no "
887 return wpa_cli_cmd(ctrl, "WPS_PIN", 1, argc, argv);
891 static int wpa_cli_cmd_wps_check_pin(struct wpa_ctrl *ctrl, int argc,
894 return wpa_cli_cmd(ctrl, "WPS_CHECK_PIN", 1, argc, argv);
898 static int wpa_cli_cmd_wps_cancel(struct wpa_ctrl *ctrl, int argc,
901 return wpa_ctrl_command(ctrl, "WPS_CANCEL");
905 #ifdef CONFIG_WPS_NFC
907 static int wpa_cli_cmd_wps_nfc(struct wpa_ctrl *ctrl, int argc, char *argv[])
909 return wpa_cli_cmd(ctrl, "WPS_NFC", 0, argc, argv);
913 static int wpa_cli_cmd_wps_nfc_config_token(struct wpa_ctrl *ctrl, int argc,
916 return wpa_cli_cmd(ctrl, "WPS_NFC_CONFIG_TOKEN", 1, argc, argv);
920 static int wpa_cli_cmd_wps_nfc_token(struct wpa_ctrl *ctrl, int argc,
923 return wpa_cli_cmd(ctrl, "WPS_NFC_TOKEN", 1, argc, argv);
927 static int wpa_cli_cmd_wps_nfc_tag_read(struct wpa_ctrl *ctrl, int argc,
935 printf("Invalid 'wps_nfc_tag_read' command - one argument "
940 buflen = 18 + os_strlen(argv[0]);
941 buf = os_malloc(buflen);
944 os_snprintf(buf, buflen, "WPS_NFC_TAG_READ %s", argv[0]);
946 ret = wpa_ctrl_command(ctrl, buf);
953 static int wpa_cli_cmd_nfc_get_handover_req(struct wpa_ctrl *ctrl, int argc,
956 return wpa_cli_cmd(ctrl, "NFC_GET_HANDOVER_REQ", 2, argc, argv);
960 static int wpa_cli_cmd_nfc_get_handover_sel(struct wpa_ctrl *ctrl, int argc,
963 return wpa_cli_cmd(ctrl, "NFC_GET_HANDOVER_SEL", 2, argc, argv);
967 static int wpa_cli_cmd_nfc_report_handover(struct wpa_ctrl *ctrl, int argc,
970 return wpa_cli_cmd(ctrl, "NFC_REPORT_HANDOVER", 4, argc, argv);
973 #endif /* CONFIG_WPS_NFC */
976 static int wpa_cli_cmd_wps_reg(struct wpa_ctrl *ctrl, int argc, char *argv[])
982 res = os_snprintf(cmd, sizeof(cmd), "WPS_REG %s %s",
984 else if (argc == 5 || argc == 6) {
985 char ssid_hex[2 * SSID_MAX_LEN + 1];
986 char key_hex[2 * 64 + 1];
990 for (i = 0; i < SSID_MAX_LEN; i++) {
991 if (argv[2][i] == '\0')
993 os_snprintf(&ssid_hex[i * 2], 3, "%02x", argv[2][i]);
998 for (i = 0; i < 64; i++) {
999 if (argv[5][i] == '\0')
1001 os_snprintf(&key_hex[i * 2], 3, "%02x",
1006 res = os_snprintf(cmd, sizeof(cmd),
1007 "WPS_REG %s %s %s %s %s %s",
1008 argv[0], argv[1], ssid_hex, argv[3], argv[4],
1011 printf("Invalid WPS_REG command: need two arguments:\n"
1012 "- BSSID of the target AP\n"
1014 printf("Alternatively, six arguments can be used to "
1015 "reconfigure the AP:\n"
1016 "- BSSID of the target AP\n"
1019 "- new auth (OPEN, WPAPSK, WPA2PSK)\n"
1020 "- new encr (NONE, WEP, TKIP, CCMP)\n"
1025 if (os_snprintf_error(sizeof(cmd), res)) {
1026 printf("Too long WPS_REG command.\n");
1029 return wpa_ctrl_command(ctrl, cmd);
1033 static int wpa_cli_cmd_wps_ap_pin(struct wpa_ctrl *ctrl, int argc,
1036 return wpa_cli_cmd(ctrl, "WPS_AP_PIN", 1, argc, argv);
1040 static int wpa_cli_cmd_wps_er_start(struct wpa_ctrl *ctrl, int argc,
1043 return wpa_cli_cmd(ctrl, "WPS_ER_START", 0, argc, argv);
1047 static int wpa_cli_cmd_wps_er_stop(struct wpa_ctrl *ctrl, int argc,
1050 return wpa_ctrl_command(ctrl, "WPS_ER_STOP");
1055 static int wpa_cli_cmd_wps_er_pin(struct wpa_ctrl *ctrl, int argc,
1059 printf("Invalid WPS_ER_PIN command: need at least two "
1061 "- UUID: use 'any' to select any\n"
1062 "- PIN: Enrollee PIN\n"
1063 "optional: - Enrollee MAC address\n");
1067 return wpa_cli_cmd(ctrl, "WPS_ER_PIN", 2, argc, argv);
1071 static int wpa_cli_cmd_wps_er_pbc(struct wpa_ctrl *ctrl, int argc,
1074 return wpa_cli_cmd(ctrl, "WPS_ER_PBC", 1, argc, argv);
1078 static int wpa_cli_cmd_wps_er_learn(struct wpa_ctrl *ctrl, int argc,
1082 printf("Invalid WPS_ER_LEARN command: need two arguments:\n"
1083 "- UUID: specify which AP to use\n"
1088 return wpa_cli_cmd(ctrl, "WPS_ER_LEARN", 2, argc, argv);
1092 static int wpa_cli_cmd_wps_er_set_config(struct wpa_ctrl *ctrl, int argc,
1096 printf("Invalid WPS_ER_SET_CONFIG command: need two "
1098 "- UUID: specify which AP to use\n"
1099 "- Network configuration id\n");
1103 return wpa_cli_cmd(ctrl, "WPS_ER_SET_CONFIG", 2, argc, argv);
1107 static int wpa_cli_cmd_wps_er_config(struct wpa_ctrl *ctrl, int argc,
1113 if (argc == 5 || argc == 6) {
1114 char ssid_hex[2 * SSID_MAX_LEN + 1];
1115 char key_hex[2 * 64 + 1];
1119 for (i = 0; i < SSID_MAX_LEN; i++) {
1120 if (argv[2][i] == '\0')
1122 os_snprintf(&ssid_hex[i * 2], 3, "%02x", argv[2][i]);
1127 for (i = 0; i < 64; i++) {
1128 if (argv[5][i] == '\0')
1130 os_snprintf(&key_hex[i * 2], 3, "%02x",
1135 res = os_snprintf(cmd, sizeof(cmd),
1136 "WPS_ER_CONFIG %s %s %s %s %s %s",
1137 argv[0], argv[1], ssid_hex, argv[3], argv[4],
1140 printf("Invalid WPS_ER_CONFIG command: need six arguments:\n"
1144 "- new auth (OPEN, WPAPSK, WPA2PSK)\n"
1145 "- new encr (NONE, WEP, TKIP, CCMP)\n"
1150 if (os_snprintf_error(sizeof(cmd), res)) {
1151 printf("Too long WPS_ER_CONFIG command.\n");
1154 return wpa_ctrl_command(ctrl, cmd);
1158 #ifdef CONFIG_WPS_NFC
1159 static int wpa_cli_cmd_wps_er_nfc_config_token(struct wpa_ctrl *ctrl, int argc,
1163 printf("Invalid WPS_ER_NFC_CONFIG_TOKEN command: need two "
1165 "- WPS/NDEF: token format\n"
1166 "- UUID: specify which AP to use\n");
1170 return wpa_cli_cmd(ctrl, "WPS_ER_NFC_CONFIG_TOKEN", 2, argc, argv);
1172 #endif /* CONFIG_WPS_NFC */
1175 static int wpa_cli_cmd_ibss_rsn(struct wpa_ctrl *ctrl, int argc, char *argv[])
1177 return wpa_cli_cmd(ctrl, "IBSS_RSN", 1, argc, argv);
1181 static int wpa_cli_cmd_level(struct wpa_ctrl *ctrl, int argc, char *argv[])
1183 return wpa_cli_cmd(ctrl, "LEVEL", 1, argc, argv);
1187 static int wpa_cli_cmd_identity(struct wpa_ctrl *ctrl, int argc, char *argv[])
1189 char cmd[256], *pos, *end;
1193 printf("Invalid IDENTITY command: needs two arguments "
1194 "(network id and identity)\n");
1198 end = cmd + sizeof(cmd);
1200 ret = os_snprintf(pos, end - pos, WPA_CTRL_RSP "IDENTITY-%s:%s",
1202 if (os_snprintf_error(end - pos, ret)) {
1203 printf("Too long IDENTITY command.\n");
1207 for (i = 2; i < argc; i++) {
1208 ret = os_snprintf(pos, end - pos, " %s", argv[i]);
1209 if (os_snprintf_error(end - pos, ret)) {
1210 printf("Too long IDENTITY command.\n");
1216 return wpa_ctrl_command(ctrl, cmd);
1220 static int wpa_cli_cmd_password(struct wpa_ctrl *ctrl, int argc, char *argv[])
1222 char cmd[256], *pos, *end;
1226 printf("Invalid PASSWORD command: needs two arguments "
1227 "(network id and password)\n");
1231 end = cmd + sizeof(cmd);
1233 ret = os_snprintf(pos, end - pos, WPA_CTRL_RSP "PASSWORD-%s:%s",
1235 if (os_snprintf_error(end - pos, ret)) {
1236 printf("Too long PASSWORD command.\n");
1240 for (i = 2; i < argc; i++) {
1241 ret = os_snprintf(pos, end - pos, " %s", argv[i]);
1242 if (os_snprintf_error(end - pos, ret)) {
1243 printf("Too long PASSWORD command.\n");
1249 return wpa_ctrl_command(ctrl, cmd);
1253 static int wpa_cli_cmd_new_password(struct wpa_ctrl *ctrl, int argc,
1256 char cmd[256], *pos, *end;
1260 printf("Invalid NEW_PASSWORD command: needs two arguments "
1261 "(network id and password)\n");
1265 end = cmd + sizeof(cmd);
1267 ret = os_snprintf(pos, end - pos, WPA_CTRL_RSP "NEW_PASSWORD-%s:%s",
1269 if (os_snprintf_error(end - pos, ret)) {
1270 printf("Too long NEW_PASSWORD command.\n");
1274 for (i = 2; i < argc; i++) {
1275 ret = os_snprintf(pos, end - pos, " %s", argv[i]);
1276 if (os_snprintf_error(end - pos, ret)) {
1277 printf("Too long NEW_PASSWORD command.\n");
1283 return wpa_ctrl_command(ctrl, cmd);
1287 static int wpa_cli_cmd_pin(struct wpa_ctrl *ctrl, int argc, char *argv[])
1289 char cmd[256], *pos, *end;
1293 printf("Invalid PIN command: needs two arguments "
1294 "(network id and pin)\n");
1298 end = cmd + sizeof(cmd);
1300 ret = os_snprintf(pos, end - pos, WPA_CTRL_RSP "PIN-%s:%s",
1302 if (os_snprintf_error(end - pos, ret)) {
1303 printf("Too long PIN command.\n");
1307 for (i = 2; i < argc; i++) {
1308 ret = os_snprintf(pos, end - pos, " %s", argv[i]);
1309 if (os_snprintf_error(end - pos, ret)) {
1310 printf("Too long PIN command.\n");
1315 return wpa_ctrl_command(ctrl, cmd);
1319 static int wpa_cli_cmd_otp(struct wpa_ctrl *ctrl, int argc, char *argv[])
1321 char cmd[256], *pos, *end;
1325 printf("Invalid OTP command: needs two arguments (network "
1326 "id and password)\n");
1330 end = cmd + sizeof(cmd);
1332 ret = os_snprintf(pos, end - pos, WPA_CTRL_RSP "OTP-%s:%s",
1334 if (os_snprintf_error(end - pos, ret)) {
1335 printf("Too long OTP command.\n");
1339 for (i = 2; i < argc; i++) {
1340 ret = os_snprintf(pos, end - pos, " %s", argv[i]);
1341 if (os_snprintf_error(end - pos, ret)) {
1342 printf("Too long OTP command.\n");
1348 return wpa_ctrl_command(ctrl, cmd);
1352 static int wpa_cli_cmd_sim(struct wpa_ctrl *ctrl, int argc, char *argv[])
1354 char cmd[256], *pos, *end;
1358 printf("Invalid SIM command: needs two arguments "
1359 "(network id and SIM operation response)\n");
1363 end = cmd + sizeof(cmd);
1365 ret = os_snprintf(pos, end - pos, WPA_CTRL_RSP "SIM-%s:%s",
1367 if (os_snprintf_error(end - pos, ret)) {
1368 printf("Too long SIM command.\n");
1372 for (i = 2; i < argc; i++) {
1373 ret = os_snprintf(pos, end - pos, " %s", argv[i]);
1374 if (os_snprintf_error(end - pos, ret)) {
1375 printf("Too long SIM command.\n");
1380 return wpa_ctrl_command(ctrl, cmd);
1384 static int wpa_cli_cmd_passphrase(struct wpa_ctrl *ctrl, int argc,
1387 char cmd[256], *pos, *end;
1391 printf("Invalid PASSPHRASE command: needs two arguments "
1392 "(network id and passphrase)\n");
1396 end = cmd + sizeof(cmd);
1398 ret = os_snprintf(pos, end - pos, WPA_CTRL_RSP "PASSPHRASE-%s:%s",
1400 if (os_snprintf_error(end - pos, ret)) {
1401 printf("Too long PASSPHRASE command.\n");
1405 for (i = 2; i < argc; i++) {
1406 ret = os_snprintf(pos, end - pos, " %s", argv[i]);
1407 if (os_snprintf_error(end - pos, ret)) {
1408 printf("Too long PASSPHRASE command.\n");
1414 return wpa_ctrl_command(ctrl, cmd);
1418 static int wpa_cli_cmd_bssid(struct wpa_ctrl *ctrl, int argc, char *argv[])
1421 printf("Invalid BSSID command: needs two arguments (network "
1426 return wpa_cli_cmd(ctrl, "BSSID", 2, argc, argv);
1430 static int wpa_cli_cmd_blacklist(struct wpa_ctrl *ctrl, int argc, char *argv[])
1432 return wpa_cli_cmd(ctrl, "BLACKLIST", 0, argc, argv);
1436 static int wpa_cli_cmd_log_level(struct wpa_ctrl *ctrl, int argc, char *argv[])
1438 return wpa_cli_cmd(ctrl, "LOG_LEVEL", 0, argc, argv);
1442 static int wpa_cli_cmd_list_networks(struct wpa_ctrl *ctrl, int argc,
1445 return wpa_ctrl_command(ctrl, "LIST_NETWORKS");
1449 static int wpa_cli_cmd_select_network(struct wpa_ctrl *ctrl, int argc,
1452 return wpa_cli_cmd(ctrl, "SELECT_NETWORK", 1, argc, argv);
1456 static int wpa_cli_cmd_enable_network(struct wpa_ctrl *ctrl, int argc,
1459 return wpa_cli_cmd(ctrl, "ENABLE_NETWORK", 1, argc, argv);
1463 static int wpa_cli_cmd_disable_network(struct wpa_ctrl *ctrl, int argc,
1466 return wpa_cli_cmd(ctrl, "DISABLE_NETWORK", 1, argc, argv);
1470 static int wpa_cli_cmd_add_network(struct wpa_ctrl *ctrl, int argc,
1473 int res = wpa_ctrl_command(ctrl, "ADD_NETWORK");
1475 update_networks(ctrl);
1480 static int wpa_cli_cmd_remove_network(struct wpa_ctrl *ctrl, int argc,
1483 int res = wpa_cli_cmd(ctrl, "REMOVE_NETWORK", 1, argc, argv);
1485 update_networks(ctrl);
1490 static void wpa_cli_show_network_variables(void)
1492 printf("set_network variables:\n"
1493 " ssid (network name, SSID)\n"
1494 " psk (WPA passphrase or pre-shared key)\n"
1495 " key_mgmt (key management protocol)\n"
1496 " identity (EAP identity)\n"
1497 " password (EAP password)\n"
1500 "Note: Values are entered in the same format as the "
1501 "configuration file is using,\n"
1502 "i.e., strings values need to be inside double quotation "
1504 "For example: set_network 1 ssid \"network name\"\n"
1506 "Please see wpa_supplicant.conf documentation for full list "
1507 "of\navailable variables.\n");
1511 static int wpa_cli_cmd_set_network(struct wpa_ctrl *ctrl, int argc,
1515 wpa_cli_show_network_variables();
1520 printf("Invalid SET_NETWORK command: needs three arguments\n"
1521 "(network id, variable name, and value)\n");
1525 return wpa_cli_cmd(ctrl, "SET_NETWORK", 3, argc, argv);
1529 static int wpa_cli_cmd_get_network(struct wpa_ctrl *ctrl, int argc,
1533 wpa_cli_show_network_variables();
1538 printf("Invalid GET_NETWORK command: needs two arguments\n"
1539 "(network id and variable name)\n");
1543 return wpa_cli_cmd(ctrl, "GET_NETWORK", 2, argc, argv);
1547 static const char *network_fields[] = {
1548 "ssid", "scan_ssid", "bssid", "bssid_blacklist",
1549 "bssid_whitelist", "psk", "proto", "key_mgmt",
1550 "bg_scan_period", "pairwise", "group", "auth_alg", "scan_freq",
1552 #ifdef IEEE8021X_EAPOL
1553 "eap", "identity", "anonymous_identity", "password", "ca_cert",
1554 "ca_path", "client_cert", "private_key", "private_key_passwd",
1555 "dh_file", "subject_match", "altsubject_match",
1556 "domain_suffix_match", "domain_match", "ca_cert2", "ca_path2",
1557 "client_cert2", "private_key2", "private_key2_passwd",
1558 "dh_file2", "subject_match2", "altsubject_match2",
1559 "domain_suffix_match2", "domain_match2", "phase1", "phase2",
1560 "pcsc", "pin", "engine_id", "key_id", "cert_id", "ca_cert_id",
1561 "pin2", "engine2_id", "key2_id", "cert2_id", "ca_cert2_id",
1562 "engine", "engine2", "eapol_flags", "sim_num",
1563 "openssl_ciphers", "erp",
1564 #endif /* IEEE8021X_EAPOL */
1565 "wep_key0", "wep_key1", "wep_key2", "wep_key3",
1566 "wep_tx_keyidx", "priority",
1567 #ifdef IEEE8021X_EAPOL
1568 "eap_workaround", "pac_file", "fragment_size", "ocsp",
1569 #endif /* IEEE8021X_EAPOL */
1571 "mode", "no_auto_peer",
1572 #else /* CONFIG_MESH */
1574 #endif /* CONFIG_MESH */
1575 "proactive_key_caching", "disabled", "id_str",
1576 #ifdef CONFIG_IEEE80211W
1578 #endif /* CONFIG_IEEE80211W */
1579 "peerkey", "mixed_cell", "frequency", "fixed_freq",
1581 "mesh_basic_rates", "dot11MeshMaxRetries",
1582 "dot11MeshRetryTimeout", "dot11MeshConfirmTimeout",
1583 "dot11MeshHoldingTimeout",
1584 #endif /* CONFIG_MESH */
1585 "wpa_ptk_rekey", "bgscan", "ignore_broadcast_ssid",
1587 "go_p2p_dev_addr", "p2p_client_list", "psk_list",
1588 #endif /* CONFIG_P2P */
1589 #ifdef CONFIG_HT_OVERRIDES
1590 "disable_ht", "disable_ht40", "disable_sgi", "disable_ldpc",
1591 "ht40_intolerant", "disable_max_amsdu", "ampdu_factor",
1592 "ampdu_density", "ht_mcs",
1593 #endif /* CONFIG_HT_OVERRIDES */
1594 #ifdef CONFIG_VHT_OVERRIDES
1595 "disable_vht", "vht_capa", "vht_capa_mask", "vht_rx_mcs_nss_1",
1596 "vht_rx_mcs_nss_2", "vht_rx_mcs_nss_3", "vht_rx_mcs_nss_4",
1597 "vht_rx_mcs_nss_5", "vht_rx_mcs_nss_6", "vht_rx_mcs_nss_7",
1598 "vht_rx_mcs_nss_8", "vht_tx_mcs_nss_1", "vht_tx_mcs_nss_2",
1599 "vht_tx_mcs_nss_3", "vht_tx_mcs_nss_4", "vht_tx_mcs_nss_5",
1600 "vht_tx_mcs_nss_6", "vht_tx_mcs_nss_7", "vht_tx_mcs_nss_8",
1601 #endif /* CONFIG_VHT_OVERRIDES */
1602 "ap_max_inactivity", "dtim_period", "beacon_int",
1603 #ifdef CONFIG_MACSEC
1605 #endif /* CONFIG_MACSEC */
1607 "update_identifier",
1608 #endif /* CONFIG_HS20 */
1613 static char ** wpa_cli_complete_network(const char *str, int pos)
1615 int arg = get_cmd_arg_num(str, pos);
1616 int i, num_fields = ARRAY_SIZE(network_fields);
1621 res = cli_txt_list_array(&networks);
1624 res = os_calloc(num_fields + 1, sizeof(char *));
1627 for (i = 0; i < num_fields; i++) {
1628 res[i] = os_strdup(network_fields[i]);
1637 static char ** wpa_cli_complete_network_id(const char *str, int pos)
1639 int arg = get_cmd_arg_num(str, pos);
1641 return cli_txt_list_array(&networks);
1646 static int wpa_cli_cmd_dup_network(struct wpa_ctrl *ctrl, int argc,
1650 wpa_cli_show_network_variables();
1655 printf("Invalid DUP_NETWORK command: needs three arguments\n"
1656 "(src netid, dest netid, and variable name)\n");
1660 return wpa_cli_cmd(ctrl, "DUP_NETWORK", 3, argc, argv);
1664 static char ** wpa_cli_complete_dup_network(const char *str, int pos)
1666 int arg = get_cmd_arg_num(str, pos);
1667 int i, num_fields = ARRAY_SIZE(network_fields);
1673 res = cli_txt_list_array(&networks);
1676 res = os_calloc(num_fields + 1, sizeof(char *));
1679 for (i = 0; i < num_fields; i++) {
1680 res[i] = os_strdup(network_fields[i]);
1689 static int wpa_cli_cmd_list_creds(struct wpa_ctrl *ctrl, int argc,
1692 return wpa_ctrl_command(ctrl, "LIST_CREDS");
1696 static int wpa_cli_cmd_add_cred(struct wpa_ctrl *ctrl, int argc, char *argv[])
1698 return wpa_ctrl_command(ctrl, "ADD_CRED");
1702 static int wpa_cli_cmd_remove_cred(struct wpa_ctrl *ctrl, int argc,
1705 return wpa_cli_cmd(ctrl, "REMOVE_CRED", 1, argc, argv);
1709 static int wpa_cli_cmd_set_cred(struct wpa_ctrl *ctrl, int argc, char *argv[])
1712 printf("Invalid SET_CRED command: needs three arguments\n"
1713 "(cred id, variable name, and value)\n");
1717 return wpa_cli_cmd(ctrl, "SET_CRED", 3, argc, argv);
1721 static int wpa_cli_cmd_get_cred(struct wpa_ctrl *ctrl, int argc, char *argv[])
1724 printf("Invalid GET_CRED command: needs two arguments\n"
1725 "(cred id, variable name)\n");
1729 return wpa_cli_cmd(ctrl, "GET_CRED", 2, argc, argv);
1733 static int wpa_cli_cmd_disconnect(struct wpa_ctrl *ctrl, int argc,
1736 return wpa_ctrl_command(ctrl, "DISCONNECT");
1740 static int wpa_cli_cmd_reconnect(struct wpa_ctrl *ctrl, int argc,
1743 return wpa_ctrl_command(ctrl, "RECONNECT");
1747 static int wpa_cli_cmd_save_config(struct wpa_ctrl *ctrl, int argc,
1750 return wpa_ctrl_command(ctrl, "SAVE_CONFIG");
1754 static int wpa_cli_cmd_scan(struct wpa_ctrl *ctrl, int argc, char *argv[])
1756 return wpa_cli_cmd(ctrl, "SCAN", 0, argc, argv);
1760 static int wpa_cli_cmd_scan_results(struct wpa_ctrl *ctrl, int argc,
1763 return wpa_ctrl_command(ctrl, "SCAN_RESULTS");
1767 static int wpa_cli_cmd_bss(struct wpa_ctrl *ctrl, int argc, char *argv[])
1769 return wpa_cli_cmd(ctrl, "BSS", 1, argc, argv);
1773 static char ** wpa_cli_complete_bss(const char *str, int pos)
1775 int arg = get_cmd_arg_num(str, pos);
1780 res = cli_txt_list_array(&bsses);
1788 static int wpa_cli_cmd_get_capability(struct wpa_ctrl *ctrl, int argc,
1791 if (argc < 1 || argc > 2) {
1792 printf("Invalid GET_CAPABILITY command: need either one or "
1797 if ((argc == 2) && os_strcmp(argv[1], "strict") != 0) {
1798 printf("Invalid GET_CAPABILITY command: second argument, "
1799 "if any, must be 'strict'\n");
1803 return wpa_cli_cmd(ctrl, "GET_CAPABILITY", 1, argc, argv);
1807 static int wpa_cli_list_interfaces(struct wpa_ctrl *ctrl)
1809 printf("Available interfaces:\n");
1810 return wpa_ctrl_command(ctrl, "INTERFACES");
1814 static int wpa_cli_cmd_interface(struct wpa_ctrl *ctrl, int argc, char *argv[])
1817 wpa_cli_list_interfaces(ctrl);
1821 wpa_cli_close_connection();
1822 os_free(ctrl_ifname);
1823 ctrl_ifname = os_strdup(argv[0]);
1825 printf("Failed to allocate memory\n");
1829 if (wpa_cli_open_connection(ctrl_ifname, 1) == 0) {
1830 printf("Connected to interface '%s.\n", ctrl_ifname);
1832 printf("Could not connect to interface '%s' - re-trying\n",
1839 static int wpa_cli_cmd_reconfigure(struct wpa_ctrl *ctrl, int argc,
1842 return wpa_ctrl_command(ctrl, "RECONFIGURE");
1846 static int wpa_cli_cmd_terminate(struct wpa_ctrl *ctrl, int argc,
1849 return wpa_ctrl_command(ctrl, "TERMINATE");
1853 static int wpa_cli_cmd_interface_add(struct wpa_ctrl *ctrl, int argc,
1860 printf("Invalid INTERFACE_ADD command: needs at least one "
1861 "argument (interface name)\n"
1862 "All arguments: ifname confname driver ctrl_interface "
1863 "driver_param bridge_name [create]\n");
1868 * INTERFACE_ADD <ifname>TAB<confname>TAB<driver>TAB<ctrl_interface>TAB
1869 * <driver_param>TAB<bridge_name>[TAB<create>]
1871 res = os_snprintf(cmd, sizeof(cmd),
1872 "INTERFACE_ADD %s\t%s\t%s\t%s\t%s\t%s\t%s",
1874 argc > 1 ? argv[1] : "", argc > 2 ? argv[2] : "",
1875 argc > 3 ? argv[3] : "", argc > 4 ? argv[4] : "",
1876 argc > 5 ? argv[5] : "", argc > 6 ? argv[6] : "");
1877 if (os_snprintf_error(sizeof(cmd), res))
1879 cmd[sizeof(cmd) - 1] = '\0';
1880 return wpa_ctrl_command(ctrl, cmd);
1884 static int wpa_cli_cmd_interface_remove(struct wpa_ctrl *ctrl, int argc,
1887 return wpa_cli_cmd(ctrl, "INTERFACE_REMOVE", 1, argc, argv);
1891 static int wpa_cli_cmd_interface_list(struct wpa_ctrl *ctrl, int argc,
1894 return wpa_ctrl_command(ctrl, "INTERFACE_LIST");
1899 static int wpa_cli_cmd_sta(struct wpa_ctrl *ctrl, int argc, char *argv[])
1901 return wpa_cli_cmd(ctrl, "STA", 1, argc, argv);
1905 static int wpa_ctrl_command_sta(struct wpa_ctrl *ctrl, char *cmd,
1906 char *addr, size_t addr_len)
1908 char buf[4096], *pos;
1912 if (ctrl_conn == NULL) {
1913 printf("Not connected to hostapd - command dropped.\n");
1916 len = sizeof(buf) - 1;
1917 ret = wpa_ctrl_request(ctrl, cmd, os_strlen(cmd), buf, &len,
1920 printf("'%s' command timed out.\n", cmd);
1922 } else if (ret < 0) {
1923 printf("'%s' command failed.\n", cmd);
1928 if (os_memcmp(buf, "FAIL", 4) == 0)
1933 while (*pos != '\0' && *pos != '\n')
1936 os_strlcpy(addr, buf, addr_len);
1941 static int wpa_cli_cmd_all_sta(struct wpa_ctrl *ctrl, int argc, char *argv[])
1943 char addr[32], cmd[64];
1945 if (wpa_ctrl_command_sta(ctrl, "STA-FIRST", addr, sizeof(addr)))
1948 os_snprintf(cmd, sizeof(cmd), "STA-NEXT %s", addr);
1949 } while (wpa_ctrl_command_sta(ctrl, cmd, addr, sizeof(addr)) == 0);
1955 static int wpa_cli_cmd_deauthenticate(struct wpa_ctrl *ctrl, int argc,
1958 return wpa_cli_cmd(ctrl, "DEAUTHENTICATE", 1, argc, argv);
1962 static int wpa_cli_cmd_disassociate(struct wpa_ctrl *ctrl, int argc,
1965 return wpa_cli_cmd(ctrl, "DISASSOCIATE", 1, argc, argv);
1968 static int wpa_cli_cmd_chanswitch(struct wpa_ctrl *ctrl, int argc,
1971 return wpa_cli_cmd(ctrl, "CHAN_SWITCH", 2, argc, argv);
1974 #endif /* CONFIG_AP */
1977 static int wpa_cli_cmd_suspend(struct wpa_ctrl *ctrl, int argc, char *argv[])
1979 return wpa_ctrl_command(ctrl, "SUSPEND");
1983 static int wpa_cli_cmd_resume(struct wpa_ctrl *ctrl, int argc, char *argv[])
1985 return wpa_ctrl_command(ctrl, "RESUME");
1989 #ifdef CONFIG_TESTING_OPTIONS
1990 static int wpa_cli_cmd_drop_sa(struct wpa_ctrl *ctrl, int argc, char *argv[])
1992 return wpa_ctrl_command(ctrl, "DROP_SA");
1994 #endif /* CONFIG_TESTING_OPTIONS */
1997 static int wpa_cli_cmd_roam(struct wpa_ctrl *ctrl, int argc, char *argv[])
1999 return wpa_cli_cmd(ctrl, "ROAM", 1, argc, argv);
2005 static int wpa_cli_cmd_mesh_interface_add(struct wpa_ctrl *ctrl, int argc,
2008 return wpa_cli_cmd(ctrl, "MESH_INTERFACE_ADD", 0, argc, argv);
2012 static int wpa_cli_cmd_mesh_group_add(struct wpa_ctrl *ctrl, int argc,
2015 return wpa_cli_cmd(ctrl, "MESH_GROUP_ADD", 1, argc, argv);
2019 static int wpa_cli_cmd_mesh_group_remove(struct wpa_ctrl *ctrl, int argc,
2022 return wpa_cli_cmd(ctrl, "MESH_GROUP_REMOVE", 1, argc, argv);
2025 #endif /* CONFIG_MESH */
2030 static int wpa_cli_cmd_p2p_find(struct wpa_ctrl *ctrl, int argc, char *argv[])
2032 return wpa_cli_cmd(ctrl, "P2P_FIND", 0, argc, argv);
2036 static char ** wpa_cli_complete_p2p_find(const char *str, int pos)
2039 int arg = get_cmd_arg_num(str, pos);
2041 res = os_calloc(6, sizeof(char *));
2044 res[0] = os_strdup("type=social");
2045 if (res[0] == NULL) {
2049 res[1] = os_strdup("type=progressive");
2052 res[2] = os_strdup("delay=");
2055 res[3] = os_strdup("dev_id=");
2059 res[4] = os_strdup("[timeout]");
2065 static int wpa_cli_cmd_p2p_stop_find(struct wpa_ctrl *ctrl, int argc,
2068 return wpa_ctrl_command(ctrl, "P2P_STOP_FIND");
2072 static int wpa_cli_cmd_p2p_asp_provision(struct wpa_ctrl *ctrl, int argc,
2075 return wpa_cli_cmd(ctrl, "P2P_ASP_PROVISION", 3, argc, argv);
2079 static int wpa_cli_cmd_p2p_asp_provision_resp(struct wpa_ctrl *ctrl, int argc,
2082 return wpa_cli_cmd(ctrl, "P2P_ASP_PROVISION_RESP", 2, argc, argv);
2086 static int wpa_cli_cmd_p2p_connect(struct wpa_ctrl *ctrl, int argc,
2089 return wpa_cli_cmd(ctrl, "P2P_CONNECT", 2, argc, argv);
2093 static char ** wpa_cli_complete_p2p_connect(const char *str, int pos)
2095 int arg = get_cmd_arg_num(str, pos);
2100 res = cli_txt_list_array(&p2p_peers);
2108 static int wpa_cli_cmd_p2p_listen(struct wpa_ctrl *ctrl, int argc,
2111 return wpa_cli_cmd(ctrl, "P2P_LISTEN", 0, argc, argv);
2115 static int wpa_cli_cmd_p2p_group_remove(struct wpa_ctrl *ctrl, int argc,
2118 return wpa_cli_cmd(ctrl, "P2P_GROUP_REMOVE", 1, argc, argv);
2122 static char ** wpa_cli_complete_p2p_group_remove(const char *str, int pos)
2124 int arg = get_cmd_arg_num(str, pos);
2129 res = cli_txt_list_array(&p2p_groups);
2137 static int wpa_cli_cmd_p2p_group_add(struct wpa_ctrl *ctrl, int argc,
2140 return wpa_cli_cmd(ctrl, "P2P_GROUP_ADD", 0, argc, argv);
2144 static int wpa_cli_cmd_p2p_prov_disc(struct wpa_ctrl *ctrl, int argc,
2147 if (argc != 2 && argc != 3) {
2148 printf("Invalid P2P_PROV_DISC command: needs at least "
2149 "two arguments, address and config method\n"
2150 "(display, keypad, or pbc) and an optional join\n");
2154 return wpa_cli_cmd(ctrl, "P2P_PROV_DISC", 2, argc, argv);
2158 static int wpa_cli_cmd_p2p_get_passphrase(struct wpa_ctrl *ctrl, int argc,
2161 return wpa_ctrl_command(ctrl, "P2P_GET_PASSPHRASE");
2165 static int wpa_cli_cmd_p2p_serv_disc_req(struct wpa_ctrl *ctrl, int argc,
2171 printf("Invalid P2P_SERV_DISC_REQ command: needs two "
2172 "or more arguments (address and TLVs)\n");
2176 if (write_cmd(cmd, sizeof(cmd), "P2P_SERV_DISC_REQ", argc, argv) < 0)
2178 return wpa_ctrl_command(ctrl, cmd);
2182 static int wpa_cli_cmd_p2p_serv_disc_cancel_req(struct wpa_ctrl *ctrl,
2183 int argc, char *argv[])
2185 return wpa_cli_cmd(ctrl, "P2P_SERV_DISC_CANCEL_REQ", 1, argc, argv);
2189 static int wpa_cli_cmd_p2p_serv_disc_resp(struct wpa_ctrl *ctrl, int argc,
2196 printf("Invalid P2P_SERV_DISC_RESP command: needs four "
2197 "arguments (freq, address, dialog token, and TLVs)\n");
2201 res = os_snprintf(cmd, sizeof(cmd), "P2P_SERV_DISC_RESP %s %s %s %s",
2202 argv[0], argv[1], argv[2], argv[3]);
2203 if (os_snprintf_error(sizeof(cmd), res))
2205 cmd[sizeof(cmd) - 1] = '\0';
2206 return wpa_ctrl_command(ctrl, cmd);
2210 static int wpa_cli_cmd_p2p_service_update(struct wpa_ctrl *ctrl, int argc,
2213 return wpa_ctrl_command(ctrl, "P2P_SERVICE_UPDATE");
2217 static int wpa_cli_cmd_p2p_serv_disc_external(struct wpa_ctrl *ctrl,
2218 int argc, char *argv[])
2220 return wpa_cli_cmd(ctrl, "P2P_SERV_DISC_EXTERNAL", 1, argc, argv);
2224 static int wpa_cli_cmd_p2p_service_flush(struct wpa_ctrl *ctrl, int argc,
2227 return wpa_ctrl_command(ctrl, "P2P_SERVICE_FLUSH");
2231 static int wpa_cli_cmd_p2p_service_add(struct wpa_ctrl *ctrl, int argc,
2235 printf("Invalid P2P_SERVICE_ADD command: needs 3-6 arguments\n");
2239 return wpa_cli_cmd(ctrl, "P2P_SERVICE_ADD", 3, argc, argv);
2243 static int wpa_cli_cmd_p2p_service_rep(struct wpa_ctrl *ctrl, int argc,
2246 if (argc < 5 || argc > 6) {
2247 printf("Invalid P2P_SERVICE_REP command: needs 5-6 "
2252 return wpa_cli_cmd(ctrl, "P2P_SERVICE_REP", 5, argc, argv);
2256 static int wpa_cli_cmd_p2p_service_del(struct wpa_ctrl *ctrl, int argc,
2262 if (argc != 2 && argc != 3) {
2263 printf("Invalid P2P_SERVICE_DEL command: needs two or three "
2269 res = os_snprintf(cmd, sizeof(cmd),
2270 "P2P_SERVICE_DEL %s %s %s",
2271 argv[0], argv[1], argv[2]);
2273 res = os_snprintf(cmd, sizeof(cmd),
2274 "P2P_SERVICE_DEL %s %s",
2276 if (os_snprintf_error(sizeof(cmd), res))
2278 cmd[sizeof(cmd) - 1] = '\0';
2279 return wpa_ctrl_command(ctrl, cmd);
2283 static int wpa_cli_cmd_p2p_reject(struct wpa_ctrl *ctrl,
2284 int argc, char *argv[])
2286 return wpa_cli_cmd(ctrl, "P2P_REJECT", 1, argc, argv);
2290 static int wpa_cli_cmd_p2p_invite(struct wpa_ctrl *ctrl,
2291 int argc, char *argv[])
2293 return wpa_cli_cmd(ctrl, "P2P_INVITE", 1, argc, argv);
2297 static int wpa_cli_cmd_p2p_peer(struct wpa_ctrl *ctrl, int argc, char *argv[])
2299 return wpa_cli_cmd(ctrl, "P2P_PEER", 1, argc, argv);
2303 static char ** wpa_cli_complete_p2p_peer(const char *str, int pos)
2305 int arg = get_cmd_arg_num(str, pos);
2310 res = cli_txt_list_array(&p2p_peers);
2318 static int wpa_ctrl_command_p2p_peer(struct wpa_ctrl *ctrl, char *cmd,
2319 char *addr, size_t addr_len,
2322 char buf[4096], *pos;
2326 if (ctrl_conn == NULL)
2328 len = sizeof(buf) - 1;
2329 ret = wpa_ctrl_request(ctrl, cmd, os_strlen(cmd), buf, &len,
2332 printf("'%s' command timed out.\n", cmd);
2334 } else if (ret < 0) {
2335 printf("'%s' command failed.\n", cmd);
2340 if (os_memcmp(buf, "FAIL", 4) == 0)
2344 while (*pos != '\0' && *pos != '\n')
2347 os_strlcpy(addr, buf, addr_len);
2348 if (!discovered || os_strstr(pos, "[PROBE_REQ_ONLY]") == NULL)
2349 printf("%s\n", addr);
2354 static int wpa_cli_cmd_p2p_peers(struct wpa_ctrl *ctrl, int argc, char *argv[])
2356 char addr[32], cmd[64];
2359 discovered = argc > 0 && os_strcmp(argv[0], "discovered") == 0;
2361 if (wpa_ctrl_command_p2p_peer(ctrl, "P2P_PEER FIRST",
2362 addr, sizeof(addr), discovered))
2365 os_snprintf(cmd, sizeof(cmd), "P2P_PEER NEXT-%s", addr);
2366 } while (wpa_ctrl_command_p2p_peer(ctrl, cmd, addr, sizeof(addr),
2373 static int wpa_cli_cmd_p2p_set(struct wpa_ctrl *ctrl, int argc, char *argv[])
2375 return wpa_cli_cmd(ctrl, "P2P_SET", 2, argc, argv);
2379 static char ** wpa_cli_complete_p2p_set(const char *str, int pos)
2381 int arg = get_cmd_arg_num(str, pos);
2382 const char *fields[] = {
2402 int i, num_fields = ARRAY_SIZE(fields);
2405 char **res = os_calloc(num_fields + 1, sizeof(char *));
2408 for (i = 0; i < num_fields; i++) {
2409 res[i] = os_strdup(fields[i]);
2416 if (arg == 2 && os_strncasecmp(str, "p2p_set peer_filter ", 20) == 0)
2417 return cli_txt_list_array(&p2p_peers);
2423 static int wpa_cli_cmd_p2p_flush(struct wpa_ctrl *ctrl, int argc, char *argv[])
2425 return wpa_ctrl_command(ctrl, "P2P_FLUSH");
2429 static int wpa_cli_cmd_p2p_cancel(struct wpa_ctrl *ctrl, int argc,
2432 return wpa_ctrl_command(ctrl, "P2P_CANCEL");
2436 static int wpa_cli_cmd_p2p_unauthorize(struct wpa_ctrl *ctrl, int argc,
2439 return wpa_cli_cmd(ctrl, "P2P_UNAUTHORIZE", 1, argc, argv);
2443 static int wpa_cli_cmd_p2p_presence_req(struct wpa_ctrl *ctrl, int argc,
2446 if (argc != 0 && argc != 2 && argc != 4) {
2447 printf("Invalid P2P_PRESENCE_REQ command: needs two arguments "
2448 "(preferred duration, interval; in microsecods).\n"
2449 "Optional second pair can be used to provide "
2450 "acceptable values.\n");
2454 return wpa_cli_cmd(ctrl, "P2P_PRESENCE_REQ", 0, argc, argv);
2458 static int wpa_cli_cmd_p2p_ext_listen(struct wpa_ctrl *ctrl, int argc,
2461 if (argc != 0 && argc != 2) {
2462 printf("Invalid P2P_EXT_LISTEN command: needs two arguments "
2463 "(availability period, availability interval; in "
2465 "Extended Listen Timing can be cancelled with this "
2466 "command when used without parameters.\n");
2470 return wpa_cli_cmd(ctrl, "P2P_EXT_LISTEN", 0, argc, argv);
2474 static int wpa_cli_cmd_p2p_remove_client(struct wpa_ctrl *ctrl, int argc,
2477 return wpa_cli_cmd(ctrl, "P2P_REMOVE_CLIENT", 1, argc, argv);
2480 #endif /* CONFIG_P2P */
2482 #ifdef CONFIG_WIFI_DISPLAY
2484 static int wpa_cli_cmd_wfd_subelem_set(struct wpa_ctrl *ctrl, int argc,
2490 if (argc != 1 && argc != 2) {
2491 printf("Invalid WFD_SUBELEM_SET command: needs one or two "
2492 "arguments (subelem, hexdump)\n");
2496 res = os_snprintf(cmd, sizeof(cmd), "WFD_SUBELEM_SET %s %s",
2497 argv[0], argc > 1 ? argv[1] : "");
2498 if (os_snprintf_error(sizeof(cmd), res))
2500 cmd[sizeof(cmd) - 1] = '\0';
2501 return wpa_ctrl_command(ctrl, cmd);
2505 static int wpa_cli_cmd_wfd_subelem_get(struct wpa_ctrl *ctrl, int argc,
2512 printf("Invalid WFD_SUBELEM_GET command: needs one "
2513 "argument (subelem)\n");
2517 res = os_snprintf(cmd, sizeof(cmd), "WFD_SUBELEM_GET %s",
2519 if (os_snprintf_error(sizeof(cmd), res))
2521 cmd[sizeof(cmd) - 1] = '\0';
2522 return wpa_ctrl_command(ctrl, cmd);
2524 #endif /* CONFIG_WIFI_DISPLAY */
2527 #ifdef CONFIG_INTERWORKING
2528 static int wpa_cli_cmd_fetch_anqp(struct wpa_ctrl *ctrl, int argc,
2531 return wpa_ctrl_command(ctrl, "FETCH_ANQP");
2535 static int wpa_cli_cmd_stop_fetch_anqp(struct wpa_ctrl *ctrl, int argc,
2538 return wpa_ctrl_command(ctrl, "STOP_FETCH_ANQP");
2542 static int wpa_cli_cmd_interworking_select(struct wpa_ctrl *ctrl, int argc,
2545 return wpa_cli_cmd(ctrl, "INTERWORKING_SELECT", 0, argc, argv);
2549 static int wpa_cli_cmd_interworking_connect(struct wpa_ctrl *ctrl, int argc,
2552 return wpa_cli_cmd(ctrl, "INTERWORKING_CONNECT", 1, argc, argv);
2556 static int wpa_cli_cmd_interworking_add_network(struct wpa_ctrl *ctrl, int argc,
2559 return wpa_cli_cmd(ctrl, "INTERWORKING_ADD_NETWORK", 1, argc, argv);
2563 static int wpa_cli_cmd_anqp_get(struct wpa_ctrl *ctrl, int argc, char *argv[])
2565 return wpa_cli_cmd(ctrl, "ANQP_GET", 2, argc, argv);
2569 static int wpa_cli_cmd_gas_request(struct wpa_ctrl *ctrl, int argc,
2572 return wpa_cli_cmd(ctrl, "GAS_REQUEST", 2, argc, argv);
2576 static int wpa_cli_cmd_gas_response_get(struct wpa_ctrl *ctrl, int argc,
2579 return wpa_cli_cmd(ctrl, "GAS_RESPONSE_GET", 2, argc, argv);
2581 #endif /* CONFIG_INTERWORKING */
2586 static int wpa_cli_cmd_hs20_anqp_get(struct wpa_ctrl *ctrl, int argc,
2589 return wpa_cli_cmd(ctrl, "HS20_ANQP_GET", 2, argc, argv);
2593 static int wpa_cli_cmd_get_nai_home_realm_list(struct wpa_ctrl *ctrl, int argc,
2599 printf("Command needs one or two arguments (dst mac addr and "
2600 "optional home realm)\n");
2604 if (write_cmd(cmd, sizeof(cmd), "HS20_GET_NAI_HOME_REALM_LIST",
2608 return wpa_ctrl_command(ctrl, cmd);
2612 static int wpa_cli_cmd_hs20_icon_request(struct wpa_ctrl *ctrl, int argc,
2618 printf("Command needs two arguments (dst mac addr and "
2623 if (write_cmd(cmd, sizeof(cmd), "HS20_ICON_REQUEST", argc, argv) < 0)
2626 return wpa_ctrl_command(ctrl, cmd);
2630 static int wpa_cli_cmd_fetch_osu(struct wpa_ctrl *ctrl, int argc, char *argv[])
2632 return wpa_ctrl_command(ctrl, "FETCH_OSU");
2636 static int wpa_cli_cmd_cancel_fetch_osu(struct wpa_ctrl *ctrl, int argc,
2639 return wpa_ctrl_command(ctrl, "CANCEL_FETCH_OSU");
2642 #endif /* CONFIG_HS20 */
2645 static int wpa_cli_cmd_sta_autoconnect(struct wpa_ctrl *ctrl, int argc,
2648 return wpa_cli_cmd(ctrl, "STA_AUTOCONNECT", 1, argc, argv);
2652 static int wpa_cli_cmd_tdls_discover(struct wpa_ctrl *ctrl, int argc,
2655 return wpa_cli_cmd(ctrl, "TDLS_DISCOVER", 1, argc, argv);
2659 static int wpa_cli_cmd_tdls_setup(struct wpa_ctrl *ctrl, int argc,
2662 return wpa_cli_cmd(ctrl, "TDLS_SETUP", 1, argc, argv);
2666 static int wpa_cli_cmd_tdls_teardown(struct wpa_ctrl *ctrl, int argc,
2669 return wpa_cli_cmd(ctrl, "TDLS_TEARDOWN", 1, argc, argv);
2673 static int wpa_cli_cmd_tdls_link_status(struct wpa_ctrl *ctrl, int argc,
2676 return wpa_cli_cmd(ctrl, "TDLS_LINK_STATUS", 1, argc, argv);
2680 static int wpa_cli_cmd_wmm_ac_addts(struct wpa_ctrl *ctrl, int argc,
2683 return wpa_cli_cmd(ctrl, "WMM_AC_ADDTS", 3, argc, argv);
2687 static int wpa_cli_cmd_wmm_ac_delts(struct wpa_ctrl *ctrl, int argc,
2690 return wpa_cli_cmd(ctrl, "WMM_AC_DELTS", 1, argc, argv);
2694 static int wpa_cli_cmd_wmm_ac_status(struct wpa_ctrl *ctrl, int argc,
2697 return wpa_ctrl_command(ctrl, "WMM_AC_STATUS");
2701 static int wpa_cli_cmd_tdls_chan_switch(struct wpa_ctrl *ctrl, int argc,
2704 return wpa_cli_cmd(ctrl, "TDLS_CHAN_SWITCH", 2, argc, argv);
2708 static int wpa_cli_cmd_tdls_cancel_chan_switch(struct wpa_ctrl *ctrl, int argc,
2711 return wpa_cli_cmd(ctrl, "TDLS_CANCEL_CHAN_SWITCH", 1, argc, argv);
2715 static int wpa_cli_cmd_signal_poll(struct wpa_ctrl *ctrl, int argc,
2718 return wpa_ctrl_command(ctrl, "SIGNAL_POLL");
2722 static int wpa_cli_cmd_pktcnt_poll(struct wpa_ctrl *ctrl, int argc,
2725 return wpa_ctrl_command(ctrl, "PKTCNT_POLL");
2729 static int wpa_cli_cmd_reauthenticate(struct wpa_ctrl *ctrl, int argc,
2732 return wpa_ctrl_command(ctrl, "REAUTHENTICATE");
2736 #ifdef CONFIG_AUTOSCAN
2738 static int wpa_cli_cmd_autoscan(struct wpa_ctrl *ctrl, int argc, char *argv[])
2741 return wpa_ctrl_command(ctrl, "AUTOSCAN ");
2743 return wpa_cli_cmd(ctrl, "AUTOSCAN", 0, argc, argv);
2746 #endif /* CONFIG_AUTOSCAN */
2751 static int wpa_cli_cmd_wnm_sleep(struct wpa_ctrl *ctrl, int argc, char *argv[])
2753 return wpa_cli_cmd(ctrl, "WNM_SLEEP", 0, argc, argv);
2757 static int wpa_cli_cmd_wnm_bss_query(struct wpa_ctrl *ctrl, int argc, char *argv[])
2759 return wpa_cli_cmd(ctrl, "WNM_BSS_QUERY", 1, argc, argv);
2762 #endif /* CONFIG_WNM */
2765 static int wpa_cli_cmd_raw(struct wpa_ctrl *ctrl, int argc, char *argv[])
2769 return wpa_cli_cmd(ctrl, argv[0], 0, argc - 1, &argv[1]);
2774 static int wpa_cli_cmd_driver(struct wpa_ctrl *ctrl, int argc, char *argv[])
2776 return wpa_cli_cmd(ctrl, "DRIVER", 1, argc, argv);
2778 #endif /* ANDROID */
2781 static int wpa_cli_cmd_vendor(struct wpa_ctrl *ctrl, int argc, char *argv[])
2783 return wpa_cli_cmd(ctrl, "VENDOR", 1, argc, argv);
2787 static int wpa_cli_cmd_flush(struct wpa_ctrl *ctrl, int argc, char *argv[])
2789 return wpa_ctrl_command(ctrl, "FLUSH");
2793 static int wpa_cli_cmd_radio_work(struct wpa_ctrl *ctrl, int argc, char *argv[])
2795 return wpa_cli_cmd(ctrl, "RADIO_WORK", 1, argc, argv);
2799 static int wpa_cli_cmd_neighbor_rep_request(struct wpa_ctrl *ctrl, int argc,
2802 return wpa_cli_cmd(ctrl, "NEIGHBOR_REP_REQUEST", 0, argc, argv);
2806 static int wpa_cli_cmd_erp_flush(struct wpa_ctrl *ctrl, int argc, char *argv[])
2808 return wpa_ctrl_command(ctrl, "ERP_FLUSH");
2812 static int wpa_cli_cmd_mac_rand_scan(struct wpa_ctrl *ctrl, int argc,
2815 return wpa_cli_cmd(ctrl, "MAC_RAND_SCAN", 1, argc, argv);
2819 static int wpa_cli_cmd_get_pref_freq_list(struct wpa_ctrl *ctrl, int argc,
2822 return wpa_cli_cmd(ctrl, "GET_PREF_FREQ_LIST", 1, argc, argv);
2826 enum wpa_cli_cmd_flags {
2827 cli_cmd_flag_none = 0x00,
2828 cli_cmd_flag_sensitive = 0x01
2831 struct wpa_cli_cmd {
2833 int (*handler)(struct wpa_ctrl *ctrl, int argc, char *argv[]);
2834 char ** (*completion)(const char *str, int pos);
2835 enum wpa_cli_cmd_flags flags;
2839 static const struct wpa_cli_cmd wpa_cli_commands[] = {
2840 { "status", wpa_cli_cmd_status, NULL,
2842 "[verbose] = get current WPA/EAPOL/EAP status" },
2843 { "ifname", wpa_cli_cmd_ifname, NULL,
2845 "= get current interface name" },
2846 { "ping", wpa_cli_cmd_ping, NULL,
2848 "= pings wpa_supplicant" },
2849 { "relog", wpa_cli_cmd_relog, NULL,
2851 "= re-open log-file (allow rolling logs)" },
2852 { "note", wpa_cli_cmd_note, NULL,
2854 "<text> = add a note to wpa_supplicant debug log" },
2855 { "mib", wpa_cli_cmd_mib, NULL,
2857 "= get MIB variables (dot1x, dot11)" },
2858 { "help", wpa_cli_cmd_help, wpa_cli_complete_help,
2860 "[command] = show usage help" },
2861 { "interface", wpa_cli_cmd_interface, NULL,
2863 "[ifname] = show interfaces/select interface" },
2864 { "level", wpa_cli_cmd_level, NULL,
2866 "<debug level> = change debug level" },
2867 { "license", wpa_cli_cmd_license, NULL,
2869 "= show full wpa_cli license" },
2870 { "quit", wpa_cli_cmd_quit, NULL,
2873 { "set", wpa_cli_cmd_set, wpa_cli_complete_set,
2875 "= set variables (shows list of variables when run without "
2877 { "dump", wpa_cli_cmd_dump, NULL,
2879 "= dump config variables" },
2880 { "get", wpa_cli_cmd_get, wpa_cli_complete_get,
2882 "<name> = get information" },
2883 { "logon", wpa_cli_cmd_logon, NULL,
2885 "= IEEE 802.1X EAPOL state machine logon" },
2886 { "logoff", wpa_cli_cmd_logoff, NULL,
2888 "= IEEE 802.1X EAPOL state machine logoff" },
2889 { "pmksa", wpa_cli_cmd_pmksa, NULL,
2891 "= show PMKSA cache" },
2892 { "pmksa_flush", wpa_cli_cmd_pmksa_flush, NULL,
2894 "= flush PMKSA cache entries" },
2895 { "reassociate", wpa_cli_cmd_reassociate, NULL,
2897 "= force reassociation" },
2898 { "reattach", wpa_cli_cmd_reattach, NULL,
2900 "= force reassociation back to the same BSS" },
2901 { "preauthenticate", wpa_cli_cmd_preauthenticate, wpa_cli_complete_bss,
2903 "<BSSID> = force preauthentication" },
2904 { "identity", wpa_cli_cmd_identity, NULL,
2906 "<network id> <identity> = configure identity for an SSID" },
2907 { "password", wpa_cli_cmd_password, NULL,
2908 cli_cmd_flag_sensitive,
2909 "<network id> <password> = configure password for an SSID" },
2910 { "new_password", wpa_cli_cmd_new_password, NULL,
2911 cli_cmd_flag_sensitive,
2912 "<network id> <password> = change password for an SSID" },
2913 { "pin", wpa_cli_cmd_pin, NULL,
2914 cli_cmd_flag_sensitive,
2915 "<network id> <pin> = configure pin for an SSID" },
2916 { "otp", wpa_cli_cmd_otp, NULL,
2917 cli_cmd_flag_sensitive,
2918 "<network id> <password> = configure one-time-password for an SSID"
2920 { "passphrase", wpa_cli_cmd_passphrase, NULL,
2921 cli_cmd_flag_sensitive,
2922 "<network id> <passphrase> = configure private key passphrase\n"
2924 { "sim", wpa_cli_cmd_sim, NULL,
2925 cli_cmd_flag_sensitive,
2926 "<network id> <pin> = report SIM operation result" },
2927 { "bssid", wpa_cli_cmd_bssid, NULL,
2929 "<network id> <BSSID> = set preferred BSSID for an SSID" },
2930 { "blacklist", wpa_cli_cmd_blacklist, wpa_cli_complete_bss,
2932 "<BSSID> = add a BSSID to the blacklist\n"
2933 "blacklist clear = clear the blacklist\n"
2934 "blacklist = display the blacklist" },
2935 { "log_level", wpa_cli_cmd_log_level, NULL,
2937 "<level> [<timestamp>] = update the log level/timestamp\n"
2938 "log_level = display the current log level and log options" },
2939 { "list_networks", wpa_cli_cmd_list_networks, NULL,
2941 "= list configured networks" },
2942 { "select_network", wpa_cli_cmd_select_network,
2943 wpa_cli_complete_network_id,
2945 "<network id> = select a network (disable others)" },
2946 { "enable_network", wpa_cli_cmd_enable_network,
2947 wpa_cli_complete_network_id,
2949 "<network id> = enable a network" },
2950 { "disable_network", wpa_cli_cmd_disable_network,
2951 wpa_cli_complete_network_id,
2953 "<network id> = disable a network" },
2954 { "add_network", wpa_cli_cmd_add_network, NULL,
2956 "= add a network" },
2957 { "remove_network", wpa_cli_cmd_remove_network,
2958 wpa_cli_complete_network_id,
2960 "<network id> = remove a network" },
2961 { "set_network", wpa_cli_cmd_set_network, wpa_cli_complete_network,
2962 cli_cmd_flag_sensitive,
2963 "<network id> <variable> <value> = set network variables (shows\n"
2964 " list of variables when run without arguments)" },
2965 { "get_network", wpa_cli_cmd_get_network, wpa_cli_complete_network,
2967 "<network id> <variable> = get network variables" },
2968 { "dup_network", wpa_cli_cmd_dup_network, wpa_cli_complete_dup_network,
2970 "<src network id> <dst network id> <variable> = duplicate network variables"
2972 { "list_creds", wpa_cli_cmd_list_creds, NULL,
2974 "= list configured credentials" },
2975 { "add_cred", wpa_cli_cmd_add_cred, NULL,
2977 "= add a credential" },
2978 { "remove_cred", wpa_cli_cmd_remove_cred, NULL,
2980 "<cred id> = remove a credential" },
2981 { "set_cred", wpa_cli_cmd_set_cred, NULL,
2982 cli_cmd_flag_sensitive,
2983 "<cred id> <variable> <value> = set credential variables" },
2984 { "get_cred", wpa_cli_cmd_get_cred, NULL,
2986 "<cred id> <variable> = get credential variables" },
2987 { "save_config", wpa_cli_cmd_save_config, NULL,
2989 "= save the current configuration" },
2990 { "disconnect", wpa_cli_cmd_disconnect, NULL,
2992 "= disconnect and wait for reassociate/reconnect command before\n"
2994 { "reconnect", wpa_cli_cmd_reconnect, NULL,
2996 "= like reassociate, but only takes effect if already disconnected"
2998 { "scan", wpa_cli_cmd_scan, NULL,
3000 "= request new BSS scan" },
3001 { "scan_results", wpa_cli_cmd_scan_results, NULL,
3003 "= get latest scan results" },
3004 { "bss", wpa_cli_cmd_bss, wpa_cli_complete_bss,
3006 "<<idx> | <bssid>> = get detailed scan result info" },
3007 { "get_capability", wpa_cli_cmd_get_capability, NULL,
3009 "<eap/pairwise/group/key_mgmt/proto/auth_alg/channels/freq/modes> "
3010 "= get capabilities" },
3011 { "reconfigure", wpa_cli_cmd_reconfigure, NULL,
3013 "= force wpa_supplicant to re-read its configuration file" },
3014 { "terminate", wpa_cli_cmd_terminate, NULL,
3016 "= terminate wpa_supplicant" },
3017 { "interface_add", wpa_cli_cmd_interface_add, NULL,
3019 "<ifname> <confname> <driver> <ctrl_interface> <driver_param>\n"
3020 " <bridge_name> = adds new interface, all parameters but <ifname>\n"
3022 { "interface_remove", wpa_cli_cmd_interface_remove, NULL,
3024 "<ifname> = removes the interface" },
3025 { "interface_list", wpa_cli_cmd_interface_list, NULL,
3027 "= list available interfaces" },
3028 { "ap_scan", wpa_cli_cmd_ap_scan, NULL,
3030 "<value> = set ap_scan parameter" },
3031 { "scan_interval", wpa_cli_cmd_scan_interval, NULL,
3033 "<value> = set scan_interval parameter (in seconds)" },
3034 { "bss_expire_age", wpa_cli_cmd_bss_expire_age, NULL,
3036 "<value> = set BSS expiration age parameter" },
3037 { "bss_expire_count", wpa_cli_cmd_bss_expire_count, NULL,
3039 "<value> = set BSS expiration scan count parameter" },
3040 { "bss_flush", wpa_cli_cmd_bss_flush, NULL,
3042 "<value> = set BSS flush age (0 by default)" },
3043 { "stkstart", wpa_cli_cmd_stkstart, NULL,
3045 "<addr> = request STK negotiation with <addr>" },
3046 { "ft_ds", wpa_cli_cmd_ft_ds, wpa_cli_complete_bss,
3048 "<addr> = request over-the-DS FT with <addr>" },
3049 { "wps_pbc", wpa_cli_cmd_wps_pbc, wpa_cli_complete_bss,
3051 "[BSSID] = start Wi-Fi Protected Setup: Push Button Configuration" },
3052 { "wps_pin", wpa_cli_cmd_wps_pin, wpa_cli_complete_bss,
3053 cli_cmd_flag_sensitive,
3054 "<BSSID> [PIN] = start WPS PIN method (returns PIN, if not "
3056 { "wps_check_pin", wpa_cli_cmd_wps_check_pin, NULL,
3057 cli_cmd_flag_sensitive,
3058 "<PIN> = verify PIN checksum" },
3059 { "wps_cancel", wpa_cli_cmd_wps_cancel, NULL, cli_cmd_flag_none,
3060 "Cancels the pending WPS operation" },
3061 #ifdef CONFIG_WPS_NFC
3062 { "wps_nfc", wpa_cli_cmd_wps_nfc, wpa_cli_complete_bss,
3064 "[BSSID] = start Wi-Fi Protected Setup: NFC" },
3065 { "wps_nfc_config_token", wpa_cli_cmd_wps_nfc_config_token, NULL,
3067 "<WPS|NDEF> = build configuration token" },
3068 { "wps_nfc_token", wpa_cli_cmd_wps_nfc_token, NULL,
3070 "<WPS|NDEF> = create password token" },
3071 { "wps_nfc_tag_read", wpa_cli_cmd_wps_nfc_tag_read, NULL,
3072 cli_cmd_flag_sensitive,
3073 "<hexdump of payload> = report read NFC tag with WPS data" },
3074 { "nfc_get_handover_req", wpa_cli_cmd_nfc_get_handover_req, NULL,
3076 "<NDEF> <WPS> = create NFC handover request" },
3077 { "nfc_get_handover_sel", wpa_cli_cmd_nfc_get_handover_sel, NULL,
3079 "<NDEF> <WPS> = create NFC handover select" },
3080 { "nfc_report_handover", wpa_cli_cmd_nfc_report_handover, NULL,
3082 "<role> <type> <hexdump of req> <hexdump of sel> = report completed "
3084 #endif /* CONFIG_WPS_NFC */
3085 { "wps_reg", wpa_cli_cmd_wps_reg, wpa_cli_complete_bss,
3086 cli_cmd_flag_sensitive,
3087 "<BSSID> <AP PIN> = start WPS Registrar to configure an AP" },
3088 { "wps_ap_pin", wpa_cli_cmd_wps_ap_pin, NULL,
3089 cli_cmd_flag_sensitive,
3090 "[params..] = enable/disable AP PIN" },
3091 { "wps_er_start", wpa_cli_cmd_wps_er_start, NULL,
3093 "[IP address] = start Wi-Fi Protected Setup External Registrar" },
3094 { "wps_er_stop", wpa_cli_cmd_wps_er_stop, NULL,
3096 "= stop Wi-Fi Protected Setup External Registrar" },
3097 { "wps_er_pin", wpa_cli_cmd_wps_er_pin, NULL,
3098 cli_cmd_flag_sensitive,
3099 "<UUID> <PIN> = add an Enrollee PIN to External Registrar" },
3100 { "wps_er_pbc", wpa_cli_cmd_wps_er_pbc, NULL,
3102 "<UUID> = accept an Enrollee PBC using External Registrar" },
3103 { "wps_er_learn", wpa_cli_cmd_wps_er_learn, NULL,
3104 cli_cmd_flag_sensitive,
3105 "<UUID> <PIN> = learn AP configuration" },
3106 { "wps_er_set_config", wpa_cli_cmd_wps_er_set_config, NULL,
3108 "<UUID> <network id> = set AP configuration for enrolling" },
3109 { "wps_er_config", wpa_cli_cmd_wps_er_config, NULL,
3110 cli_cmd_flag_sensitive,
3111 "<UUID> <PIN> <SSID> <auth> <encr> <key> = configure AP" },
3112 #ifdef CONFIG_WPS_NFC
3113 { "wps_er_nfc_config_token", wpa_cli_cmd_wps_er_nfc_config_token, NULL,
3115 "<WPS/NDEF> <UUID> = build NFC configuration token" },
3116 #endif /* CONFIG_WPS_NFC */
3117 { "ibss_rsn", wpa_cli_cmd_ibss_rsn, NULL,
3119 "<addr> = request RSN authentication with <addr> in IBSS" },
3121 { "sta", wpa_cli_cmd_sta, NULL,
3123 "<addr> = get information about an associated station (AP)" },
3124 { "all_sta", wpa_cli_cmd_all_sta, NULL,
3126 "= get information about all associated stations (AP)" },
3127 { "deauthenticate", wpa_cli_cmd_deauthenticate, NULL,
3129 "<addr> = deauthenticate a station" },
3130 { "disassociate", wpa_cli_cmd_disassociate, NULL,
3132 "<addr> = disassociate a station" },
3133 { "chan_switch", wpa_cli_cmd_chanswitch, NULL,
3135 "<cs_count> <freq> [sec_channel_offset=] [center_freq1=]"
3136 " [center_freq2=] [bandwidth=] [blocktx] [ht|vht]"
3137 " = CSA parameters" },
3138 #endif /* CONFIG_AP */
3139 { "suspend", wpa_cli_cmd_suspend, NULL, cli_cmd_flag_none,
3140 "= notification of suspend/hibernate" },
3141 { "resume", wpa_cli_cmd_resume, NULL, cli_cmd_flag_none,
3142 "= notification of resume/thaw" },
3143 #ifdef CONFIG_TESTING_OPTIONS
3144 { "drop_sa", wpa_cli_cmd_drop_sa, NULL, cli_cmd_flag_none,
3145 "= drop SA without deauth/disassoc (test command)" },
3146 #endif /* CONFIG_TESTING_OPTIONS */
3147 { "roam", wpa_cli_cmd_roam, wpa_cli_complete_bss,
3149 "<addr> = roam to the specified BSS" },
3151 { "mesh_interface_add", wpa_cli_cmd_mesh_interface_add, NULL,
3153 "[ifname] = Create a new mesh interface" },
3154 { "mesh_group_add", wpa_cli_cmd_mesh_group_add, NULL,
3156 "<network id> = join a mesh network (disable others)" },
3157 { "mesh_group_remove", wpa_cli_cmd_mesh_group_remove, NULL,
3159 "<ifname> = Remove mesh group interface" },
3160 #endif /* CONFIG_MESH */
3162 { "p2p_find", wpa_cli_cmd_p2p_find, wpa_cli_complete_p2p_find,
3164 "[timeout] [type=*] = find P2P Devices for up-to timeout seconds" },
3165 { "p2p_stop_find", wpa_cli_cmd_p2p_stop_find, NULL, cli_cmd_flag_none,
3166 "= stop P2P Devices search" },
3167 { "p2p_asp_provision", wpa_cli_cmd_p2p_asp_provision, NULL,
3169 "<addr> adv_id=<adv_id> conncap=<conncap> [info=<infodata>] = provision with a P2P ASP Device" },
3170 { "p2p_asp_provision_resp", wpa_cli_cmd_p2p_asp_provision_resp, NULL,
3172 "<addr> adv_id=<adv_id> [role<conncap>] [info=<infodata>] = provision with a P2P ASP Device" },
3173 { "p2p_connect", wpa_cli_cmd_p2p_connect, wpa_cli_complete_p2p_connect,
3175 "<addr> <\"pbc\"|PIN> [ht40] = connect to a P2P Device" },
3176 { "p2p_listen", wpa_cli_cmd_p2p_listen, NULL, cli_cmd_flag_none,
3177 "[timeout] = listen for P2P Devices for up-to timeout seconds" },
3178 { "p2p_group_remove", wpa_cli_cmd_p2p_group_remove,
3179 wpa_cli_complete_p2p_group_remove, cli_cmd_flag_none,
3180 "<ifname> = remove P2P group interface (terminate group if GO)" },
3181 { "p2p_group_add", wpa_cli_cmd_p2p_group_add, NULL, cli_cmd_flag_none,
3182 "[ht40] = add a new P2P group (local end as GO)" },
3183 { "p2p_prov_disc", wpa_cli_cmd_p2p_prov_disc,
3184 wpa_cli_complete_p2p_peer, cli_cmd_flag_none,
3185 "<addr> <method> = request provisioning discovery" },
3186 { "p2p_get_passphrase", wpa_cli_cmd_p2p_get_passphrase, NULL,
3188 "= get the passphrase for a group (GO only)" },
3189 { "p2p_serv_disc_req", wpa_cli_cmd_p2p_serv_disc_req,
3190 wpa_cli_complete_p2p_peer, cli_cmd_flag_none,
3191 "<addr> <TLVs> = schedule service discovery request" },
3192 { "p2p_serv_disc_cancel_req", wpa_cli_cmd_p2p_serv_disc_cancel_req,
3193 NULL, cli_cmd_flag_none,
3194 "<id> = cancel pending service discovery request" },
3195 { "p2p_serv_disc_resp", wpa_cli_cmd_p2p_serv_disc_resp, NULL,
3197 "<freq> <addr> <dialog token> <TLVs> = service discovery response" },
3198 { "p2p_service_update", wpa_cli_cmd_p2p_service_update, NULL,
3200 "= indicate change in local services" },
3201 { "p2p_serv_disc_external", wpa_cli_cmd_p2p_serv_disc_external, NULL,
3203 "<external> = set external processing of service discovery" },
3204 { "p2p_service_flush", wpa_cli_cmd_p2p_service_flush, NULL,
3206 "= remove all stored service entries" },
3207 { "p2p_service_add", wpa_cli_cmd_p2p_service_add, NULL,
3209 "<bonjour|upnp|asp> <query|version> <response|service> = add a local "
3211 { "p2p_service_rep", wpa_cli_cmd_p2p_service_rep, NULL,
3213 "asp <auto> <adv_id> <svc_state> <svc_string> [<svc_info>] = replace "
3214 "local ASP service" },
3215 { "p2p_service_del", wpa_cli_cmd_p2p_service_del, NULL,
3217 "<bonjour|upnp> <query|version> [|service] = remove a local "
3219 { "p2p_reject", wpa_cli_cmd_p2p_reject, wpa_cli_complete_p2p_peer,
3221 "<addr> = reject connection attempts from a specific peer" },
3222 { "p2p_invite", wpa_cli_cmd_p2p_invite, NULL,
3224 "<cmd> [peer=addr] = invite peer" },
3225 { "p2p_peers", wpa_cli_cmd_p2p_peers, NULL, cli_cmd_flag_none,
3226 "[discovered] = list known (optionally, only fully discovered) P2P "
3228 { "p2p_peer", wpa_cli_cmd_p2p_peer, wpa_cli_complete_p2p_peer,
3230 "<address> = show information about known P2P peer" },
3231 { "p2p_set", wpa_cli_cmd_p2p_set, wpa_cli_complete_p2p_set,
3233 "<field> <value> = set a P2P parameter" },
3234 { "p2p_flush", wpa_cli_cmd_p2p_flush, NULL, cli_cmd_flag_none,
3235 "= flush P2P state" },
3236 { "p2p_cancel", wpa_cli_cmd_p2p_cancel, NULL, cli_cmd_flag_none,
3237 "= cancel P2P group formation" },
3238 { "p2p_unauthorize", wpa_cli_cmd_p2p_unauthorize,
3239 wpa_cli_complete_p2p_peer, cli_cmd_flag_none,
3240 "<address> = unauthorize a peer" },
3241 { "p2p_presence_req", wpa_cli_cmd_p2p_presence_req, NULL,
3243 "[<duration> <interval>] [<duration> <interval>] = request GO "
3245 { "p2p_ext_listen", wpa_cli_cmd_p2p_ext_listen, NULL,
3247 "[<period> <interval>] = set extended listen timing" },
3248 { "p2p_remove_client", wpa_cli_cmd_p2p_remove_client,
3249 wpa_cli_complete_p2p_peer, cli_cmd_flag_none,
3250 "<address|iface=address> = remove a peer from all groups" },
3251 #endif /* CONFIG_P2P */
3252 #ifdef CONFIG_WIFI_DISPLAY
3253 { "wfd_subelem_set", wpa_cli_cmd_wfd_subelem_set, NULL,
3255 "<subelem> [contents] = set Wi-Fi Display subelement" },
3256 { "wfd_subelem_get", wpa_cli_cmd_wfd_subelem_get, NULL,
3258 "<subelem> = get Wi-Fi Display subelement" },
3259 #endif /* CONFIG_WIFI_DISPLAY */
3260 #ifdef CONFIG_INTERWORKING
3261 { "fetch_anqp", wpa_cli_cmd_fetch_anqp, NULL, cli_cmd_flag_none,
3262 "= fetch ANQP information for all APs" },
3263 { "stop_fetch_anqp", wpa_cli_cmd_stop_fetch_anqp, NULL,
3265 "= stop fetch_anqp operation" },
3266 { "interworking_select", wpa_cli_cmd_interworking_select, NULL,
3268 "[auto] = perform Interworking network selection" },
3269 { "interworking_connect", wpa_cli_cmd_interworking_connect,
3270 wpa_cli_complete_bss, cli_cmd_flag_none,
3271 "<BSSID> = connect using Interworking credentials" },
3272 { "interworking_add_network", wpa_cli_cmd_interworking_add_network,
3273 wpa_cli_complete_bss, cli_cmd_flag_none,
3274 "<BSSID> = connect using Interworking credentials" },
3275 { "anqp_get", wpa_cli_cmd_anqp_get, wpa_cli_complete_bss,
3277 "<addr> <info id>[,<info id>]... = request ANQP information" },
3278 { "gas_request", wpa_cli_cmd_gas_request, wpa_cli_complete_bss,
3280 "<addr> <AdvProtoID> [QueryReq] = GAS request" },
3281 { "gas_response_get", wpa_cli_cmd_gas_response_get,
3282 wpa_cli_complete_bss, cli_cmd_flag_none,
3283 "<addr> <dialog token> [start,len] = Fetch last GAS response" },
3284 #endif /* CONFIG_INTERWORKING */
3286 { "hs20_anqp_get", wpa_cli_cmd_hs20_anqp_get, wpa_cli_complete_bss,
3288 "<addr> <subtype>[,<subtype>]... = request HS 2.0 ANQP information"
3290 { "nai_home_realm_list", wpa_cli_cmd_get_nai_home_realm_list,
3291 wpa_cli_complete_bss, cli_cmd_flag_none,
3292 "<addr> <home realm> = get HS20 nai home realm list" },
3293 { "hs20_icon_request", wpa_cli_cmd_hs20_icon_request,
3294 wpa_cli_complete_bss, cli_cmd_flag_none,
3295 "<addr> <icon name> = get Hotspot 2.0 OSU icon" },
3296 { "fetch_osu", wpa_cli_cmd_fetch_osu, NULL, cli_cmd_flag_none,
3297 "= fetch OSU provider information from all APs" },
3298 { "cancel_fetch_osu", wpa_cli_cmd_cancel_fetch_osu, NULL,
3300 "= cancel fetch_osu command" },
3301 #endif /* CONFIG_HS20 */
3302 { "sta_autoconnect", wpa_cli_cmd_sta_autoconnect, NULL,
3304 "<0/1> = disable/enable automatic reconnection" },
3305 { "tdls_discover", wpa_cli_cmd_tdls_discover, NULL,
3307 "<addr> = request TDLS discovery with <addr>" },
3308 { "tdls_setup", wpa_cli_cmd_tdls_setup, NULL,
3310 "<addr> = request TDLS setup with <addr>" },
3311 { "tdls_teardown", wpa_cli_cmd_tdls_teardown, NULL,
3313 "<addr> = tear down TDLS with <addr>" },
3314 { "tdls_link_status", wpa_cli_cmd_tdls_link_status, NULL,
3316 "<addr> = TDLS link status with <addr>" },
3317 { "wmm_ac_addts", wpa_cli_cmd_wmm_ac_addts, NULL,
3319 "<uplink/downlink/bidi> <tsid=0..7> <up=0..7> [nominal_msdu_size=#] "
3320 "[mean_data_rate=#] [min_phy_rate=#] [sba=#] [fixed_nominal_msdu] "
3321 "= add WMM-AC traffic stream" },
3322 { "wmm_ac_delts", wpa_cli_cmd_wmm_ac_delts, NULL,
3324 "<tsid> = delete WMM-AC traffic stream" },
3325 { "wmm_ac_status", wpa_cli_cmd_wmm_ac_status, NULL,
3327 "= show status for Wireless Multi-Media Admission-Control" },
3328 { "tdls_chan_switch", wpa_cli_cmd_tdls_chan_switch, NULL,
3330 "<addr> <oper class> <freq> [sec_channel_offset=] [center_freq1=] "
3331 "[center_freq2=] [bandwidth=] [ht|vht] = enable channel switching "
3333 { "tdls_cancel_chan_switch", wpa_cli_cmd_tdls_cancel_chan_switch, NULL,
3335 "<addr> = disable channel switching with TDLS peer <addr>" },
3336 { "signal_poll", wpa_cli_cmd_signal_poll, NULL,
3338 "= get signal parameters" },
3339 { "pktcnt_poll", wpa_cli_cmd_pktcnt_poll, NULL,
3341 "= get TX/RX packet counters" },
3342 { "reauthenticate", wpa_cli_cmd_reauthenticate, NULL,
3344 "= trigger IEEE 802.1X/EAPOL reauthentication" },
3345 #ifdef CONFIG_AUTOSCAN
3346 { "autoscan", wpa_cli_cmd_autoscan, NULL, cli_cmd_flag_none,
3347 "[params] = Set or unset (if none) autoscan parameters" },
3348 #endif /* CONFIG_AUTOSCAN */
3350 { "wnm_sleep", wpa_cli_cmd_wnm_sleep, NULL, cli_cmd_flag_none,
3351 "<enter/exit> [interval=#] = enter/exit WNM-Sleep mode" },
3352 { "wnm_bss_query", wpa_cli_cmd_wnm_bss_query, NULL, cli_cmd_flag_none,
3353 "<query reason> = Send BSS Transition Management Query" },
3354 #endif /* CONFIG_WNM */
3355 { "raw", wpa_cli_cmd_raw, NULL, cli_cmd_flag_sensitive,
3356 "<params..> = Sent unprocessed command" },
3357 { "flush", wpa_cli_cmd_flush, NULL, cli_cmd_flag_none,
3358 "= flush wpa_supplicant state" },
3360 { "driver", wpa_cli_cmd_driver, NULL, cli_cmd_flag_none,
3361 "<command> = driver private commands" },
3362 #endif /* ANDROID */
3363 { "radio_work", wpa_cli_cmd_radio_work, NULL, cli_cmd_flag_none,
3364 "= radio_work <show/add/done>" },
3365 { "vendor", wpa_cli_cmd_vendor, NULL, cli_cmd_flag_none,
3366 "<vendor id> <command id> [<hex formatted command argument>] = Send vendor command"
3368 { "neighbor_rep_request",
3369 wpa_cli_cmd_neighbor_rep_request, NULL, cli_cmd_flag_none,
3370 "[ssid=<SSID>] = Trigger request to AP for neighboring AP report "
3371 "(with optional given SSID, default: current SSID)"
3373 { "erp_flush", wpa_cli_cmd_erp_flush, NULL, cli_cmd_flag_none,
3374 "= flush ERP keys" },
3376 wpa_cli_cmd_mac_rand_scan, NULL, cli_cmd_flag_none,
3377 "<scan|sched|pno|all> enable=<0/1> [addr=mac-address "
3378 "mask=mac-address-mask] = scan MAC randomization"
3380 { "get_pref_freq_list", wpa_cli_cmd_get_pref_freq_list, NULL,
3382 "<interface type> = retrieve preferred freq list for the specified interface type" },
3383 { NULL, NULL, NULL, cli_cmd_flag_none, NULL }
3388 * Prints command usage, lines are padded with the specified string.
3390 static void print_cmd_help(const struct wpa_cli_cmd *cmd, const char *pad)
3395 printf("%s%s ", pad, cmd->cmd);
3396 for (n = 0; (c = cmd->usage[n]); n++) {
3405 static void print_help(const char *cmd)
3408 printf("commands:\n");
3409 for (n = 0; wpa_cli_commands[n].cmd; n++) {
3410 if (cmd == NULL || str_starts(wpa_cli_commands[n].cmd, cmd))
3411 print_cmd_help(&wpa_cli_commands[n], " ");
3416 static int wpa_cli_edit_filter_history_cb(void *ctx, const char *cmd)
3418 const char *c, *delim;
3422 delim = os_strchr(cmd, ' ');
3426 len = os_strlen(cmd);
3428 for (n = 0; (c = wpa_cli_commands[n].cmd); n++) {
3429 if (os_strncasecmp(cmd, c, len) == 0 && len == os_strlen(c))
3430 return (wpa_cli_commands[n].flags &
3431 cli_cmd_flag_sensitive);
3437 static char ** wpa_list_cmd_list(void)
3441 struct cli_txt_entry *e;
3443 count = ARRAY_SIZE(wpa_cli_commands);
3444 count += dl_list_len(&p2p_groups);
3445 count += dl_list_len(&ifnames);
3446 res = os_calloc(count + 1, sizeof(char *));
3450 for (i = 0; wpa_cli_commands[i].cmd; i++) {
3451 res[i] = os_strdup(wpa_cli_commands[i].cmd);
3456 dl_list_for_each(e, &p2p_groups, struct cli_txt_entry, list) {
3457 size_t len = 8 + os_strlen(e->txt);
3458 res[i] = os_malloc(len);
3461 os_snprintf(res[i], len, "ifname=%s", e->txt);
3465 dl_list_for_each(e, &ifnames, struct cli_txt_entry, list) {
3466 res[i] = os_strdup(e->txt);
3476 static char ** wpa_cli_cmd_completion(const char *cmd, const char *str,
3481 for (i = 0; wpa_cli_commands[i].cmd; i++) {
3482 if (os_strcasecmp(wpa_cli_commands[i].cmd, cmd) == 0) {
3483 if (wpa_cli_commands[i].completion)
3484 return wpa_cli_commands[i].completion(str,
3487 printf("\r%s\n", wpa_cli_commands[i].usage);
3497 static char ** wpa_cli_edit_completion_cb(void *ctx, const char *str, int pos)
3503 if (pos > 7 && os_strncasecmp(str, "IFNAME=", 7) == 0) {
3504 end = os_strchr(str, ' ');
3505 if (end && pos > end - str) {
3506 pos -= end - str + 1;
3511 end = os_strchr(str, ' ');
3512 if (end == NULL || str + pos < end)
3513 return wpa_list_cmd_list();
3515 cmd = os_malloc(pos + 1);
3518 os_memcpy(cmd, str, pos);
3519 cmd[end - str] = '\0';
3520 res = wpa_cli_cmd_completion(cmd, str, pos);
3526 static int wpa_request(struct wpa_ctrl *ctrl, int argc, char *argv[])
3528 const struct wpa_cli_cmd *cmd, *match = NULL;
3532 if (argc > 1 && os_strncasecmp(argv[0], "IFNAME=", 7) == 0) {
3533 ifname_prefix = argv[0] + 7;
3537 ifname_prefix = NULL;
3543 cmd = wpa_cli_commands;
3545 if (os_strncasecmp(cmd->cmd, argv[0], os_strlen(argv[0])) == 0)
3548 if (os_strcasecmp(cmd->cmd, argv[0]) == 0) {
3549 /* we have an exact match */
3559 printf("Ambiguous command '%s'; possible commands:", argv[0]);
3560 cmd = wpa_cli_commands;
3562 if (os_strncasecmp(cmd->cmd, argv[0],
3563 os_strlen(argv[0])) == 0) {
3564 printf(" %s", cmd->cmd);
3570 } else if (count == 0) {
3571 printf("Unknown command '%s'\n", argv[0]);
3574 ret = match->handler(ctrl, argc - 1, &argv[1]);
3581 static int str_match(const char *a, const char *b)
3583 return os_strncmp(a, b, os_strlen(b)) == 0;
3587 static int wpa_cli_exec(const char *program, const char *arg1,
3594 len = os_strlen(arg1) + os_strlen(arg2) + 2;
3595 arg = os_malloc(len);
3598 os_snprintf(arg, len, "%s %s", arg1, arg2);
3599 res = os_exec(program, arg, 1);
3606 static void wpa_cli_action_process(const char *msg)
3609 char *copy = NULL, *id, *pos2;
3610 const char *ifname = ctrl_ifname;
3611 char ifname_buf[100];
3613 if (eloop_terminated())
3617 if (os_strncmp(pos, "IFNAME=", 7) == 0) {
3619 end = os_strchr(pos + 7, ' ');
3620 if (end && (unsigned int) (end - pos) < sizeof(ifname_buf)) {
3622 os_memcpy(ifname_buf, pos, end - pos);
3623 ifname_buf[end - pos] = '\0';
3624 ifname = ifname_buf;
3629 const char *prev = pos;
3631 pos = os_strchr(pos, '>');
3638 if (str_match(pos, WPA_EVENT_CONNECTED)) {
3640 os_unsetenv("WPA_ID");
3641 os_unsetenv("WPA_ID_STR");
3642 os_unsetenv("WPA_CTRL_DIR");
3644 pos = os_strstr(pos, "[id=");
3646 copy = os_strdup(pos + 4);
3650 while (*pos2 && *pos2 != ' ')
3654 os_setenv("WPA_ID", id, 1);
3655 while (*pos2 && *pos2 != '=')
3660 while (*pos2 && *pos2 != ']')
3663 os_setenv("WPA_ID_STR", id, 1);
3667 os_setenv("WPA_CTRL_DIR", ctrl_iface_dir, 1);
3669 if (wpa_cli_connected <= 0 || new_id != wpa_cli_last_id) {
3670 wpa_cli_connected = 1;
3671 wpa_cli_last_id = new_id;
3672 wpa_cli_exec(action_file, ifname, "CONNECTED");
3674 } else if (str_match(pos, WPA_EVENT_DISCONNECTED)) {
3675 if (wpa_cli_connected) {
3676 wpa_cli_connected = 0;
3677 wpa_cli_exec(action_file, ifname, "DISCONNECTED");
3679 } else if (str_match(pos, MESH_GROUP_STARTED)) {
3680 wpa_cli_exec(action_file, ctrl_ifname, pos);
3681 } else if (str_match(pos, MESH_GROUP_REMOVED)) {
3682 wpa_cli_exec(action_file, ctrl_ifname, pos);
3683 } else if (str_match(pos, MESH_PEER_CONNECTED)) {
3684 wpa_cli_exec(action_file, ctrl_ifname, pos);
3685 } else if (str_match(pos, MESH_PEER_DISCONNECTED)) {
3686 wpa_cli_exec(action_file, ctrl_ifname, pos);
3687 } else if (str_match(pos, P2P_EVENT_GROUP_STARTED)) {
3688 wpa_cli_exec(action_file, ifname, pos);
3689 } else if (str_match(pos, P2P_EVENT_GROUP_REMOVED)) {
3690 wpa_cli_exec(action_file, ifname, pos);
3691 } else if (str_match(pos, P2P_EVENT_CROSS_CONNECT_ENABLE)) {
3692 wpa_cli_exec(action_file, ifname, pos);
3693 } else if (str_match(pos, P2P_EVENT_CROSS_CONNECT_DISABLE)) {
3694 wpa_cli_exec(action_file, ifname, pos);
3695 } else if (str_match(pos, P2P_EVENT_GO_NEG_FAILURE)) {
3696 wpa_cli_exec(action_file, ifname, pos);
3697 } else if (str_match(pos, WPS_EVENT_SUCCESS)) {
3698 wpa_cli_exec(action_file, ifname, pos);
3699 } else if (str_match(pos, WPS_EVENT_FAIL)) {
3700 wpa_cli_exec(action_file, ifname, pos);
3701 } else if (str_match(pos, AP_STA_CONNECTED)) {
3702 wpa_cli_exec(action_file, ifname, pos);
3703 } else if (str_match(pos, AP_STA_DISCONNECTED)) {
3704 wpa_cli_exec(action_file, ifname, pos);
3705 } else if (str_match(pos, ESS_DISASSOC_IMMINENT)) {
3706 wpa_cli_exec(action_file, ifname, pos);
3707 } else if (str_match(pos, HS20_SUBSCRIPTION_REMEDIATION)) {
3708 wpa_cli_exec(action_file, ifname, pos);
3709 } else if (str_match(pos, HS20_DEAUTH_IMMINENT_NOTICE)) {
3710 wpa_cli_exec(action_file, ifname, pos);
3711 } else if (str_match(pos, WPA_EVENT_TERMINATING)) {
3712 printf("wpa_supplicant is terminating - stop monitoring\n");
3718 #ifndef CONFIG_ANSI_C_EXTRA
3719 static void wpa_cli_action_cb(char *msg, size_t len)
3721 wpa_cli_action_process(msg);
3723 #endif /* CONFIG_ANSI_C_EXTRA */
3726 static void wpa_cli_reconnect(void)
3728 wpa_cli_close_connection();
3729 if (wpa_cli_open_connection(ctrl_ifname, 1) < 0)
3734 printf("\rConnection to wpa_supplicant re-established\n");
3740 static void cli_event(const char *str)
3742 const char *start, *s;
3744 start = os_strchr(str, '>');
3750 if (str_starts(start, WPA_EVENT_BSS_ADDED)) {
3751 s = os_strchr(start, ' ');
3754 s = os_strchr(s + 1, ' ');
3757 cli_txt_list_add(&bsses, s + 1);
3761 if (str_starts(start, WPA_EVENT_BSS_REMOVED)) {
3762 s = os_strchr(start, ' ');
3765 s = os_strchr(s + 1, ' ');
3768 cli_txt_list_del_addr(&bsses, s + 1);
3773 if (str_starts(start, P2P_EVENT_DEVICE_FOUND)) {
3774 s = os_strstr(start, " p2p_dev_addr=");
3777 cli_txt_list_add_addr(&p2p_peers, s + 14);
3781 if (str_starts(start, P2P_EVENT_DEVICE_LOST)) {
3782 s = os_strstr(start, " p2p_dev_addr=");
3785 cli_txt_list_del_addr(&p2p_peers, s + 14);
3789 if (str_starts(start, P2P_EVENT_GROUP_STARTED)) {
3790 s = os_strchr(start, ' ');
3793 cli_txt_list_add_word(&p2p_groups, s + 1, ' ');
3797 if (str_starts(start, P2P_EVENT_GROUP_REMOVED)) {
3798 s = os_strchr(start, ' ');
3801 cli_txt_list_del_word(&p2p_groups, s + 1, ' ');
3804 #endif /* CONFIG_P2P */
3808 static int check_terminating(const char *msg)
3810 const char *pos = msg;
3814 pos = os_strchr(pos, '>');
3821 if (str_match(pos, WPA_EVENT_TERMINATING) && ctrl_conn) {
3823 printf("\rConnection to wpa_supplicant lost - trying to "
3826 wpa_cli_attached = 0;
3827 wpa_cli_close_connection();
3835 static void wpa_cli_recv_pending(struct wpa_ctrl *ctrl, int action_monitor)
3837 if (ctrl_conn == NULL) {
3838 wpa_cli_reconnect();
3841 while (wpa_ctrl_pending(ctrl) > 0) {
3843 size_t len = sizeof(buf) - 1;
3844 if (wpa_ctrl_recv(ctrl, buf, &len) == 0) {
3847 wpa_cli_action_process(buf);
3850 if (wpa_cli_show_event(buf)) {
3852 printf("\r%s\n", buf);
3856 if (interactive && check_terminating(buf) > 0)
3860 printf("Could not read pending message.\n");
3865 if (wpa_ctrl_pending(ctrl) < 0) {
3866 printf("Connection to wpa_supplicant lost - trying to "
3868 wpa_cli_reconnect();
3874 static int tokenize_cmd(char *cmd, char *argv[])
3887 if (argc == max_args)
3890 char *pos2 = os_strrchr(pos, '"');
3894 while (*pos != '\0' && *pos != ' ')
3904 static void wpa_cli_ping(void *eloop_ctx, void *timeout_ctx)
3908 char *prefix = ifname_prefix;
3910 ifname_prefix = NULL;
3911 res = _wpa_ctrl_command(ctrl_conn, "PING", 0);
3912 ifname_prefix = prefix;
3914 printf("Connection to wpa_supplicant lost - trying to "
3916 wpa_cli_close_connection();
3920 wpa_cli_reconnect();
3921 eloop_register_timeout(ping_interval, 0, wpa_cli_ping, NULL, NULL);
3925 static void wpa_cli_mon_receive(int sock, void *eloop_ctx, void *sock_ctx)
3927 wpa_cli_recv_pending(mon_conn, 0);
3931 static void wpa_cli_edit_cmd_cb(void *ctx, char *cmd)
3933 char *argv[max_args];
3935 argc = tokenize_cmd(cmd, argv);
3937 wpa_request(ctrl_conn, argc, argv);
3941 static void wpa_cli_edit_eof_cb(void *ctx)
3947 static int warning_displayed = 0;
3948 static char *hfile = NULL;
3949 static int edit_started = 0;
3951 static void start_edit(void)
3956 #ifdef CONFIG_CTRL_IFACE_UDP_REMOTE
3957 ps = wpa_ctrl_get_remote_ifname(ctrl_conn);
3958 #endif /* CONFIG_CTRL_IFACE_UDP_REMOTE */
3960 #ifdef CONFIG_WPA_CLI_HISTORY_DIR
3961 home = CONFIG_WPA_CLI_HISTORY_DIR;
3962 #else /* CONFIG_WPA_CLI_HISTORY_DIR */
3963 home = getenv("HOME");
3964 #endif /* CONFIG_WPA_CLI_HISTORY_DIR */
3966 const char *fname = ".wpa_cli_history";
3967 int hfile_len = os_strlen(home) + 1 + os_strlen(fname) + 1;
3968 hfile = os_malloc(hfile_len);
3970 os_snprintf(hfile, hfile_len, "%s/%s", home, fname);
3973 if (edit_init(wpa_cli_edit_cmd_cb, wpa_cli_edit_eof_cb,
3974 wpa_cli_edit_completion_cb, NULL, hfile, ps) < 0) {
3980 eloop_register_timeout(ping_interval, 0, wpa_cli_ping, NULL, NULL);
3984 static void update_bssid_list(struct wpa_ctrl *ctrl)
3987 size_t len = sizeof(buf);
3989 char *cmd = "BSS RANGE=ALL MASK=0x2";
3994 ret = wpa_ctrl_request(ctrl, cmd, os_strlen(cmd), buf, &len, NULL);
4001 pos = os_strstr(pos, "bssid=");
4005 end = os_strchr(pos, '\n');
4009 cli_txt_list_add(&bsses, pos);
4015 static void update_ifnames(struct wpa_ctrl *ctrl)
4018 size_t len = sizeof(buf);
4020 char *cmd = "INTERFACES";
4024 cli_txt_list_flush(&ifnames);
4028 ret = wpa_ctrl_request(ctrl, cmd, os_strlen(cmd), buf, &len, NULL);
4035 end = os_strchr(pos, '\n');
4039 ret = os_snprintf(txt, sizeof(txt), "ifname=%s", pos);
4040 if (!os_snprintf_error(sizeof(txt), ret))
4041 cli_txt_list_add(&ifnames, txt);
4047 static void update_networks(struct wpa_ctrl *ctrl)
4050 size_t len = sizeof(buf);
4052 char *cmd = "LIST_NETWORKS";
4056 cli_txt_list_flush(&networks);
4060 ret = wpa_ctrl_request(ctrl, cmd, os_strlen(cmd), buf, &len, NULL);
4067 end = os_strchr(pos, '\n');
4072 cli_txt_list_add_word(&networks, pos, '\t');
4079 static void try_connection(void *eloop_ctx, void *timeout_ctx)
4084 if (ctrl_ifname == NULL)
4085 ctrl_ifname = wpa_cli_get_default_ifname();
4087 if (!wpa_cli_open_connection(ctrl_ifname, 1) == 0) {
4088 if (!warning_displayed) {
4089 printf("Could not connect to wpa_supplicant: "
4091 ctrl_ifname ? ctrl_ifname : "(nil)");
4092 warning_displayed = 1;
4094 eloop_register_timeout(1, 0, try_connection, NULL, NULL);
4098 update_bssid_list(ctrl_conn);
4099 update_networks(ctrl_conn);
4101 if (warning_displayed)
4102 printf("Connection established.\n");
4109 static void wpa_cli_interactive(void)
4111 printf("\nInteractive mode\n\n");
4113 eloop_register_timeout(0, 0, try_connection, NULL, NULL);
4115 eloop_cancel_timeout(try_connection, NULL, NULL);
4117 cli_txt_list_flush(&p2p_peers);
4118 cli_txt_list_flush(&p2p_groups);
4119 cli_txt_list_flush(&bsses);
4120 cli_txt_list_flush(&ifnames);
4121 cli_txt_list_flush(&networks);
4123 edit_deinit(hfile, wpa_cli_edit_filter_history_cb);
4125 eloop_cancel_timeout(wpa_cli_ping, NULL, NULL);
4126 wpa_cli_close_connection();
4130 static void wpa_cli_action_ping(void *eloop_ctx, void *timeout_ctx)
4132 struct wpa_ctrl *ctrl = eloop_ctx;
4136 /* verify that connection is still working */
4137 len = sizeof(buf) - 1;
4138 if (wpa_ctrl_request(ctrl, "PING", 4, buf, &len,
4139 wpa_cli_action_cb) < 0 ||
4140 len < 4 || os_memcmp(buf, "PONG", 4) != 0) {
4141 printf("wpa_supplicant did not reply to PING command - exiting\n");
4145 eloop_register_timeout(ping_interval, 0, wpa_cli_action_ping,
4150 static void wpa_cli_action_receive(int sock, void *eloop_ctx, void *sock_ctx)
4152 struct wpa_ctrl *ctrl = eloop_ctx;
4154 wpa_cli_recv_pending(ctrl, 1);
4158 static void wpa_cli_action(struct wpa_ctrl *ctrl)
4160 #ifdef CONFIG_ANSI_C_EXTRA
4161 /* TODO: ANSI C version(?) */
4162 printf("Action processing not supported in ANSI C build.\n");
4163 #else /* CONFIG_ANSI_C_EXTRA */
4166 fd = wpa_ctrl_get_fd(ctrl);
4167 eloop_register_timeout(ping_interval, 0, wpa_cli_action_ping,
4169 eloop_register_read_sock(fd, wpa_cli_action_receive, ctrl, NULL);
4171 eloop_cancel_timeout(wpa_cli_action_ping, ctrl, NULL);
4172 eloop_unregister_read_sock(fd);
4173 #endif /* CONFIG_ANSI_C_EXTRA */
4177 static void wpa_cli_cleanup(void)
4179 wpa_cli_close_connection();
4181 os_daemonize_terminate(pid_file);
4183 os_program_deinit();
4187 static void wpa_cli_terminate(int sig, void *ctx)
4193 static char * wpa_cli_get_default_ifname(void)
4195 char *ifname = NULL;
4198 char ifprop[PROPERTY_VALUE_MAX];
4199 if (property_get("wifi.interface", ifprop, NULL) != 0) {
4200 ifname = os_strdup(ifprop);
4201 printf("Using interface '%s'\n", ifname ? ifname : "N/A");
4204 #ifdef CONFIG_CTRL_IFACE_UNIX
4205 struct dirent *dent;
4206 DIR *dir = opendir(ctrl_iface_dir);
4210 while ((dent = readdir(dir))) {
4211 #ifdef _DIRENT_HAVE_D_TYPE
4213 * Skip the file if it is not a socket. Also accept
4214 * DT_UNKNOWN (0) in case the C library or underlying
4215 * file system does not support d_type.
4217 if (dent->d_type != DT_SOCK && dent->d_type != DT_UNKNOWN)
4219 #endif /* _DIRENT_HAVE_D_TYPE */
4220 if (os_strcmp(dent->d_name, ".") == 0 ||
4221 os_strcmp(dent->d_name, "..") == 0)
4223 printf("Selected interface '%s'\n", dent->d_name);
4224 ifname = os_strdup(dent->d_name);
4228 #endif /* CONFIG_CTRL_IFACE_UNIX */
4230 #ifdef CONFIG_CTRL_IFACE_NAMED_PIPE
4231 char buf[4096], *pos;
4233 struct wpa_ctrl *ctrl;
4236 ctrl = wpa_ctrl_open(NULL);
4240 len = sizeof(buf) - 1;
4241 ret = wpa_ctrl_request(ctrl, "INTERFACES", 10, buf, &len, NULL);
4244 pos = os_strchr(buf, '\n');
4247 ifname = os_strdup(buf);
4249 wpa_ctrl_close(ctrl);
4250 #endif /* CONFIG_CTRL_IFACE_NAMED_PIPE */
4251 #endif /* ANDROID */
4257 int main(int argc, char *argv[])
4262 const char *global = NULL;
4264 if (os_program_init())
4268 c = getopt(argc, argv, "a:Bg:G:hi:p:P:s:v");
4273 action_file = optarg;
4282 ping_interval = atoi(optarg);
4288 printf("%s\n", wpa_cli_version);
4291 os_free(ctrl_ifname);
4292 ctrl_ifname = os_strdup(optarg);
4295 ctrl_iface_dir = optarg;
4301 client_socket_dir = optarg;
4309 interactive = (argc == optind) && (action_file == NULL);
4312 printf("%s\n\n%s\n\n", wpa_cli_version, wpa_cli_license);
4318 #ifdef CONFIG_CTRL_IFACE_NAMED_PIPE
4319 ctrl_conn = wpa_ctrl_open(NULL);
4320 #else /* CONFIG_CTRL_IFACE_NAMED_PIPE */
4321 ctrl_conn = wpa_ctrl_open(global);
4322 #endif /* CONFIG_CTRL_IFACE_NAMED_PIPE */
4323 if (ctrl_conn == NULL) {
4324 fprintf(stderr, "Failed to connect to wpa_supplicant "
4325 "global interface: %s error: %s\n",
4326 global, strerror(errno));
4331 update_ifnames(ctrl_conn);
4332 mon_conn = wpa_ctrl_open(global);
4334 if (wpa_ctrl_attach(mon_conn) == 0) {
4335 wpa_cli_attached = 1;
4336 eloop_register_read_sock(
4337 wpa_ctrl_get_fd(mon_conn),
4338 wpa_cli_mon_receive,
4341 printf("Failed to open monitor "
4342 "connection through global "
4343 "control interface\n");
4349 eloop_register_signal_terminate(wpa_cli_terminate, NULL);
4351 if (ctrl_ifname == NULL)
4352 ctrl_ifname = wpa_cli_get_default_ifname();
4355 wpa_cli_interactive();
4358 wpa_cli_open_connection(ctrl_ifname, 0) < 0) {
4359 fprintf(stderr, "Failed to connect to non-global "
4360 "ctrl_ifname: %s error: %s\n",
4361 ctrl_ifname ? ctrl_ifname : "(nil)",
4367 if (wpa_ctrl_attach(ctrl_conn) == 0) {
4368 wpa_cli_attached = 1;
4370 printf("Warning: Failed to attach to "
4371 "wpa_supplicant.\n");
4376 if (daemonize && os_daemonize(pid_file))
4380 wpa_cli_action(ctrl_conn);
4382 ret = wpa_request(ctrl_conn, argc - optind,
4386 os_free(ctrl_ifname);
4393 #else /* CONFIG_CTRL_IFACE */
4394 int main(int argc, char *argv[])
4396 printf("CONFIG_CTRL_IFACE not defined - wpa_cli disabled\n");
4399 #endif /* CONFIG_CTRL_IFACE */