Move ACL control interface commands into shared files

This is a step towards allowing these commands to be used from
wpa_supplicant.

Signed-off-by: Chaoli Zhou <quic_zchaoli@quicinc.com>
This commit is contained in:
Chaoli Zhou 2022-03-24 13:48:57 +08:00 committed by Jouni Malinen
parent 9306956626
commit f5ac428116
7 changed files with 172 additions and 162 deletions

View file

@ -118,52 +118,6 @@ static int hostapd_config_read_vlan_file(struct hostapd_bss_config *bss,
#endif /* CONFIG_NO_VLAN */ #endif /* CONFIG_NO_VLAN */
int hostapd_acl_comp(const void *a, const void *b)
{
const struct mac_acl_entry *aa = a;
const struct mac_acl_entry *bb = b;
return os_memcmp(aa->addr, bb->addr, sizeof(macaddr));
}
int hostapd_add_acl_maclist(struct mac_acl_entry **acl, int *num,
int vlan_id, const u8 *addr)
{
struct mac_acl_entry *newacl;
newacl = os_realloc_array(*acl, *num + 1, sizeof(**acl));
if (!newacl) {
wpa_printf(MSG_ERROR, "MAC list reallocation failed");
return -1;
}
*acl = newacl;
os_memcpy((*acl)[*num].addr, addr, ETH_ALEN);
os_memset(&(*acl)[*num].vlan_id, 0, sizeof((*acl)[*num].vlan_id));
(*acl)[*num].vlan_id.untagged = vlan_id;
(*acl)[*num].vlan_id.notempty = !!vlan_id;
(*num)++;
return 0;
}
void hostapd_remove_acl_mac(struct mac_acl_entry **acl, int *num,
const u8 *addr)
{
int i = 0;
while (i < *num) {
if (os_memcmp((*acl)[i].addr, addr, ETH_ALEN) == 0) {
os_remove_in_array(*acl, *num, sizeof(**acl), i);
(*num)--;
} else {
i++;
}
}
}
static int hostapd_config_read_maclist(const char *fname, static int hostapd_config_read_maclist(const char *fname,
struct mac_acl_entry **acl, int *num) struct mac_acl_entry **acl, int *num)
{ {

View file

@ -13,10 +13,5 @@ struct hostapd_config * hostapd_config_read(const char *fname);
int hostapd_set_iface(struct hostapd_config *conf, int hostapd_set_iface(struct hostapd_config *conf,
struct hostapd_bss_config *bss, const char *field, struct hostapd_bss_config *bss, const char *field,
char *value); char *value);
int hostapd_acl_comp(const void *a, const void *b);
int hostapd_add_acl_maclist(struct mac_acl_entry **acl, int *num,
int vlan_id, const u8 *addr);
void hostapd_remove_acl_mac(struct mac_acl_entry **acl, int *num,
const u8 *addr);
#endif /* CONFIG_FILE_H */ #endif /* CONFIG_FILE_H */

View file

@ -1133,43 +1133,6 @@ static int hostapd_ctrl_iface_get_config(struct hostapd_data *hapd,
} }
static void hostapd_disassoc_accept_mac(struct hostapd_data *hapd)
{
struct sta_info *sta;
struct vlan_description vlan_id;
if (hapd->conf->macaddr_acl != DENY_UNLESS_ACCEPTED)
return;
for (sta = hapd->sta_list; sta; sta = sta->next) {
if (!hostapd_maclist_found(hapd->conf->accept_mac,
hapd->conf->num_accept_mac,
sta->addr, &vlan_id) ||
(vlan_id.notempty &&
vlan_compare(&vlan_id, sta->vlan_desc)))
ap_sta_disconnect(hapd, sta, sta->addr,
WLAN_REASON_UNSPECIFIED);
}
}
static void hostapd_disassoc_deny_mac(struct hostapd_data *hapd)
{
struct sta_info *sta;
struct vlan_description vlan_id;
for (sta = hapd->sta_list; sta; sta = sta->next) {
if (hostapd_maclist_found(hapd->conf->deny_mac,
hapd->conf->num_deny_mac, sta->addr,
&vlan_id) &&
(!vlan_id.notempty ||
!vlan_compare(&vlan_id, sta->vlan_desc)))
ap_sta_disconnect(hapd, sta, sta->addr,
WLAN_REASON_UNSPECIFIED);
}
}
static int hostapd_ctrl_iface_set_band(struct hostapd_data *hapd, static int hostapd_ctrl_iface_set_band(struct hostapd_data *hapd,
const char *bands) const char *bands)
{ {
@ -3153,80 +3116,6 @@ static int hostapd_ctrl_driver_flags2(struct hostapd_iface *iface, char *buf,
} }
static int hostapd_ctrl_iface_acl_del_mac(struct mac_acl_entry **acl, int *num,
const char *txtaddr)
{
u8 addr[ETH_ALEN];
struct vlan_description vlan_id;
if (!(*num))
return 0;
if (hwaddr_aton(txtaddr, addr))
return -1;
if (hostapd_maclist_found(*acl, *num, addr, &vlan_id))
hostapd_remove_acl_mac(acl, num, addr);
return 0;
}
static void hostapd_ctrl_iface_acl_clear_list(struct mac_acl_entry **acl,
int *num)
{
while (*num)
hostapd_remove_acl_mac(acl, num, (*acl)[0].addr);
}
static int hostapd_ctrl_iface_acl_show_mac(struct mac_acl_entry *acl, int num,
char *buf, size_t buflen)
{
int i = 0, len = 0, ret = 0;
if (!acl)
return 0;
while (i < num) {
ret = os_snprintf(buf + len, buflen - len,
MACSTR " VLAN_ID=%d\n",
MAC2STR(acl[i].addr),
acl[i].vlan_id.untagged);
if (ret < 0 || (size_t) ret >= buflen - len)
return len;
i++;
len += ret;
}
return len;
}
static int hostapd_ctrl_iface_acl_add_mac(struct mac_acl_entry **acl, int *num,
const char *cmd)
{
u8 addr[ETH_ALEN];
struct vlan_description vlan_id;
int ret = 0, vlanid = 0;
const char *pos;
if (hwaddr_aton(cmd, addr))
return -1;
pos = os_strstr(cmd, "VLAN_ID=");
if (pos)
vlanid = atoi(pos + 8);
if (!hostapd_maclist_found(*acl, *num, addr, &vlan_id)) {
ret = hostapd_add_acl_maclist(acl, num, vlanid, addr);
if (ret != -1 && *acl)
qsort(*acl, *num, sizeof(**acl), hostapd_acl_comp);
}
return ret < 0 ? -1 : 0;
}
static int hostapd_ctrl_iface_get_capability(struct hostapd_data *hapd, static int hostapd_ctrl_iface_get_capability(struct hostapd_data *hapd,
const char *field, char *buf, const char *field, char *buf,
size_t buflen) size_t buflen)

View file

@ -1646,3 +1646,49 @@ bool hostapd_sae_pk_exclusively(struct hostapd_bss_config *conf)
return with_pk; return with_pk;
} }
#endif /* CONFIG_SAE_PK */ #endif /* CONFIG_SAE_PK */
int hostapd_acl_comp(const void *a, const void *b)
{
const struct mac_acl_entry *aa = a;
const struct mac_acl_entry *bb = b;
return os_memcmp(aa->addr, bb->addr, sizeof(macaddr));
}
int hostapd_add_acl_maclist(struct mac_acl_entry **acl, int *num,
int vlan_id, const u8 *addr)
{
struct mac_acl_entry *newacl;
newacl = os_realloc_array(*acl, *num + 1, sizeof(**acl));
if (!newacl) {
wpa_printf(MSG_ERROR, "MAC list reallocation failed");
return -1;
}
*acl = newacl;
os_memcpy((*acl)[*num].addr, addr, ETH_ALEN);
os_memset(&(*acl)[*num].vlan_id, 0, sizeof((*acl)[*num].vlan_id));
(*acl)[*num].vlan_id.untagged = vlan_id;
(*acl)[*num].vlan_id.notempty = !!vlan_id;
(*num)++;
return 0;
}
void hostapd_remove_acl_mac(struct mac_acl_entry **acl, int *num,
const u8 *addr)
{
int i = 0;
while (i < *num) {
if (os_memcmp((*acl)[i].addr, addr, ETH_ALEN) == 0) {
os_remove_in_array(*acl, *num, sizeof(**acl), i);
(*num)--;
} else {
i++;
}
}
}

View file

@ -1202,5 +1202,10 @@ int hostapd_sae_pw_id_in_use(struct hostapd_bss_config *conf);
bool hostapd_sae_pk_in_use(struct hostapd_bss_config *conf); bool hostapd_sae_pk_in_use(struct hostapd_bss_config *conf);
bool hostapd_sae_pk_exclusively(struct hostapd_bss_config *conf); bool hostapd_sae_pk_exclusively(struct hostapd_bss_config *conf);
int hostapd_setup_sae_pt(struct hostapd_bss_config *conf); int hostapd_setup_sae_pt(struct hostapd_bss_config *conf);
int hostapd_acl_comp(const void *a, const void *b);
int hostapd_add_acl_maclist(struct mac_acl_entry **acl, int *num,
int vlan_id, const u8 *addr);
void hostapd_remove_acl_mac(struct mac_acl_entry **acl, int *num,
const u8 *addr);
#endif /* HOSTAPD_CONFIG_H */ #endif /* HOSTAPD_CONFIG_H */

View file

@ -1281,3 +1281,114 @@ fail:
} }
#endif /* CONFIG_WNM_AP */ #endif /* CONFIG_WNM_AP */
int hostapd_ctrl_iface_acl_del_mac(struct mac_acl_entry **acl, int *num,
const char *txtaddr)
{
u8 addr[ETH_ALEN];
struct vlan_description vlan_id;
if (!(*num))
return 0;
if (hwaddr_aton(txtaddr, addr))
return -1;
if (hostapd_maclist_found(*acl, *num, addr, &vlan_id))
hostapd_remove_acl_mac(acl, num, addr);
return 0;
}
void hostapd_ctrl_iface_acl_clear_list(struct mac_acl_entry **acl,
int *num)
{
while (*num)
hostapd_remove_acl_mac(acl, num, (*acl)[0].addr);
}
int hostapd_ctrl_iface_acl_show_mac(struct mac_acl_entry *acl, int num,
char *buf, size_t buflen)
{
int i = 0, len = 0, ret = 0;
if (!acl)
return 0;
while (i < num) {
ret = os_snprintf(buf + len, buflen - len,
MACSTR " VLAN_ID=%d\n",
MAC2STR(acl[i].addr),
acl[i].vlan_id.untagged);
if (ret < 0 || (size_t) ret >= buflen - len)
return len;
i++;
len += ret;
}
return len;
}
int hostapd_ctrl_iface_acl_add_mac(struct mac_acl_entry **acl, int *num,
const char *cmd)
{
u8 addr[ETH_ALEN];
struct vlan_description vlan_id;
int ret = 0, vlanid = 0;
const char *pos;
if (hwaddr_aton(cmd, addr))
return -1;
pos = os_strstr(cmd, "VLAN_ID=");
if (pos)
vlanid = atoi(pos + 8);
if (!hostapd_maclist_found(*acl, *num, addr, &vlan_id)) {
ret = hostapd_add_acl_maclist(acl, num, vlanid, addr);
if (ret != -1 && *acl)
qsort(*acl, *num, sizeof(**acl), hostapd_acl_comp);
}
return ret < 0 ? -1 : 0;
}
void hostapd_disassoc_accept_mac(struct hostapd_data *hapd)
{
struct sta_info *sta;
struct vlan_description vlan_id;
if (hapd->conf->macaddr_acl != DENY_UNLESS_ACCEPTED)
return;
for (sta = hapd->sta_list; sta; sta = sta->next) {
if (!hostapd_maclist_found(hapd->conf->accept_mac,
hapd->conf->num_accept_mac,
sta->addr, &vlan_id) ||
(vlan_id.notempty &&
vlan_compare(&vlan_id, sta->vlan_desc)))
ap_sta_disconnect(hapd, sta, sta->addr,
WLAN_REASON_UNSPECIFIED);
}
}
void hostapd_disassoc_deny_mac(struct hostapd_data *hapd)
{
struct sta_info *sta;
struct vlan_description vlan_id;
for (sta = hapd->sta_list; sta; sta = sta->next) {
if (hostapd_maclist_found(hapd->conf->deny_mac,
hapd->conf->num_deny_mac, sta->addr,
&vlan_id) &&
(!vlan_id.notempty ||
!vlan_compare(&vlan_id, sta->vlan_desc)))
ap_sta_disconnect(hapd, sta, sta->addr,
WLAN_REASON_UNSPECIFIED);
}
}

View file

@ -43,5 +43,15 @@ int hostapd_ctrl_iface_ess_disassoc(struct hostapd_data *hapd,
const char *cmd); const char *cmd);
int hostapd_ctrl_iface_bss_tm_req(struct hostapd_data *hapd, int hostapd_ctrl_iface_bss_tm_req(struct hostapd_data *hapd,
const char *cmd); const char *cmd);
int hostapd_ctrl_iface_acl_add_mac(struct mac_acl_entry **acl, int *num,
const char *cmd);
int hostapd_ctrl_iface_acl_del_mac(struct mac_acl_entry **acl, int *num,
const char *txtaddr);
void hostapd_ctrl_iface_acl_clear_list(struct mac_acl_entry **acl,
int *num);
int hostapd_ctrl_iface_acl_show_mac(struct mac_acl_entry *acl, int num,
char *buf, size_t buflen);
void hostapd_disassoc_accept_mac(struct hostapd_data *hapd);
void hostapd_disassoc_deny_mac(struct hostapd_data *hapd);
#endif /* CTRL_IFACE_AP_H */ #endif /* CTRL_IFACE_AP_H */