Skip to content

Commit

Permalink
wifi: shell: Add a shell command to list stations
Browse files Browse the repository at this point in the history
In AP mode maintain the database of connected stations based on the
Wi-Fi management events and dump the list.

Signed-off-by: Chaitanya Tata <Chaitanya.Tata@nordicsemi.no>
  • Loading branch information
krish2718 committed Dec 27, 2023
1 parent 7bae00b commit 496decf
Show file tree
Hide file tree
Showing 2 changed files with 105 additions and 0 deletions.
8 changes: 8 additions & 0 deletions subsys/net/l2/wifi/Kconfig
Expand Up @@ -64,6 +64,14 @@ config WIFI_MGMT_SCAN_CHAN_MAX_MANUAL
There are approximately 100 channels allocated across the three supported bands.
The default of 3 allows the 3 most common channels (2.4GHz: 1, 6, 11) to be specified.

config WIFI_SHELL_MAX_AP_STA
int "Maximum number of APs and STAs that can be managed in Wi-Fi shell"
range 1 5
default 1
help
This option defines the maximum number of APs and STAs that can be managed
in Wi-Fi shell.

config WIFI_NM
bool "Wi-Fi Network manager support"
help
Expand Down
97 changes: 97 additions & 0 deletions subsys/net/l2/wifi/wifi_shell.c
Expand Up @@ -24,6 +24,7 @@ LOG_MODULE_REGISTER(net_wifi_shell, LOG_LEVEL_INF);
#include <zephyr/net/wifi_mgmt.h>
#include <zephyr/net/wifi_utils.h>
#include <zephyr/posix/unistd.h>
#include <zephyr/sys/slist.h>

#include "net_private.h"

Expand Down Expand Up @@ -64,6 +65,13 @@ static uint32_t scan_result;

static struct net_mgmt_event_callback wifi_shell_mgmt_cb;

K_MUTEX_DEFINE(wifi_ap_sta_list_lock);
struct wifi_ap_sta_node {
bool valid;
struct wifi_ap_sta_info sta_info;
};
struct wifi_ap_sta_node sta_list[CONFIG_WIFI_SHELL_MAX_AP_STA];

#define print(sh, level, fmt, ...) \
do { \
if (sh) { \
Expand Down Expand Up @@ -328,17 +336,42 @@ static void handle_wifi_ap_disable_result(struct net_mgmt_event_callback *cb)
} else {
print(context.sh, SHELL_NORMAL, "AP disabled\n");
}

k_mutex_lock(&wifi_ap_sta_list_lock, K_FOREVER);
for (int i = 0; i < CONFIG_WIFI_SHELL_MAX_AP_STA; i++) {
if (!sta_list[i].valid) {
continue;
}

sta_list[i].valid = false;
}
k_mutex_unlock(&wifi_ap_sta_list_lock);
}

static void handle_wifi_ap_sta_connected(struct net_mgmt_event_callback *cb)
{
const struct wifi_ap_sta_info *sta_info =
(const struct wifi_ap_sta_info *)cb->info;
uint8_t mac_string_buf[sizeof("xx:xx:xx:xx:xx:xx")];
int i;

print(context.sh, SHELL_NORMAL, "Station connected: %s\n",
net_sprint_ll_addr_buf(sta_info->mac, WIFI_MAC_ADDR_LEN,
mac_string_buf, sizeof(mac_string_buf)));

k_mutex_lock(&wifi_ap_sta_list_lock, K_FOREVER);
for (i = 0; i < CONFIG_WIFI_SHELL_MAX_AP_STA; i++) {
if (!sta_list[i].valid) {
sta_list[i].sta_info = *sta_info;
sta_list[i].valid = true;
break;
}
}
if (i == CONFIG_WIFI_SHELL_MAX_AP_STA) {
print(context.sh, SHELL_WARNING, "No space to store station info: "
"Increase CONFIG_WIFI_SHELL_MAX_AP_STA\n");
}
k_mutex_unlock(&wifi_ap_sta_list_lock);
}

static void handle_wifi_ap_sta_disconnected(struct net_mgmt_event_callback *cb)
Expand All @@ -350,6 +383,20 @@ static void handle_wifi_ap_sta_disconnected(struct net_mgmt_event_callback *cb)
print(context.sh, SHELL_NORMAL, "Station disconnected: %s\n",
net_sprint_ll_addr_buf(sta_info->mac, WIFI_MAC_ADDR_LEN,
mac_string_buf, sizeof(mac_string_buf)));

k_mutex_lock(&wifi_ap_sta_list_lock, K_FOREVER);
for (int i = 0; i < CONFIG_WIFI_SHELL_MAX_AP_STA; i++) {
if (!sta_list[i].valid) {
continue;
}

if (!memcmp(sta_list[i].sta_info.mac, sta_info->mac,
WIFI_MAC_ADDR_LEN)) {
sta_list[i].valid = false;
break;
}
}
k_mutex_unlock(&wifi_ap_sta_list_lock);
}

static void wifi_mgmt_event_handler(struct net_mgmt_event_callback *cb,
Expand Down Expand Up @@ -1169,6 +1216,8 @@ static int cmd_wifi_ap_enable(const struct shell *sh, size_t argc,

context.sh = sh;

k_mutex_init(&wifi_ap_sta_list_lock);

ret = net_mgmt(NET_REQUEST_WIFI_AP_ENABLE, iface, &cnx_params,
sizeof(struct wifi_connect_req_params));
if (ret) {
Expand Down Expand Up @@ -1197,6 +1246,50 @@ static int cmd_wifi_ap_disable(const struct shell *sh, size_t argc,
return 0;
}

static int cmd_wifi_ap_stations(const struct shell *sh, size_t argc,
char *argv[])
{
size_t id = 1;

(void)argv;
(void)argc;

shell_fprintf(sh, SHELL_NORMAL, "AP stations:\n");
shell_fprintf(sh, SHELL_NORMAL, "============\n");

k_mutex_lock(&wifi_ap_sta_list_lock, K_FOREVER);
for (int i = 0; i < CONFIG_WIFI_SHELL_MAX_AP_STA; i++) {
struct wifi_ap_sta_info *sta;

if (!sta_list[i].valid) {
continue;
}

sta = &sta_list[i].sta_info;

shell_fprintf(sh, SHELL_NORMAL, "Station %zu:\n", id++);
shell_fprintf(sh, SHELL_NORMAL, "==========\n");
uint8_t mac_string_buf[sizeof("xx:xx:xx:xx:xx:xx")];

shell_fprintf(sh, SHELL_NORMAL, "MAC: %s\n",
net_sprint_ll_addr_buf(sta->mac,
WIFI_MAC_ADDR_LEN,
mac_string_buf,
sizeof(mac_string_buf)));
shell_fprintf(sh, SHELL_NORMAL, "Link mode: %s\n",
wifi_link_mode_txt(sta->link_mode));
shell_fprintf(sh, SHELL_NORMAL, "TWT: %s\n",
sta->twt_capable ? "Supported" : "Not supported");
}

if (id == 1) {
shell_fprintf(sh, SHELL_NORMAL, "No stations connected\n");
}
k_mutex_unlock(&wifi_ap_sta_list_lock);

return 0;
}


static int cmd_wifi_reg_domain(const struct shell *sh, size_t argc,
char *argv[])
Expand Down Expand Up @@ -1675,6 +1768,10 @@ SHELL_STATIC_SUBCMD_SET_CREATE(wifi_cmd_ap,
": 0:Disable, 1:Optional, 2:Required.\n",
cmd_wifi_ap_enable,
2, 4),
SHELL_CMD_ARG(stations, NULL,
"List stations connected to the AP",
cmd_wifi_ap_stations,
1, 0),
SHELL_SUBCMD_SET_END
);

Expand Down

0 comments on commit 496decf

Please sign in to comment.