| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 1 | /* | 
|  | 2 | * hostapd / Configuration file parser | 
| Sunil Ravi | eb83e2a | 2024-06-28 17:34:56 +0000 | [diff] [blame] | 3 | * Copyright (c) 2003-2018, Jouni Malinen <j@w1.fi> | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 4 | * | 
| Dmitry Shmidt | c5ec7f5 | 2012-03-06 16:33:24 -0800 | [diff] [blame] | 5 | * This software may be distributed under the terms of the BSD license. | 
|  | 6 | * See README for more details. | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 7 | */ | 
|  | 8 |  | 
|  | 9 | #include "utils/includes.h" | 
|  | 10 | #ifndef CONFIG_NATIVE_WINDOWS | 
|  | 11 | #include <grp.h> | 
|  | 12 | #endif /* CONFIG_NATIVE_WINDOWS */ | 
|  | 13 |  | 
|  | 14 | #include "utils/common.h" | 
|  | 15 | #include "utils/uuid.h" | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 16 | #include "utils/crc32.h" | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 17 | #include "common/ieee802_11_defs.h" | 
| Hai Shalom | 899fcc7 | 2020-10-19 14:38:18 -0700 | [diff] [blame] | 18 | #include "common/sae.h" | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 19 | #include "crypto/sha256.h" | 
|  | 20 | #include "crypto/tls.h" | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 21 | #include "drivers/driver.h" | 
|  | 22 | #include "eap_server/eap.h" | 
|  | 23 | #include "radius/radius_client.h" | 
|  | 24 | #include "ap/wpa_auth.h" | 
|  | 25 | #include "ap/ap_config.h" | 
|  | 26 | #include "config_file.h" | 
|  | 27 |  | 
|  | 28 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 29 | #ifndef CONFIG_NO_VLAN | 
|  | 30 | static int hostapd_config_read_vlan_file(struct hostapd_bss_config *bss, | 
|  | 31 | const char *fname) | 
|  | 32 | { | 
|  | 33 | FILE *f; | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 34 | char buf[128], *pos, *pos2, *pos3; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 35 | int line = 0, vlan_id; | 
|  | 36 | struct hostapd_vlan *vlan; | 
|  | 37 |  | 
|  | 38 | f = fopen(fname, "r"); | 
|  | 39 | if (!f) { | 
|  | 40 | wpa_printf(MSG_ERROR, "VLAN file '%s' not readable.", fname); | 
|  | 41 | return -1; | 
|  | 42 | } | 
|  | 43 |  | 
|  | 44 | while (fgets(buf, sizeof(buf), f)) { | 
|  | 45 | line++; | 
|  | 46 |  | 
|  | 47 | if (buf[0] == '#') | 
|  | 48 | continue; | 
|  | 49 | pos = buf; | 
|  | 50 | while (*pos != '\0') { | 
|  | 51 | if (*pos == '\n') { | 
|  | 52 | *pos = '\0'; | 
|  | 53 | break; | 
|  | 54 | } | 
|  | 55 | pos++; | 
|  | 56 | } | 
|  | 57 | if (buf[0] == '\0') | 
|  | 58 | continue; | 
|  | 59 |  | 
|  | 60 | if (buf[0] == '*') { | 
|  | 61 | vlan_id = VLAN_ID_WILDCARD; | 
|  | 62 | pos = buf + 1; | 
|  | 63 | } else { | 
|  | 64 | vlan_id = strtol(buf, &pos, 10); | 
|  | 65 | if (buf == pos || vlan_id < 1 || | 
|  | 66 | vlan_id > MAX_VLAN_ID) { | 
|  | 67 | wpa_printf(MSG_ERROR, "Invalid VLAN ID at " | 
|  | 68 | "line %d in '%s'", line, fname); | 
|  | 69 | fclose(f); | 
|  | 70 | return -1; | 
|  | 71 | } | 
|  | 72 | } | 
|  | 73 |  | 
|  | 74 | while (*pos == ' ' || *pos == '\t') | 
|  | 75 | pos++; | 
|  | 76 | pos2 = pos; | 
|  | 77 | while (*pos2 != ' ' && *pos2 != '\t' && *pos2 != '\0') | 
|  | 78 | pos2++; | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 79 |  | 
|  | 80 | if (*pos2 != '\0') | 
|  | 81 | *(pos2++) = '\0'; | 
|  | 82 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 83 | if (*pos == '\0' || os_strlen(pos) > IFNAMSIZ) { | 
|  | 84 | wpa_printf(MSG_ERROR, "Invalid VLAN ifname at line %d " | 
|  | 85 | "in '%s'", line, fname); | 
|  | 86 | fclose(f); | 
|  | 87 | return -1; | 
|  | 88 | } | 
|  | 89 |  | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 90 | while (*pos2 == ' ' || *pos2 == '\t') | 
|  | 91 | pos2++; | 
|  | 92 | pos3 = pos2; | 
|  | 93 | while (*pos3 != ' ' && *pos3 != '\t' && *pos3 != '\0') | 
|  | 94 | pos3++; | 
|  | 95 | *pos3 = '\0'; | 
|  | 96 |  | 
| Dmitry Shmidt | 4b06059 | 2013-04-29 16:42:49 -0700 | [diff] [blame] | 97 | vlan = os_zalloc(sizeof(*vlan)); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 98 | if (vlan == NULL) { | 
|  | 99 | wpa_printf(MSG_ERROR, "Out of memory while reading " | 
|  | 100 | "VLAN interfaces from '%s'", fname); | 
|  | 101 | fclose(f); | 
|  | 102 | return -1; | 
|  | 103 | } | 
|  | 104 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 105 | vlan->vlan_id = vlan_id; | 
| Dmitry Shmidt | 57c2d39 | 2016-02-23 13:40:19 -0800 | [diff] [blame] | 106 | vlan->vlan_desc.untagged = vlan_id; | 
|  | 107 | vlan->vlan_desc.notempty = !!vlan_id; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 108 | os_strlcpy(vlan->ifname, pos, sizeof(vlan->ifname)); | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 109 | os_strlcpy(vlan->bridge, pos2, sizeof(vlan->bridge)); | 
| Dmitry Shmidt | d5c075b | 2013-08-05 14:36:10 -0700 | [diff] [blame] | 110 | vlan->next = bss->vlan; | 
|  | 111 | bss->vlan = vlan; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 112 | } | 
|  | 113 |  | 
|  | 114 | fclose(f); | 
|  | 115 |  | 
|  | 116 | return 0; | 
|  | 117 | } | 
|  | 118 | #endif /* CONFIG_NO_VLAN */ | 
|  | 119 |  | 
|  | 120 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 121 | static int hostapd_config_read_maclist(const char *fname, | 
|  | 122 | struct mac_acl_entry **acl, int *num) | 
|  | 123 | { | 
|  | 124 | FILE *f; | 
|  | 125 | char buf[128], *pos; | 
|  | 126 | int line = 0; | 
|  | 127 | u8 addr[ETH_ALEN]; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 128 | int vlan_id; | 
|  | 129 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 130 | f = fopen(fname, "r"); | 
|  | 131 | if (!f) { | 
|  | 132 | wpa_printf(MSG_ERROR, "MAC list file '%s' not found.", fname); | 
|  | 133 | return -1; | 
|  | 134 | } | 
|  | 135 |  | 
|  | 136 | while (fgets(buf, sizeof(buf), f)) { | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 137 | int rem = 0; | 
| Dmitry Shmidt | f21452a | 2014-02-26 10:55:25 -0800 | [diff] [blame] | 138 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 139 | line++; | 
|  | 140 |  | 
|  | 141 | if (buf[0] == '#') | 
|  | 142 | continue; | 
|  | 143 | pos = buf; | 
|  | 144 | while (*pos != '\0') { | 
|  | 145 | if (*pos == '\n') { | 
|  | 146 | *pos = '\0'; | 
|  | 147 | break; | 
|  | 148 | } | 
|  | 149 | pos++; | 
|  | 150 | } | 
|  | 151 | if (buf[0] == '\0') | 
|  | 152 | continue; | 
| Dmitry Shmidt | f21452a | 2014-02-26 10:55:25 -0800 | [diff] [blame] | 153 | pos = buf; | 
|  | 154 | if (buf[0] == '-') { | 
|  | 155 | rem = 1; | 
|  | 156 | pos++; | 
|  | 157 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 158 |  | 
| Dmitry Shmidt | f21452a | 2014-02-26 10:55:25 -0800 | [diff] [blame] | 159 | if (hwaddr_aton(pos, addr)) { | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 160 | wpa_printf(MSG_ERROR, "Invalid MAC address '%s' at " | 
| Dmitry Shmidt | f21452a | 2014-02-26 10:55:25 -0800 | [diff] [blame] | 161 | "line %d in '%s'", pos, line, fname); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 162 | fclose(f); | 
|  | 163 | return -1; | 
|  | 164 | } | 
|  | 165 |  | 
| Dmitry Shmidt | f21452a | 2014-02-26 10:55:25 -0800 | [diff] [blame] | 166 | if (rem) { | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 167 | hostapd_remove_acl_mac(acl, num, addr); | 
| Dmitry Shmidt | f21452a | 2014-02-26 10:55:25 -0800 | [diff] [blame] | 168 | continue; | 
|  | 169 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 170 | vlan_id = 0; | 
|  | 171 | pos = buf; | 
|  | 172 | while (*pos != '\0' && *pos != ' ' && *pos != '\t') | 
|  | 173 | pos++; | 
|  | 174 | while (*pos == ' ' || *pos == '\t') | 
|  | 175 | pos++; | 
|  | 176 | if (*pos != '\0') | 
|  | 177 | vlan_id = atoi(pos); | 
|  | 178 |  | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 179 | if (hostapd_add_acl_maclist(acl, num, vlan_id, addr) < 0) { | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 180 | fclose(f); | 
|  | 181 | return -1; | 
|  | 182 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 183 | } | 
|  | 184 |  | 
|  | 185 | fclose(f); | 
|  | 186 |  | 
| Dmitry Shmidt | 9839ecd | 2016-11-07 11:05:47 -0800 | [diff] [blame] | 187 | if (*acl) | 
|  | 188 | qsort(*acl, *num, sizeof(**acl), hostapd_acl_comp); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 189 |  | 
|  | 190 | return 0; | 
|  | 191 | } | 
|  | 192 |  | 
|  | 193 |  | 
|  | 194 | #ifdef EAP_SERVER | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 195 |  | 
|  | 196 | static int hostapd_config_eap_user_salted(struct hostapd_eap_user *user, | 
|  | 197 | const char *hash, size_t len, | 
|  | 198 | char **pos, int line, | 
|  | 199 | const char *fname) | 
|  | 200 | { | 
|  | 201 | char *pos2 = *pos; | 
|  | 202 |  | 
|  | 203 | while (*pos2 != '\0' && *pos2 != ' ' && *pos2 != '\t' && *pos2 != '#') | 
|  | 204 | pos2++; | 
|  | 205 |  | 
|  | 206 | if (pos2 - *pos < (int) (2 * (len + 1))) { /* at least 1 byte of salt */ | 
|  | 207 | wpa_printf(MSG_ERROR, | 
|  | 208 | "Invalid salted %s hash on line %d in '%s'", | 
|  | 209 | hash, line, fname); | 
|  | 210 | return -1; | 
|  | 211 | } | 
|  | 212 |  | 
|  | 213 | user->password = os_malloc(len); | 
|  | 214 | if (!user->password) { | 
|  | 215 | wpa_printf(MSG_ERROR, | 
|  | 216 | "Failed to allocate memory for salted %s hash", | 
|  | 217 | hash); | 
|  | 218 | return -1; | 
|  | 219 | } | 
|  | 220 |  | 
|  | 221 | if (hexstr2bin(*pos, user->password, len) < 0) { | 
|  | 222 | wpa_printf(MSG_ERROR, | 
|  | 223 | "Invalid salted password on line %d in '%s'", | 
|  | 224 | line, fname); | 
|  | 225 | return -1; | 
|  | 226 | } | 
|  | 227 | user->password_len = len; | 
|  | 228 | *pos += 2 * len; | 
|  | 229 |  | 
|  | 230 | user->salt_len = (pos2 - *pos) / 2; | 
|  | 231 | user->salt = os_malloc(user->salt_len); | 
|  | 232 | if (!user->salt) { | 
|  | 233 | wpa_printf(MSG_ERROR, | 
|  | 234 | "Failed to allocate memory for salted %s hash", | 
|  | 235 | hash); | 
|  | 236 | return -1; | 
|  | 237 | } | 
|  | 238 |  | 
|  | 239 | if (hexstr2bin(*pos, user->salt, user->salt_len) < 0) { | 
|  | 240 | wpa_printf(MSG_ERROR, | 
|  | 241 | "Invalid salt for password on line %d in '%s'", | 
|  | 242 | line, fname); | 
|  | 243 | return -1; | 
|  | 244 | } | 
|  | 245 |  | 
|  | 246 | *pos = pos2; | 
|  | 247 | return 0; | 
|  | 248 | } | 
|  | 249 |  | 
|  | 250 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 251 | static int hostapd_config_read_eap_user(const char *fname, | 
|  | 252 | struct hostapd_bss_config *conf) | 
|  | 253 | { | 
|  | 254 | FILE *f; | 
|  | 255 | char buf[512], *pos, *start, *pos2; | 
|  | 256 | int line = 0, ret = 0, num_methods; | 
| Dmitry Shmidt | 216983b | 2015-02-06 10:50:36 -0800 | [diff] [blame] | 257 | struct hostapd_eap_user *user = NULL, *tail = NULL, *new_user = NULL; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 258 |  | 
| Dmitry Shmidt | d5e4923 | 2012-12-03 15:08:10 -0800 | [diff] [blame] | 259 | if (os_strncmp(fname, "sqlite:", 7) == 0) { | 
| Dmitry Shmidt | 912c6ec | 2015-03-30 13:16:51 -0700 | [diff] [blame] | 260 | #ifdef CONFIG_SQLITE | 
| Dmitry Shmidt | d5e4923 | 2012-12-03 15:08:10 -0800 | [diff] [blame] | 261 | os_free(conf->eap_user_sqlite); | 
|  | 262 | conf->eap_user_sqlite = os_strdup(fname + 7); | 
|  | 263 | return 0; | 
| Dmitry Shmidt | 912c6ec | 2015-03-30 13:16:51 -0700 | [diff] [blame] | 264 | #else /* CONFIG_SQLITE */ | 
|  | 265 | wpa_printf(MSG_ERROR, | 
|  | 266 | "EAP user file in SQLite DB, but CONFIG_SQLITE was not enabled in the build."); | 
|  | 267 | return -1; | 
|  | 268 | #endif /* CONFIG_SQLITE */ | 
| Dmitry Shmidt | d5e4923 | 2012-12-03 15:08:10 -0800 | [diff] [blame] | 269 | } | 
|  | 270 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 271 | f = fopen(fname, "r"); | 
|  | 272 | if (!f) { | 
|  | 273 | wpa_printf(MSG_ERROR, "EAP user file '%s' not found.", fname); | 
|  | 274 | return -1; | 
|  | 275 | } | 
|  | 276 |  | 
|  | 277 | /* Lines: "user" METHOD,METHOD2 "password" (password optional) */ | 
|  | 278 | while (fgets(buf, sizeof(buf), f)) { | 
|  | 279 | line++; | 
|  | 280 |  | 
|  | 281 | if (buf[0] == '#') | 
|  | 282 | continue; | 
|  | 283 | pos = buf; | 
|  | 284 | while (*pos != '\0') { | 
|  | 285 | if (*pos == '\n') { | 
|  | 286 | *pos = '\0'; | 
|  | 287 | break; | 
|  | 288 | } | 
|  | 289 | pos++; | 
|  | 290 | } | 
|  | 291 | if (buf[0] == '\0') | 
|  | 292 | continue; | 
|  | 293 |  | 
| Dmitry Shmidt | 818ea48 | 2014-03-10 13:15:21 -0700 | [diff] [blame] | 294 | #ifndef CONFIG_NO_RADIUS | 
|  | 295 | if (user && os_strncmp(buf, "radius_accept_attr=", 19) == 0) { | 
|  | 296 | struct hostapd_radius_attr *attr, *a; | 
|  | 297 | attr = hostapd_parse_radius_attr(buf + 19); | 
|  | 298 | if (attr == NULL) { | 
| Hai Shalom | 899fcc7 | 2020-10-19 14:38:18 -0700 | [diff] [blame] | 299 | wpa_printf(MSG_ERROR, "Invalid radius_accept_attr: %s", | 
| Dmitry Shmidt | 818ea48 | 2014-03-10 13:15:21 -0700 | [diff] [blame] | 300 | buf + 19); | 
| Dmitry Shmidt | 9866086 | 2014-03-11 17:26:21 -0700 | [diff] [blame] | 301 | user = NULL; /* already in the BSS list */ | 
| Dmitry Shmidt | 818ea48 | 2014-03-10 13:15:21 -0700 | [diff] [blame] | 302 | goto failed; | 
|  | 303 | } | 
|  | 304 | if (user->accept_attr == NULL) { | 
|  | 305 | user->accept_attr = attr; | 
|  | 306 | } else { | 
|  | 307 | a = user->accept_attr; | 
|  | 308 | while (a->next) | 
|  | 309 | a = a->next; | 
|  | 310 | a->next = attr; | 
|  | 311 | } | 
|  | 312 | continue; | 
|  | 313 | } | 
|  | 314 | #endif /* CONFIG_NO_RADIUS */ | 
|  | 315 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 316 | user = NULL; | 
|  | 317 |  | 
|  | 318 | if (buf[0] != '"' && buf[0] != '*') { | 
|  | 319 | wpa_printf(MSG_ERROR, "Invalid EAP identity (no \" in " | 
|  | 320 | "start) on line %d in '%s'", line, fname); | 
|  | 321 | goto failed; | 
|  | 322 | } | 
|  | 323 |  | 
|  | 324 | user = os_zalloc(sizeof(*user)); | 
|  | 325 | if (user == NULL) { | 
|  | 326 | wpa_printf(MSG_ERROR, "EAP user allocation failed"); | 
|  | 327 | goto failed; | 
|  | 328 | } | 
|  | 329 | user->force_version = -1; | 
|  | 330 |  | 
|  | 331 | if (buf[0] == '*') { | 
|  | 332 | pos = buf; | 
|  | 333 | } else { | 
|  | 334 | pos = buf + 1; | 
|  | 335 | start = pos; | 
|  | 336 | while (*pos != '"' && *pos != '\0') | 
|  | 337 | pos++; | 
|  | 338 | if (*pos == '\0') { | 
|  | 339 | wpa_printf(MSG_ERROR, "Invalid EAP identity " | 
|  | 340 | "(no \" in end) on line %d in '%s'", | 
|  | 341 | line, fname); | 
|  | 342 | goto failed; | 
|  | 343 | } | 
|  | 344 |  | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 345 | user->identity = os_memdup(start, pos - start); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 346 | if (user->identity == NULL) { | 
|  | 347 | wpa_printf(MSG_ERROR, "Failed to allocate " | 
|  | 348 | "memory for EAP identity"); | 
|  | 349 | goto failed; | 
|  | 350 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 351 | user->identity_len = pos - start; | 
|  | 352 |  | 
|  | 353 | if (pos[0] == '"' && pos[1] == '*') { | 
|  | 354 | user->wildcard_prefix = 1; | 
|  | 355 | pos++; | 
|  | 356 | } | 
|  | 357 | } | 
|  | 358 | pos++; | 
|  | 359 | while (*pos == ' ' || *pos == '\t') | 
|  | 360 | pos++; | 
|  | 361 |  | 
|  | 362 | if (*pos == '\0') { | 
|  | 363 | wpa_printf(MSG_ERROR, "No EAP method on line %d in " | 
|  | 364 | "'%s'", line, fname); | 
|  | 365 | goto failed; | 
|  | 366 | } | 
|  | 367 |  | 
|  | 368 | start = pos; | 
|  | 369 | while (*pos != ' ' && *pos != '\t' && *pos != '\0') | 
|  | 370 | pos++; | 
|  | 371 | if (*pos == '\0') { | 
|  | 372 | pos = NULL; | 
|  | 373 | } else { | 
|  | 374 | *pos = '\0'; | 
|  | 375 | pos++; | 
|  | 376 | } | 
|  | 377 | num_methods = 0; | 
|  | 378 | while (*start) { | 
|  | 379 | char *pos3 = os_strchr(start, ','); | 
|  | 380 | if (pos3) { | 
|  | 381 | *pos3++ = '\0'; | 
|  | 382 | } | 
|  | 383 | user->methods[num_methods].method = | 
|  | 384 | eap_server_get_type( | 
|  | 385 | start, | 
|  | 386 | &user->methods[num_methods].vendor); | 
|  | 387 | if (user->methods[num_methods].vendor == | 
|  | 388 | EAP_VENDOR_IETF && | 
|  | 389 | user->methods[num_methods].method == EAP_TYPE_NONE) | 
|  | 390 | { | 
|  | 391 | if (os_strcmp(start, "TTLS-PAP") == 0) { | 
|  | 392 | user->ttls_auth |= EAP_TTLS_AUTH_PAP; | 
|  | 393 | goto skip_eap; | 
|  | 394 | } | 
|  | 395 | if (os_strcmp(start, "TTLS-CHAP") == 0) { | 
|  | 396 | user->ttls_auth |= EAP_TTLS_AUTH_CHAP; | 
|  | 397 | goto skip_eap; | 
|  | 398 | } | 
|  | 399 | if (os_strcmp(start, "TTLS-MSCHAP") == 0) { | 
|  | 400 | user->ttls_auth |= | 
|  | 401 | EAP_TTLS_AUTH_MSCHAP; | 
|  | 402 | goto skip_eap; | 
|  | 403 | } | 
|  | 404 | if (os_strcmp(start, "TTLS-MSCHAPV2") == 0) { | 
|  | 405 | user->ttls_auth |= | 
|  | 406 | EAP_TTLS_AUTH_MSCHAPV2; | 
|  | 407 | goto skip_eap; | 
|  | 408 | } | 
| Dmitry Shmidt | df5a7e4 | 2014-04-02 12:59:59 -0700 | [diff] [blame] | 409 | if (os_strcmp(start, "MACACL") == 0) { | 
|  | 410 | user->macacl = 1; | 
|  | 411 | goto skip_eap; | 
|  | 412 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 413 | wpa_printf(MSG_ERROR, "Unsupported EAP type " | 
|  | 414 | "'%s' on line %d in '%s'", | 
|  | 415 | start, line, fname); | 
|  | 416 | goto failed; | 
|  | 417 | } | 
|  | 418 |  | 
|  | 419 | num_methods++; | 
| Dmitry Shmidt | 1f69aa5 | 2012-01-24 16:10:04 -0800 | [diff] [blame] | 420 | if (num_methods >= EAP_MAX_METHODS) | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 421 | break; | 
|  | 422 | skip_eap: | 
|  | 423 | if (pos3 == NULL) | 
|  | 424 | break; | 
|  | 425 | start = pos3; | 
|  | 426 | } | 
| Dmitry Shmidt | df5a7e4 | 2014-04-02 12:59:59 -0700 | [diff] [blame] | 427 | if (num_methods == 0 && user->ttls_auth == 0 && !user->macacl) { | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 428 | wpa_printf(MSG_ERROR, "No EAP types configured on " | 
|  | 429 | "line %d in '%s'", line, fname); | 
|  | 430 | goto failed; | 
|  | 431 | } | 
|  | 432 |  | 
|  | 433 | if (pos == NULL) | 
|  | 434 | goto done; | 
|  | 435 |  | 
|  | 436 | while (*pos == ' ' || *pos == '\t') | 
|  | 437 | pos++; | 
|  | 438 | if (*pos == '\0') | 
|  | 439 | goto done; | 
|  | 440 |  | 
|  | 441 | if (os_strncmp(pos, "[ver=0]", 7) == 0) { | 
|  | 442 | user->force_version = 0; | 
|  | 443 | goto done; | 
|  | 444 | } | 
|  | 445 |  | 
|  | 446 | if (os_strncmp(pos, "[ver=1]", 7) == 0) { | 
|  | 447 | user->force_version = 1; | 
|  | 448 | goto done; | 
|  | 449 | } | 
|  | 450 |  | 
|  | 451 | if (os_strncmp(pos, "[2]", 3) == 0) { | 
|  | 452 | user->phase2 = 1; | 
|  | 453 | goto done; | 
|  | 454 | } | 
|  | 455 |  | 
|  | 456 | if (*pos == '"') { | 
|  | 457 | pos++; | 
|  | 458 | start = pos; | 
|  | 459 | while (*pos != '"' && *pos != '\0') | 
|  | 460 | pos++; | 
|  | 461 | if (*pos == '\0') { | 
|  | 462 | wpa_printf(MSG_ERROR, "Invalid EAP password " | 
|  | 463 | "(no \" in end) on line %d in '%s'", | 
|  | 464 | line, fname); | 
|  | 465 | goto failed; | 
|  | 466 | } | 
|  | 467 |  | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 468 | user->password = os_memdup(start, pos - start); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 469 | if (user->password == NULL) { | 
|  | 470 | wpa_printf(MSG_ERROR, "Failed to allocate " | 
|  | 471 | "memory for EAP password"); | 
|  | 472 | goto failed; | 
|  | 473 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 474 | user->password_len = pos - start; | 
|  | 475 |  | 
|  | 476 | pos++; | 
|  | 477 | } else if (os_strncmp(pos, "hash:", 5) == 0) { | 
|  | 478 | pos += 5; | 
|  | 479 | pos2 = pos; | 
|  | 480 | while (*pos2 != '\0' && *pos2 != ' ' && | 
|  | 481 | *pos2 != '\t' && *pos2 != '#') | 
|  | 482 | pos2++; | 
|  | 483 | if (pos2 - pos != 32) { | 
|  | 484 | wpa_printf(MSG_ERROR, "Invalid password hash " | 
|  | 485 | "on line %d in '%s'", line, fname); | 
|  | 486 | goto failed; | 
|  | 487 | } | 
|  | 488 | user->password = os_malloc(16); | 
|  | 489 | if (user->password == NULL) { | 
|  | 490 | wpa_printf(MSG_ERROR, "Failed to allocate " | 
|  | 491 | "memory for EAP password hash"); | 
|  | 492 | goto failed; | 
|  | 493 | } | 
|  | 494 | if (hexstr2bin(pos, user->password, 16) < 0) { | 
|  | 495 | wpa_printf(MSG_ERROR, "Invalid hash password " | 
|  | 496 | "on line %d in '%s'", line, fname); | 
|  | 497 | goto failed; | 
|  | 498 | } | 
|  | 499 | user->password_len = 16; | 
|  | 500 | user->password_hash = 1; | 
|  | 501 | pos = pos2; | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 502 | } else if (os_strncmp(pos, "ssha1:", 6) == 0) { | 
|  | 503 | pos += 6; | 
|  | 504 | if (hostapd_config_eap_user_salted(user, "sha1", 20, | 
|  | 505 | &pos, | 
|  | 506 | line, fname) < 0) | 
|  | 507 | goto failed; | 
|  | 508 | } else if (os_strncmp(pos, "ssha256:", 8) == 0) { | 
|  | 509 | pos += 8; | 
|  | 510 | if (hostapd_config_eap_user_salted(user, "sha256", 32, | 
|  | 511 | &pos, | 
|  | 512 | line, fname) < 0) | 
|  | 513 | goto failed; | 
|  | 514 | } else if (os_strncmp(pos, "ssha512:", 8) == 0) { | 
|  | 515 | pos += 8; | 
|  | 516 | if (hostapd_config_eap_user_salted(user, "sha512", 64, | 
|  | 517 | &pos, | 
|  | 518 | line, fname) < 0) | 
|  | 519 | goto failed; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 520 | } else { | 
|  | 521 | pos2 = pos; | 
|  | 522 | while (*pos2 != '\0' && *pos2 != ' ' && | 
|  | 523 | *pos2 != '\t' && *pos2 != '#') | 
|  | 524 | pos2++; | 
|  | 525 | if ((pos2 - pos) & 1) { | 
|  | 526 | wpa_printf(MSG_ERROR, "Invalid hex password " | 
|  | 527 | "on line %d in '%s'", line, fname); | 
|  | 528 | goto failed; | 
|  | 529 | } | 
|  | 530 | user->password = os_malloc((pos2 - pos) / 2); | 
|  | 531 | if (user->password == NULL) { | 
|  | 532 | wpa_printf(MSG_ERROR, "Failed to allocate " | 
|  | 533 | "memory for EAP password"); | 
|  | 534 | goto failed; | 
|  | 535 | } | 
|  | 536 | if (hexstr2bin(pos, user->password, | 
|  | 537 | (pos2 - pos) / 2) < 0) { | 
|  | 538 | wpa_printf(MSG_ERROR, "Invalid hex password " | 
|  | 539 | "on line %d in '%s'", line, fname); | 
|  | 540 | goto failed; | 
|  | 541 | } | 
|  | 542 | user->password_len = (pos2 - pos) / 2; | 
|  | 543 | pos = pos2; | 
|  | 544 | } | 
|  | 545 |  | 
|  | 546 | while (*pos == ' ' || *pos == '\t') | 
|  | 547 | pos++; | 
|  | 548 | if (os_strncmp(pos, "[2]", 3) == 0) { | 
|  | 549 | user->phase2 = 1; | 
|  | 550 | } | 
|  | 551 |  | 
|  | 552 | done: | 
|  | 553 | if (tail == NULL) { | 
| Dmitry Shmidt | 216983b | 2015-02-06 10:50:36 -0800 | [diff] [blame] | 554 | tail = new_user = user; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 555 | } else { | 
|  | 556 | tail->next = user; | 
|  | 557 | tail = user; | 
|  | 558 | } | 
|  | 559 | continue; | 
|  | 560 |  | 
|  | 561 | failed: | 
| Dmitry Shmidt | 818ea48 | 2014-03-10 13:15:21 -0700 | [diff] [blame] | 562 | if (user) | 
|  | 563 | hostapd_config_free_eap_user(user); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 564 | ret = -1; | 
|  | 565 | break; | 
|  | 566 | } | 
|  | 567 |  | 
|  | 568 | fclose(f); | 
|  | 569 |  | 
| Dmitry Shmidt | 216983b | 2015-02-06 10:50:36 -0800 | [diff] [blame] | 570 | if (ret == 0) { | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 571 | hostapd_config_free_eap_users(conf->eap_user); | 
| Dmitry Shmidt | 216983b | 2015-02-06 10:50:36 -0800 | [diff] [blame] | 572 | conf->eap_user = new_user; | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 573 | } else { | 
|  | 574 | hostapd_config_free_eap_users(new_user); | 
| Dmitry Shmidt | 216983b | 2015-02-06 10:50:36 -0800 | [diff] [blame] | 575 | } | 
|  | 576 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 577 | return ret; | 
|  | 578 | } | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 579 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 580 | #endif /* EAP_SERVER */ | 
|  | 581 |  | 
|  | 582 |  | 
|  | 583 | #ifndef CONFIG_NO_RADIUS | 
|  | 584 | static int | 
|  | 585 | hostapd_config_read_radius_addr(struct hostapd_radius_server **server, | 
|  | 586 | int *num_server, const char *val, int def_port, | 
|  | 587 | struct hostapd_radius_server **curr_serv) | 
|  | 588 | { | 
|  | 589 | struct hostapd_radius_server *nserv; | 
|  | 590 | int ret; | 
|  | 591 | static int server_index = 1; | 
|  | 592 |  | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 593 | nserv = os_realloc_array(*server, *num_server + 1, sizeof(*nserv)); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 594 | if (nserv == NULL) | 
|  | 595 | return -1; | 
|  | 596 |  | 
|  | 597 | *server = nserv; | 
|  | 598 | nserv = &nserv[*num_server]; | 
|  | 599 | (*num_server)++; | 
|  | 600 | (*curr_serv) = nserv; | 
|  | 601 |  | 
|  | 602 | os_memset(nserv, 0, sizeof(*nserv)); | 
|  | 603 | nserv->port = def_port; | 
|  | 604 | ret = hostapd_parse_ip_addr(val, &nserv->addr); | 
|  | 605 | nserv->index = server_index++; | 
|  | 606 |  | 
|  | 607 | return ret; | 
|  | 608 | } | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 609 |  | 
|  | 610 |  | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 611 |  | 
| Dmitry Shmidt | 7f2c753 | 2016-08-15 09:48:12 -0700 | [diff] [blame] | 612 | static int hostapd_parse_das_client(struct hostapd_bss_config *bss, char *val) | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 613 | { | 
|  | 614 | char *secret; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 615 |  | 
|  | 616 | secret = os_strchr(val, ' '); | 
|  | 617 | if (secret == NULL) | 
|  | 618 | return -1; | 
|  | 619 |  | 
| Dmitry Shmidt | 7f2c753 | 2016-08-15 09:48:12 -0700 | [diff] [blame] | 620 | *secret++ = '\0'; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 621 |  | 
|  | 622 | if (hostapd_parse_ip_addr(val, &bss->radius_das_client_addr)) | 
|  | 623 | return -1; | 
|  | 624 |  | 
|  | 625 | os_free(bss->radius_das_shared_secret); | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 626 | bss->radius_das_shared_secret = (u8 *) os_strdup(secret); | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 627 | if (bss->radius_das_shared_secret == NULL) | 
|  | 628 | return -1; | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 629 | bss->radius_das_shared_secret_len = os_strlen(secret); | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 630 |  | 
|  | 631 | return 0; | 
|  | 632 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 633 | #endif /* CONFIG_NO_RADIUS */ | 
|  | 634 |  | 
|  | 635 |  | 
|  | 636 | static int hostapd_config_parse_key_mgmt(int line, const char *value) | 
|  | 637 | { | 
|  | 638 | int val = 0, last; | 
|  | 639 | char *start, *end, *buf; | 
|  | 640 |  | 
|  | 641 | buf = os_strdup(value); | 
|  | 642 | if (buf == NULL) | 
|  | 643 | return -1; | 
|  | 644 | start = buf; | 
|  | 645 |  | 
|  | 646 | while (*start != '\0') { | 
|  | 647 | while (*start == ' ' || *start == '\t') | 
|  | 648 | start++; | 
|  | 649 | if (*start == '\0') | 
|  | 650 | break; | 
|  | 651 | end = start; | 
|  | 652 | while (*end != ' ' && *end != '\t' && *end != '\0') | 
|  | 653 | end++; | 
|  | 654 | last = *end == '\0'; | 
|  | 655 | *end = '\0'; | 
|  | 656 | if (os_strcmp(start, "WPA-PSK") == 0) | 
|  | 657 | val |= WPA_KEY_MGMT_PSK; | 
|  | 658 | else if (os_strcmp(start, "WPA-EAP") == 0) | 
|  | 659 | val |= WPA_KEY_MGMT_IEEE8021X; | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 660 | #ifdef CONFIG_IEEE80211R_AP | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 661 | else if (os_strcmp(start, "FT-PSK") == 0) | 
|  | 662 | val |= WPA_KEY_MGMT_FT_PSK; | 
|  | 663 | else if (os_strcmp(start, "FT-EAP") == 0) | 
|  | 664 | val |= WPA_KEY_MGMT_FT_IEEE8021X; | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 665 | #ifdef CONFIG_SHA384 | 
|  | 666 | else if (os_strcmp(start, "FT-EAP-SHA384") == 0) | 
|  | 667 | val |= WPA_KEY_MGMT_FT_IEEE8021X_SHA384; | 
|  | 668 | #endif /* CONFIG_SHA384 */ | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 669 | #endif /* CONFIG_IEEE80211R_AP */ | 
| Sunil Ravi | 2a14cf1 | 2023-11-21 00:54:38 +0000 | [diff] [blame] | 670 | #ifdef CONFIG_SHA384 | 
|  | 671 | else if (os_strcmp(start, "WPA-EAP-SHA384") == 0) | 
|  | 672 | val |= WPA_KEY_MGMT_IEEE8021X_SHA384; | 
|  | 673 | #endif /* CONFIG_SHA384 */ | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 674 | else if (os_strcmp(start, "WPA-PSK-SHA256") == 0) | 
|  | 675 | val |= WPA_KEY_MGMT_PSK_SHA256; | 
|  | 676 | else if (os_strcmp(start, "WPA-EAP-SHA256") == 0) | 
|  | 677 | val |= WPA_KEY_MGMT_IEEE8021X_SHA256; | 
| Dmitry Shmidt | d5e4923 | 2012-12-03 15:08:10 -0800 | [diff] [blame] | 678 | #ifdef CONFIG_SAE | 
|  | 679 | else if (os_strcmp(start, "SAE") == 0) | 
|  | 680 | val |= WPA_KEY_MGMT_SAE; | 
| Sunil Ravi | 89eba10 | 2022-09-13 21:04:37 -0700 | [diff] [blame] | 681 | else if (os_strcmp(start, "SAE-EXT-KEY") == 0) | 
|  | 682 | val |= WPA_KEY_MGMT_SAE_EXT_KEY; | 
| Dmitry Shmidt | d5e4923 | 2012-12-03 15:08:10 -0800 | [diff] [blame] | 683 | else if (os_strcmp(start, "FT-SAE") == 0) | 
|  | 684 | val |= WPA_KEY_MGMT_FT_SAE; | 
| Sunil Ravi | 89eba10 | 2022-09-13 21:04:37 -0700 | [diff] [blame] | 685 | else if (os_strcmp(start, "FT-SAE-EXT-KEY") == 0) | 
|  | 686 | val |= WPA_KEY_MGMT_FT_SAE_EXT_KEY; | 
| Dmitry Shmidt | d5e4923 | 2012-12-03 15:08:10 -0800 | [diff] [blame] | 687 | #endif /* CONFIG_SAE */ | 
| Dmitry Shmidt | 807291d | 2015-01-27 13:40:23 -0800 | [diff] [blame] | 688 | #ifdef CONFIG_SUITEB | 
| Dmitry Shmidt | 6c0da2b | 2015-01-05 13:08:17 -0800 | [diff] [blame] | 689 | else if (os_strcmp(start, "WPA-EAP-SUITE-B") == 0) | 
|  | 690 | val |= WPA_KEY_MGMT_IEEE8021X_SUITE_B; | 
| Dmitry Shmidt | 807291d | 2015-01-27 13:40:23 -0800 | [diff] [blame] | 691 | #endif /* CONFIG_SUITEB */ | 
|  | 692 | #ifdef CONFIG_SUITEB192 | 
|  | 693 | else if (os_strcmp(start, "WPA-EAP-SUITE-B-192") == 0) | 
|  | 694 | val |= WPA_KEY_MGMT_IEEE8021X_SUITE_B_192; | 
|  | 695 | #endif /* CONFIG_SUITEB192 */ | 
| Dmitry Shmidt | 9839ecd | 2016-11-07 11:05:47 -0800 | [diff] [blame] | 696 | #ifdef CONFIG_FILS | 
|  | 697 | else if (os_strcmp(start, "FILS-SHA256") == 0) | 
|  | 698 | val |= WPA_KEY_MGMT_FILS_SHA256; | 
|  | 699 | else if (os_strcmp(start, "FILS-SHA384") == 0) | 
|  | 700 | val |= WPA_KEY_MGMT_FILS_SHA384; | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 701 | #ifdef CONFIG_IEEE80211R_AP | 
| Dmitry Shmidt | 9839ecd | 2016-11-07 11:05:47 -0800 | [diff] [blame] | 702 | else if (os_strcmp(start, "FT-FILS-SHA256") == 0) | 
|  | 703 | val |= WPA_KEY_MGMT_FT_FILS_SHA256; | 
|  | 704 | else if (os_strcmp(start, "FT-FILS-SHA384") == 0) | 
|  | 705 | val |= WPA_KEY_MGMT_FT_FILS_SHA384; | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 706 | #endif /* CONFIG_IEEE80211R_AP */ | 
| Dmitry Shmidt | 9839ecd | 2016-11-07 11:05:47 -0800 | [diff] [blame] | 707 | #endif /* CONFIG_FILS */ | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 708 | #ifdef CONFIG_OWE | 
|  | 709 | else if (os_strcmp(start, "OWE") == 0) | 
|  | 710 | val |= WPA_KEY_MGMT_OWE; | 
|  | 711 | #endif /* CONFIG_OWE */ | 
|  | 712 | #ifdef CONFIG_DPP | 
|  | 713 | else if (os_strcmp(start, "DPP") == 0) | 
|  | 714 | val |= WPA_KEY_MGMT_DPP; | 
|  | 715 | #endif /* CONFIG_DPP */ | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 716 | #ifdef CONFIG_HS20 | 
|  | 717 | else if (os_strcmp(start, "OSEN") == 0) | 
|  | 718 | val |= WPA_KEY_MGMT_OSEN; | 
|  | 719 | #endif /* CONFIG_HS20 */ | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 720 | #ifdef CONFIG_PASN | 
|  | 721 | else if (os_strcmp(start, "PASN") == 0) | 
|  | 722 | val |= WPA_KEY_MGMT_PASN; | 
|  | 723 | #endif /* CONFIG_PASN */ | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 724 | else { | 
|  | 725 | wpa_printf(MSG_ERROR, "Line %d: invalid key_mgmt '%s'", | 
|  | 726 | line, start); | 
|  | 727 | os_free(buf); | 
|  | 728 | return -1; | 
|  | 729 | } | 
|  | 730 |  | 
|  | 731 | if (last) | 
|  | 732 | break; | 
|  | 733 | start = end + 1; | 
|  | 734 | } | 
|  | 735 |  | 
|  | 736 | os_free(buf); | 
|  | 737 | if (val == 0) { | 
|  | 738 | wpa_printf(MSG_ERROR, "Line %d: no key_mgmt values " | 
|  | 739 | "configured.", line); | 
|  | 740 | return -1; | 
|  | 741 | } | 
|  | 742 |  | 
|  | 743 | return val; | 
|  | 744 | } | 
|  | 745 |  | 
|  | 746 |  | 
|  | 747 | static int hostapd_config_parse_cipher(int line, const char *value) | 
|  | 748 | { | 
| Dmitry Shmidt | a54fa5f | 2013-01-15 13:53:35 -0800 | [diff] [blame] | 749 | int val = wpa_parse_cipher(value); | 
|  | 750 | if (val < 0) { | 
|  | 751 | wpa_printf(MSG_ERROR, "Line %d: invalid cipher '%s'.", | 
|  | 752 | line, value); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 753 | return -1; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 754 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 755 | if (val == 0) { | 
|  | 756 | wpa_printf(MSG_ERROR, "Line %d: no cipher values configured.", | 
|  | 757 | line); | 
|  | 758 | return -1; | 
|  | 759 | } | 
|  | 760 | return val; | 
|  | 761 | } | 
|  | 762 |  | 
|  | 763 |  | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 764 | #ifdef CONFIG_WEP | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 765 | static int hostapd_config_read_wep(struct hostapd_wep_keys *wep, int keyidx, | 
|  | 766 | char *val) | 
|  | 767 | { | 
|  | 768 | size_t len = os_strlen(val); | 
|  | 769 |  | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 770 | if (keyidx < 0 || keyidx > 3) | 
|  | 771 | return -1; | 
|  | 772 |  | 
|  | 773 | if (len == 0) { | 
|  | 774 | int i, set = 0; | 
|  | 775 |  | 
|  | 776 | bin_clear_free(wep->key[keyidx], wep->len[keyidx]); | 
|  | 777 | wep->key[keyidx] = NULL; | 
|  | 778 | wep->len[keyidx] = 0; | 
|  | 779 | for (i = 0; i < NUM_WEP_KEYS; i++) { | 
|  | 780 | if (wep->key[i]) | 
|  | 781 | set++; | 
|  | 782 | } | 
|  | 783 | if (!set) | 
|  | 784 | wep->keys_set = 0; | 
|  | 785 | return 0; | 
|  | 786 | } | 
|  | 787 |  | 
|  | 788 | if (wep->key[keyidx] != NULL) | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 789 | return -1; | 
|  | 790 |  | 
|  | 791 | if (val[0] == '"') { | 
|  | 792 | if (len < 2 || val[len - 1] != '"') | 
|  | 793 | return -1; | 
|  | 794 | len -= 2; | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 795 | wep->key[keyidx] = os_memdup(val + 1, len); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 796 | if (wep->key[keyidx] == NULL) | 
|  | 797 | return -1; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 798 | wep->len[keyidx] = len; | 
|  | 799 | } else { | 
|  | 800 | if (len & 1) | 
|  | 801 | return -1; | 
|  | 802 | len /= 2; | 
|  | 803 | wep->key[keyidx] = os_malloc(len); | 
|  | 804 | if (wep->key[keyidx] == NULL) | 
|  | 805 | return -1; | 
|  | 806 | wep->len[keyidx] = len; | 
|  | 807 | if (hexstr2bin(val, wep->key[keyidx], len) < 0) | 
|  | 808 | return -1; | 
|  | 809 | } | 
|  | 810 |  | 
|  | 811 | wep->keys_set++; | 
|  | 812 |  | 
|  | 813 | return 0; | 
|  | 814 | } | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 815 | #endif /* CONFIG_WEP */ | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 816 |  | 
|  | 817 |  | 
| Dmitry Shmidt | dda10c2 | 2015-03-24 16:05:01 -0700 | [diff] [blame] | 818 | static int hostapd_parse_chanlist(struct hostapd_config *conf, char *val) | 
|  | 819 | { | 
|  | 820 | char *pos; | 
|  | 821 |  | 
|  | 822 | /* for backwards compatibility, translate ' ' in conf str to ',' */ | 
|  | 823 | pos = val; | 
|  | 824 | while (pos) { | 
|  | 825 | pos = os_strchr(pos, ' '); | 
|  | 826 | if (pos) | 
|  | 827 | *pos++ = ','; | 
|  | 828 | } | 
|  | 829 | if (freq_range_list_parse(&conf->acs_ch_list, val)) | 
|  | 830 | return -1; | 
|  | 831 |  | 
|  | 832 | return 0; | 
|  | 833 | } | 
|  | 834 |  | 
|  | 835 |  | 
| Dmitry Shmidt | ea69e84 | 2013-05-13 14:52:28 -0700 | [diff] [blame] | 836 | static int hostapd_parse_intlist(int **int_list, char *val) | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 837 | { | 
|  | 838 | int *list; | 
|  | 839 | int count; | 
|  | 840 | char *pos, *end; | 
|  | 841 |  | 
| Dmitry Shmidt | ea69e84 | 2013-05-13 14:52:28 -0700 | [diff] [blame] | 842 | os_free(*int_list); | 
|  | 843 | *int_list = NULL; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 844 |  | 
|  | 845 | pos = val; | 
|  | 846 | count = 0; | 
|  | 847 | while (*pos != '\0') { | 
|  | 848 | if (*pos == ' ') | 
|  | 849 | count++; | 
|  | 850 | pos++; | 
|  | 851 | } | 
|  | 852 |  | 
|  | 853 | list = os_malloc(sizeof(int) * (count + 2)); | 
|  | 854 | if (list == NULL) | 
|  | 855 | return -1; | 
|  | 856 | pos = val; | 
|  | 857 | count = 0; | 
|  | 858 | while (*pos != '\0') { | 
|  | 859 | end = os_strchr(pos, ' '); | 
|  | 860 | if (end) | 
|  | 861 | *end = '\0'; | 
|  | 862 |  | 
|  | 863 | list[count++] = atoi(pos); | 
|  | 864 | if (!end) | 
|  | 865 | break; | 
|  | 866 | pos = end + 1; | 
|  | 867 | } | 
|  | 868 | list[count] = -1; | 
|  | 869 |  | 
| Dmitry Shmidt | ea69e84 | 2013-05-13 14:52:28 -0700 | [diff] [blame] | 870 | *int_list = list; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 871 | return 0; | 
|  | 872 | } | 
|  | 873 |  | 
|  | 874 |  | 
|  | 875 | static int hostapd_config_bss(struct hostapd_config *conf, const char *ifname) | 
|  | 876 | { | 
| Dmitry Shmidt | cce0666 | 2013-11-04 18:44:24 -0800 | [diff] [blame] | 877 | struct hostapd_bss_config **all, *bss; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 878 |  | 
|  | 879 | if (*ifname == '\0') | 
|  | 880 | return -1; | 
|  | 881 |  | 
| Dmitry Shmidt | cce0666 | 2013-11-04 18:44:24 -0800 | [diff] [blame] | 882 | all = os_realloc_array(conf->bss, conf->num_bss + 1, | 
|  | 883 | sizeof(struct hostapd_bss_config *)); | 
|  | 884 | if (all == NULL) { | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 885 | wpa_printf(MSG_ERROR, "Failed to allocate memory for " | 
|  | 886 | "multi-BSS entry"); | 
|  | 887 | return -1; | 
|  | 888 | } | 
| Dmitry Shmidt | cce0666 | 2013-11-04 18:44:24 -0800 | [diff] [blame] | 889 | conf->bss = all; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 890 |  | 
| Dmitry Shmidt | cce0666 | 2013-11-04 18:44:24 -0800 | [diff] [blame] | 891 | bss = os_zalloc(sizeof(*bss)); | 
|  | 892 | if (bss == NULL) | 
|  | 893 | return -1; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 894 | bss->radius = os_zalloc(sizeof(*bss->radius)); | 
|  | 895 | if (bss->radius == NULL) { | 
|  | 896 | wpa_printf(MSG_ERROR, "Failed to allocate memory for " | 
|  | 897 | "multi-BSS RADIUS data"); | 
| Dmitry Shmidt | cce0666 | 2013-11-04 18:44:24 -0800 | [diff] [blame] | 898 | os_free(bss); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 899 | return -1; | 
|  | 900 | } | 
|  | 901 |  | 
| Dmitry Shmidt | cce0666 | 2013-11-04 18:44:24 -0800 | [diff] [blame] | 902 | conf->bss[conf->num_bss++] = bss; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 903 | conf->last_bss = bss; | 
|  | 904 |  | 
|  | 905 | hostapd_config_defaults_bss(bss); | 
|  | 906 | os_strlcpy(bss->iface, ifname, sizeof(bss->iface)); | 
|  | 907 | os_memcpy(bss->ssid.vlan, bss->iface, IFNAMSIZ + 1); | 
|  | 908 |  | 
|  | 909 | return 0; | 
|  | 910 | } | 
|  | 911 |  | 
|  | 912 |  | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 913 | #ifdef CONFIG_IEEE80211R_AP | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 914 |  | 
|  | 915 | static int rkh_derive_key(const char *pos, u8 *key, size_t key_len) | 
|  | 916 | { | 
|  | 917 | u8 oldkey[16]; | 
|  | 918 | int ret; | 
|  | 919 |  | 
|  | 920 | if (!hexstr2bin(pos, key, key_len)) | 
|  | 921 | return 0; | 
|  | 922 |  | 
|  | 923 | /* Try to use old short key for backwards compatibility */ | 
|  | 924 | if (hexstr2bin(pos, oldkey, sizeof(oldkey))) | 
|  | 925 | return -1; | 
|  | 926 |  | 
|  | 927 | ret = hmac_sha256_kdf(oldkey, sizeof(oldkey), "FT OLDKEY", NULL, 0, | 
|  | 928 | key, key_len); | 
|  | 929 | os_memset(oldkey, 0, sizeof(oldkey)); | 
|  | 930 | return ret; | 
|  | 931 | } | 
|  | 932 |  | 
|  | 933 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 934 | static int add_r0kh(struct hostapd_bss_config *bss, char *value) | 
|  | 935 | { | 
|  | 936 | struct ft_remote_r0kh *r0kh; | 
|  | 937 | char *pos, *next; | 
|  | 938 |  | 
|  | 939 | r0kh = os_zalloc(sizeof(*r0kh)); | 
|  | 940 | if (r0kh == NULL) | 
|  | 941 | return -1; | 
|  | 942 |  | 
|  | 943 | /* 02:01:02:03:04:05 a.example.com 000102030405060708090a0b0c0d0e0f */ | 
|  | 944 | pos = value; | 
|  | 945 | next = os_strchr(pos, ' '); | 
|  | 946 | if (next) | 
|  | 947 | *next++ = '\0'; | 
|  | 948 | if (next == NULL || hwaddr_aton(pos, r0kh->addr)) { | 
|  | 949 | wpa_printf(MSG_ERROR, "Invalid R0KH MAC address: '%s'", pos); | 
|  | 950 | os_free(r0kh); | 
|  | 951 | return -1; | 
|  | 952 | } | 
|  | 953 |  | 
|  | 954 | pos = next; | 
|  | 955 | next = os_strchr(pos, ' '); | 
|  | 956 | if (next) | 
|  | 957 | *next++ = '\0'; | 
|  | 958 | if (next == NULL || next - pos > FT_R0KH_ID_MAX_LEN) { | 
|  | 959 | wpa_printf(MSG_ERROR, "Invalid R0KH-ID: '%s'", pos); | 
|  | 960 | os_free(r0kh); | 
|  | 961 | return -1; | 
|  | 962 | } | 
|  | 963 | r0kh->id_len = next - pos - 1; | 
|  | 964 | os_memcpy(r0kh->id, pos, r0kh->id_len); | 
|  | 965 |  | 
|  | 966 | pos = next; | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 967 | if (rkh_derive_key(pos, r0kh->key, sizeof(r0kh->key)) < 0) { | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 968 | wpa_printf(MSG_ERROR, "Invalid R0KH key: '%s'", pos); | 
|  | 969 | os_free(r0kh); | 
|  | 970 | return -1; | 
|  | 971 | } | 
|  | 972 |  | 
|  | 973 | r0kh->next = bss->r0kh_list; | 
|  | 974 | bss->r0kh_list = r0kh; | 
|  | 975 |  | 
|  | 976 | return 0; | 
|  | 977 | } | 
|  | 978 |  | 
|  | 979 |  | 
|  | 980 | static int add_r1kh(struct hostapd_bss_config *bss, char *value) | 
|  | 981 | { | 
|  | 982 | struct ft_remote_r1kh *r1kh; | 
|  | 983 | char *pos, *next; | 
|  | 984 |  | 
|  | 985 | r1kh = os_zalloc(sizeof(*r1kh)); | 
|  | 986 | if (r1kh == NULL) | 
|  | 987 | return -1; | 
|  | 988 |  | 
|  | 989 | /* 02:01:02:03:04:05 02:01:02:03:04:05 | 
|  | 990 | * 000102030405060708090a0b0c0d0e0f */ | 
|  | 991 | pos = value; | 
|  | 992 | next = os_strchr(pos, ' '); | 
|  | 993 | if (next) | 
|  | 994 | *next++ = '\0'; | 
|  | 995 | if (next == NULL || hwaddr_aton(pos, r1kh->addr)) { | 
|  | 996 | wpa_printf(MSG_ERROR, "Invalid R1KH MAC address: '%s'", pos); | 
|  | 997 | os_free(r1kh); | 
|  | 998 | return -1; | 
|  | 999 | } | 
|  | 1000 |  | 
|  | 1001 | pos = next; | 
|  | 1002 | next = os_strchr(pos, ' '); | 
|  | 1003 | if (next) | 
|  | 1004 | *next++ = '\0'; | 
|  | 1005 | if (next == NULL || hwaddr_aton(pos, r1kh->id)) { | 
|  | 1006 | wpa_printf(MSG_ERROR, "Invalid R1KH-ID: '%s'", pos); | 
|  | 1007 | os_free(r1kh); | 
|  | 1008 | return -1; | 
|  | 1009 | } | 
|  | 1010 |  | 
|  | 1011 | pos = next; | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 1012 | if (rkh_derive_key(pos, r1kh->key, sizeof(r1kh->key)) < 0) { | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 1013 | wpa_printf(MSG_ERROR, "Invalid R1KH key: '%s'", pos); | 
|  | 1014 | os_free(r1kh); | 
|  | 1015 | return -1; | 
|  | 1016 | } | 
|  | 1017 |  | 
|  | 1018 | r1kh->next = bss->r1kh_list; | 
|  | 1019 | bss->r1kh_list = r1kh; | 
|  | 1020 |  | 
|  | 1021 | return 0; | 
|  | 1022 | } | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 1023 | #endif /* CONFIG_IEEE80211R_AP */ | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 1024 |  | 
|  | 1025 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 1026 | static int hostapd_config_ht_capab(struct hostapd_config *conf, | 
|  | 1027 | const char *capab) | 
|  | 1028 | { | 
|  | 1029 | if (os_strstr(capab, "[LDPC]")) | 
|  | 1030 | conf->ht_capab |= HT_CAP_INFO_LDPC_CODING_CAP; | 
|  | 1031 | if (os_strstr(capab, "[HT40-]")) { | 
|  | 1032 | conf->ht_capab |= HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET; | 
|  | 1033 | conf->secondary_channel = -1; | 
|  | 1034 | } | 
|  | 1035 | if (os_strstr(capab, "[HT40+]")) { | 
|  | 1036 | conf->ht_capab |= HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET; | 
|  | 1037 | conf->secondary_channel = 1; | 
|  | 1038 | } | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 1039 | if (os_strstr(capab, "[HT40+]") && os_strstr(capab, "[HT40-]")) { | 
|  | 1040 | conf->ht_capab |= HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET; | 
|  | 1041 | conf->ht40_plus_minus_allowed = 1; | 
|  | 1042 | } | 
| Hai Shalom | ce48b4a | 2018-09-05 11:41:35 -0700 | [diff] [blame] | 1043 | if (!os_strstr(capab, "[HT40+]") && !os_strstr(capab, "[HT40-]")) | 
|  | 1044 | conf->secondary_channel = 0; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 1045 | if (os_strstr(capab, "[GF]")) | 
|  | 1046 | conf->ht_capab |= HT_CAP_INFO_GREEN_FIELD; | 
|  | 1047 | if (os_strstr(capab, "[SHORT-GI-20]")) | 
|  | 1048 | conf->ht_capab |= HT_CAP_INFO_SHORT_GI20MHZ; | 
|  | 1049 | if (os_strstr(capab, "[SHORT-GI-40]")) | 
|  | 1050 | conf->ht_capab |= HT_CAP_INFO_SHORT_GI40MHZ; | 
|  | 1051 | if (os_strstr(capab, "[TX-STBC]")) | 
|  | 1052 | conf->ht_capab |= HT_CAP_INFO_TX_STBC; | 
|  | 1053 | if (os_strstr(capab, "[RX-STBC1]")) { | 
|  | 1054 | conf->ht_capab &= ~HT_CAP_INFO_RX_STBC_MASK; | 
|  | 1055 | conf->ht_capab |= HT_CAP_INFO_RX_STBC_1; | 
|  | 1056 | } | 
|  | 1057 | if (os_strstr(capab, "[RX-STBC12]")) { | 
|  | 1058 | conf->ht_capab &= ~HT_CAP_INFO_RX_STBC_MASK; | 
|  | 1059 | conf->ht_capab |= HT_CAP_INFO_RX_STBC_12; | 
|  | 1060 | } | 
|  | 1061 | if (os_strstr(capab, "[RX-STBC123]")) { | 
|  | 1062 | conf->ht_capab &= ~HT_CAP_INFO_RX_STBC_MASK; | 
|  | 1063 | conf->ht_capab |= HT_CAP_INFO_RX_STBC_123; | 
|  | 1064 | } | 
|  | 1065 | if (os_strstr(capab, "[DELAYED-BA]")) | 
|  | 1066 | conf->ht_capab |= HT_CAP_INFO_DELAYED_BA; | 
|  | 1067 | if (os_strstr(capab, "[MAX-AMSDU-7935]")) | 
|  | 1068 | conf->ht_capab |= HT_CAP_INFO_MAX_AMSDU_SIZE; | 
|  | 1069 | if (os_strstr(capab, "[DSSS_CCK-40]")) | 
|  | 1070 | conf->ht_capab |= HT_CAP_INFO_DSSS_CCK40MHZ; | 
| Dmitry Shmidt | d11f019 | 2014-03-24 12:09:47 -0700 | [diff] [blame] | 1071 | if (os_strstr(capab, "[40-INTOLERANT]")) | 
|  | 1072 | conf->ht_capab |= HT_CAP_INFO_40MHZ_INTOLERANT; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 1073 | if (os_strstr(capab, "[LSIG-TXOP-PROT]")) | 
|  | 1074 | conf->ht_capab |= HT_CAP_INFO_LSIG_TXOP_PROTECT_SUPPORT; | 
|  | 1075 |  | 
|  | 1076 | return 0; | 
|  | 1077 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 1078 |  | 
|  | 1079 |  | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1080 | #ifdef CONFIG_IEEE80211AC | 
|  | 1081 | static int hostapd_config_vht_capab(struct hostapd_config *conf, | 
|  | 1082 | const char *capab) | 
|  | 1083 | { | 
|  | 1084 | if (os_strstr(capab, "[MAX-MPDU-7991]")) | 
|  | 1085 | conf->vht_capab |= VHT_CAP_MAX_MPDU_LENGTH_7991; | 
|  | 1086 | if (os_strstr(capab, "[MAX-MPDU-11454]")) | 
|  | 1087 | conf->vht_capab |= VHT_CAP_MAX_MPDU_LENGTH_11454; | 
|  | 1088 | if (os_strstr(capab, "[VHT160]")) | 
|  | 1089 | conf->vht_capab |= VHT_CAP_SUPP_CHAN_WIDTH_160MHZ; | 
|  | 1090 | if (os_strstr(capab, "[VHT160-80PLUS80]")) | 
|  | 1091 | conf->vht_capab |= VHT_CAP_SUPP_CHAN_WIDTH_160_80PLUS80MHZ; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1092 | if (os_strstr(capab, "[RXLDPC]")) | 
|  | 1093 | conf->vht_capab |= VHT_CAP_RXLDPC; | 
|  | 1094 | if (os_strstr(capab, "[SHORT-GI-80]")) | 
|  | 1095 | conf->vht_capab |= VHT_CAP_SHORT_GI_80; | 
|  | 1096 | if (os_strstr(capab, "[SHORT-GI-160]")) | 
|  | 1097 | conf->vht_capab |= VHT_CAP_SHORT_GI_160; | 
|  | 1098 | if (os_strstr(capab, "[TX-STBC-2BY1]")) | 
|  | 1099 | conf->vht_capab |= VHT_CAP_TXSTBC; | 
|  | 1100 | if (os_strstr(capab, "[RX-STBC-1]")) | 
|  | 1101 | conf->vht_capab |= VHT_CAP_RXSTBC_1; | 
|  | 1102 | if (os_strstr(capab, "[RX-STBC-12]")) | 
|  | 1103 | conf->vht_capab |= VHT_CAP_RXSTBC_2; | 
|  | 1104 | if (os_strstr(capab, "[RX-STBC-123]")) | 
|  | 1105 | conf->vht_capab |= VHT_CAP_RXSTBC_3; | 
|  | 1106 | if (os_strstr(capab, "[RX-STBC-1234]")) | 
|  | 1107 | conf->vht_capab |= VHT_CAP_RXSTBC_4; | 
|  | 1108 | if (os_strstr(capab, "[SU-BEAMFORMER]")) | 
| Dmitry Shmidt | 68d0e3e | 2013-10-28 17:59:21 -0700 | [diff] [blame] | 1109 | conf->vht_capab |= VHT_CAP_SU_BEAMFORMER_CAPABLE; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1110 | if (os_strstr(capab, "[SU-BEAMFORMEE]")) | 
| Dmitry Shmidt | 68d0e3e | 2013-10-28 17:59:21 -0700 | [diff] [blame] | 1111 | conf->vht_capab |= VHT_CAP_SU_BEAMFORMEE_CAPABLE; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1112 | if (os_strstr(capab, "[BF-ANTENNA-2]") && | 
| Dmitry Shmidt | 68d0e3e | 2013-10-28 17:59:21 -0700 | [diff] [blame] | 1113 | (conf->vht_capab & VHT_CAP_SU_BEAMFORMEE_CAPABLE)) | 
|  | 1114 | conf->vht_capab |= (1 << VHT_CAP_BEAMFORMEE_STS_OFFSET); | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 1115 | if (os_strstr(capab, "[BF-ANTENNA-3]") && | 
|  | 1116 | (conf->vht_capab & VHT_CAP_SU_BEAMFORMEE_CAPABLE)) | 
|  | 1117 | conf->vht_capab |= (2 << VHT_CAP_BEAMFORMEE_STS_OFFSET); | 
|  | 1118 | if (os_strstr(capab, "[BF-ANTENNA-4]") && | 
|  | 1119 | (conf->vht_capab & VHT_CAP_SU_BEAMFORMEE_CAPABLE)) | 
|  | 1120 | conf->vht_capab |= (3 << VHT_CAP_BEAMFORMEE_STS_OFFSET); | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1121 | if (os_strstr(capab, "[SOUNDING-DIMENSION-2]") && | 
| Dmitry Shmidt | 68d0e3e | 2013-10-28 17:59:21 -0700 | [diff] [blame] | 1122 | (conf->vht_capab & VHT_CAP_SU_BEAMFORMER_CAPABLE)) | 
|  | 1123 | conf->vht_capab |= (1 << VHT_CAP_SOUNDING_DIMENSION_OFFSET); | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 1124 | if (os_strstr(capab, "[SOUNDING-DIMENSION-3]") && | 
|  | 1125 | (conf->vht_capab & VHT_CAP_SU_BEAMFORMER_CAPABLE)) | 
|  | 1126 | conf->vht_capab |= (2 << VHT_CAP_SOUNDING_DIMENSION_OFFSET); | 
|  | 1127 | if (os_strstr(capab, "[SOUNDING-DIMENSION-4]") && | 
|  | 1128 | (conf->vht_capab & VHT_CAP_SU_BEAMFORMER_CAPABLE)) | 
|  | 1129 | conf->vht_capab |= (3 << VHT_CAP_SOUNDING_DIMENSION_OFFSET); | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1130 | if (os_strstr(capab, "[MU-BEAMFORMER]")) | 
|  | 1131 | conf->vht_capab |= VHT_CAP_MU_BEAMFORMER_CAPABLE; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1132 | if (os_strstr(capab, "[VHT-TXOP-PS]")) | 
|  | 1133 | conf->vht_capab |= VHT_CAP_VHT_TXOP_PS; | 
|  | 1134 | if (os_strstr(capab, "[HTC-VHT]")) | 
|  | 1135 | conf->vht_capab |= VHT_CAP_HTC_VHT; | 
| Dmitry Shmidt | a38abf9 | 2014-03-06 13:38:44 -0800 | [diff] [blame] | 1136 | if (os_strstr(capab, "[MAX-A-MPDU-LEN-EXP7]")) | 
|  | 1137 | conf->vht_capab |= VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MAX; | 
|  | 1138 | else if (os_strstr(capab, "[MAX-A-MPDU-LEN-EXP6]")) | 
|  | 1139 | conf->vht_capab |= VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_6; | 
|  | 1140 | else if (os_strstr(capab, "[MAX-A-MPDU-LEN-EXP5]")) | 
|  | 1141 | conf->vht_capab |= VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_5; | 
|  | 1142 | else if (os_strstr(capab, "[MAX-A-MPDU-LEN-EXP4]")) | 
|  | 1143 | conf->vht_capab |= VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_4; | 
|  | 1144 | else if (os_strstr(capab, "[MAX-A-MPDU-LEN-EXP3]")) | 
|  | 1145 | conf->vht_capab |= VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_3; | 
|  | 1146 | else if (os_strstr(capab, "[MAX-A-MPDU-LEN-EXP2]")) | 
|  | 1147 | conf->vht_capab |= VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_2; | 
|  | 1148 | else if (os_strstr(capab, "[MAX-A-MPDU-LEN-EXP1]")) | 
|  | 1149 | conf->vht_capab |= VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_1; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1150 | if (os_strstr(capab, "[VHT-LINK-ADAPT2]") && | 
|  | 1151 | (conf->vht_capab & VHT_CAP_HTC_VHT)) | 
|  | 1152 | conf->vht_capab |= VHT_CAP_VHT_LINK_ADAPTATION_VHT_UNSOL_MFB; | 
|  | 1153 | if (os_strstr(capab, "[VHT-LINK-ADAPT3]") && | 
|  | 1154 | (conf->vht_capab & VHT_CAP_HTC_VHT)) | 
|  | 1155 | conf->vht_capab |= VHT_CAP_VHT_LINK_ADAPTATION_VHT_MRQ_MFB; | 
|  | 1156 | if (os_strstr(capab, "[RX-ANTENNA-PATTERN]")) | 
|  | 1157 | conf->vht_capab |= VHT_CAP_RX_ANTENNA_PATTERN; | 
|  | 1158 | if (os_strstr(capab, "[TX-ANTENNA-PATTERN]")) | 
|  | 1159 | conf->vht_capab |= VHT_CAP_TX_ANTENNA_PATTERN; | 
|  | 1160 | return 0; | 
|  | 1161 | } | 
|  | 1162 | #endif /* CONFIG_IEEE80211AC */ | 
|  | 1163 |  | 
|  | 1164 |  | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 1165 | #ifdef CONFIG_IEEE80211AX | 
|  | 1166 |  | 
|  | 1167 | static u8 find_bit_offset(u8 val) | 
|  | 1168 | { | 
|  | 1169 | u8 res = 0; | 
|  | 1170 |  | 
|  | 1171 | for (; val; val >>= 1) { | 
|  | 1172 | if (val & 1) | 
|  | 1173 | break; | 
|  | 1174 | res++; | 
|  | 1175 | } | 
|  | 1176 |  | 
|  | 1177 | return res; | 
|  | 1178 | } | 
|  | 1179 |  | 
|  | 1180 |  | 
|  | 1181 | static u8 set_he_cap(int val, u8 mask) | 
|  | 1182 | { | 
|  | 1183 | return (u8) (mask & (val << find_bit_offset(mask))); | 
|  | 1184 | } | 
|  | 1185 |  | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 1186 |  | 
|  | 1187 | static int hostapd_parse_he_srg_bitmap(u8 *bitmap, char *val) | 
|  | 1188 | { | 
|  | 1189 | int bitpos; | 
|  | 1190 | char *pos, *end; | 
|  | 1191 |  | 
|  | 1192 | os_memset(bitmap, 0, 8); | 
|  | 1193 | pos = val; | 
|  | 1194 | while (*pos != '\0') { | 
|  | 1195 | end = os_strchr(pos, ' '); | 
|  | 1196 | if (end) | 
|  | 1197 | *end = '\0'; | 
|  | 1198 |  | 
|  | 1199 | bitpos = atoi(pos); | 
|  | 1200 | if (bitpos < 0 || bitpos > 64) | 
|  | 1201 | return -1; | 
|  | 1202 |  | 
|  | 1203 | bitmap[bitpos / 8] |= BIT(bitpos % 8); | 
|  | 1204 | if (!end) | 
|  | 1205 | break; | 
|  | 1206 | pos = end + 1; | 
|  | 1207 | } | 
|  | 1208 |  | 
|  | 1209 | return 0; | 
|  | 1210 | } | 
|  | 1211 |  | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 1212 | #endif /* CONFIG_IEEE80211AX */ | 
|  | 1213 |  | 
|  | 1214 |  | 
| Dmitry Shmidt | 1f69aa5 | 2012-01-24 16:10:04 -0800 | [diff] [blame] | 1215 | #ifdef CONFIG_INTERWORKING | 
|  | 1216 | static int parse_roaming_consortium(struct hostapd_bss_config *bss, char *pos, | 
|  | 1217 | int line) | 
|  | 1218 | { | 
|  | 1219 | size_t len = os_strlen(pos); | 
|  | 1220 | u8 oi[MAX_ROAMING_CONSORTIUM_LEN]; | 
|  | 1221 |  | 
|  | 1222 | struct hostapd_roaming_consortium *rc; | 
|  | 1223 |  | 
|  | 1224 | if ((len & 1) || len < 2 * 3 || len / 2 > MAX_ROAMING_CONSORTIUM_LEN || | 
|  | 1225 | hexstr2bin(pos, oi, len / 2)) { | 
|  | 1226 | wpa_printf(MSG_ERROR, "Line %d: invalid roaming_consortium " | 
|  | 1227 | "'%s'", line, pos); | 
|  | 1228 | return -1; | 
|  | 1229 | } | 
|  | 1230 | len /= 2; | 
|  | 1231 |  | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1232 | rc = os_realloc_array(bss->roaming_consortium, | 
|  | 1233 | bss->roaming_consortium_count + 1, | 
|  | 1234 | sizeof(struct hostapd_roaming_consortium)); | 
| Dmitry Shmidt | 1f69aa5 | 2012-01-24 16:10:04 -0800 | [diff] [blame] | 1235 | if (rc == NULL) | 
|  | 1236 | return -1; | 
|  | 1237 |  | 
|  | 1238 | os_memcpy(rc[bss->roaming_consortium_count].oi, oi, len); | 
|  | 1239 | rc[bss->roaming_consortium_count].len = len; | 
|  | 1240 |  | 
|  | 1241 | bss->roaming_consortium = rc; | 
|  | 1242 | bss->roaming_consortium_count++; | 
|  | 1243 |  | 
|  | 1244 | return 0; | 
|  | 1245 | } | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1246 |  | 
|  | 1247 |  | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1248 | static int parse_lang_string(struct hostapd_lang_string **array, | 
|  | 1249 | unsigned int *count, char *pos) | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1250 | { | 
| Dmitry Shmidt | 5605286 | 2013-10-04 10:23:25 -0700 | [diff] [blame] | 1251 | char *sep, *str = NULL; | 
|  | 1252 | size_t clen, nlen, slen; | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1253 | struct hostapd_lang_string *ls; | 
| Dmitry Shmidt | 5605286 | 2013-10-04 10:23:25 -0700 | [diff] [blame] | 1254 | int ret = -1; | 
|  | 1255 |  | 
|  | 1256 | if (*pos == '"' || (*pos == 'P' && pos[1] == '"')) { | 
|  | 1257 | str = wpa_config_parse_string(pos, &slen); | 
|  | 1258 | if (!str) | 
|  | 1259 | return -1; | 
|  | 1260 | pos = str; | 
|  | 1261 | } | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1262 |  | 
|  | 1263 | sep = os_strchr(pos, ':'); | 
|  | 1264 | if (sep == NULL) | 
| Dmitry Shmidt | 5605286 | 2013-10-04 10:23:25 -0700 | [diff] [blame] | 1265 | goto fail; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1266 | *sep++ = '\0'; | 
|  | 1267 |  | 
|  | 1268 | clen = os_strlen(pos); | 
| Dmitry Shmidt | 5605286 | 2013-10-04 10:23:25 -0700 | [diff] [blame] | 1269 | if (clen < 2 || clen > sizeof(ls->lang)) | 
|  | 1270 | goto fail; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1271 | nlen = os_strlen(sep); | 
|  | 1272 | if (nlen > 252) | 
| Dmitry Shmidt | 5605286 | 2013-10-04 10:23:25 -0700 | [diff] [blame] | 1273 | goto fail; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1274 |  | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1275 | ls = os_realloc_array(*array, *count + 1, | 
|  | 1276 | sizeof(struct hostapd_lang_string)); | 
|  | 1277 | if (ls == NULL) | 
| Dmitry Shmidt | 5605286 | 2013-10-04 10:23:25 -0700 | [diff] [blame] | 1278 | goto fail; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1279 |  | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1280 | *array = ls; | 
|  | 1281 | ls = &(*array)[*count]; | 
|  | 1282 | (*count)++; | 
|  | 1283 |  | 
|  | 1284 | os_memset(ls->lang, 0, sizeof(ls->lang)); | 
|  | 1285 | os_memcpy(ls->lang, pos, clen); | 
|  | 1286 | ls->name_len = nlen; | 
|  | 1287 | os_memcpy(ls->name, sep, nlen); | 
|  | 1288 |  | 
| Dmitry Shmidt | 5605286 | 2013-10-04 10:23:25 -0700 | [diff] [blame] | 1289 | ret = 0; | 
|  | 1290 | fail: | 
|  | 1291 | os_free(str); | 
|  | 1292 | return ret; | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1293 | } | 
|  | 1294 |  | 
|  | 1295 |  | 
|  | 1296 | static int parse_venue_name(struct hostapd_bss_config *bss, char *pos, | 
|  | 1297 | int line) | 
|  | 1298 | { | 
|  | 1299 | if (parse_lang_string(&bss->venue_name, &bss->venue_name_count, pos)) { | 
|  | 1300 | wpa_printf(MSG_ERROR, "Line %d: Invalid venue_name '%s'", | 
|  | 1301 | line, pos); | 
|  | 1302 | return -1; | 
|  | 1303 | } | 
|  | 1304 | return 0; | 
|  | 1305 | } | 
|  | 1306 |  | 
|  | 1307 |  | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 1308 | static int parse_venue_url(struct hostapd_bss_config *bss, char *pos, | 
|  | 1309 | int line) | 
|  | 1310 | { | 
|  | 1311 | char *sep; | 
|  | 1312 | size_t nlen; | 
|  | 1313 | struct hostapd_venue_url *url; | 
|  | 1314 | int ret = -1; | 
|  | 1315 |  | 
|  | 1316 | sep = os_strchr(pos, ':'); | 
|  | 1317 | if (!sep) | 
|  | 1318 | goto fail; | 
|  | 1319 | *sep++ = '\0'; | 
|  | 1320 |  | 
|  | 1321 | nlen = os_strlen(sep); | 
|  | 1322 | if (nlen > 254) | 
|  | 1323 | goto fail; | 
|  | 1324 |  | 
|  | 1325 | url = os_realloc_array(bss->venue_url, bss->venue_url_count + 1, | 
|  | 1326 | sizeof(struct hostapd_venue_url)); | 
|  | 1327 | if (!url) | 
|  | 1328 | goto fail; | 
|  | 1329 |  | 
|  | 1330 | bss->venue_url = url; | 
|  | 1331 | url = &bss->venue_url[bss->venue_url_count++]; | 
|  | 1332 |  | 
|  | 1333 | url->venue_number = atoi(pos); | 
|  | 1334 | url->url_len = nlen; | 
|  | 1335 | os_memcpy(url->url, sep, nlen); | 
|  | 1336 |  | 
|  | 1337 | ret = 0; | 
|  | 1338 | fail: | 
|  | 1339 | if (ret) | 
|  | 1340 | wpa_printf(MSG_ERROR, "Line %d: Invalid venue_url '%s'", | 
|  | 1341 | line, pos); | 
|  | 1342 | return ret; | 
|  | 1343 | } | 
|  | 1344 |  | 
|  | 1345 |  | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1346 | static int parse_3gpp_cell_net(struct hostapd_bss_config *bss, char *buf, | 
|  | 1347 | int line) | 
|  | 1348 | { | 
|  | 1349 | size_t count; | 
|  | 1350 | char *pos; | 
|  | 1351 | u8 *info = NULL, *ipos; | 
|  | 1352 |  | 
|  | 1353 | /* format: <MCC1,MNC1>[;<MCC2,MNC2>][;...] */ | 
|  | 1354 |  | 
|  | 1355 | count = 1; | 
|  | 1356 | for (pos = buf; *pos; pos++) { | 
| Dmitry Shmidt | df5a7e4 | 2014-04-02 12:59:59 -0700 | [diff] [blame] | 1357 | if ((*pos < '0' || *pos > '9') && *pos != ';' && *pos != ',') | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1358 | goto fail; | 
|  | 1359 | if (*pos == ';') | 
|  | 1360 | count++; | 
|  | 1361 | } | 
|  | 1362 | if (1 + count * 3 > 0x7f) | 
|  | 1363 | goto fail; | 
|  | 1364 |  | 
|  | 1365 | info = os_zalloc(2 + 3 + count * 3); | 
|  | 1366 | if (info == NULL) | 
|  | 1367 | return -1; | 
|  | 1368 |  | 
|  | 1369 | ipos = info; | 
|  | 1370 | *ipos++ = 0; /* GUD - Version 1 */ | 
|  | 1371 | *ipos++ = 3 + count * 3; /* User Data Header Length (UDHL) */ | 
|  | 1372 | *ipos++ = 0; /* PLMN List IEI */ | 
|  | 1373 | /* ext(b8) | Length of PLMN List value contents(b7..1) */ | 
|  | 1374 | *ipos++ = 1 + count * 3; | 
|  | 1375 | *ipos++ = count; /* Number of PLMNs */ | 
|  | 1376 |  | 
|  | 1377 | pos = buf; | 
|  | 1378 | while (pos && *pos) { | 
|  | 1379 | char *mcc, *mnc; | 
|  | 1380 | size_t mnc_len; | 
|  | 1381 |  | 
|  | 1382 | mcc = pos; | 
|  | 1383 | mnc = os_strchr(pos, ','); | 
|  | 1384 | if (mnc == NULL) | 
|  | 1385 | goto fail; | 
|  | 1386 | *mnc++ = '\0'; | 
|  | 1387 | pos = os_strchr(mnc, ';'); | 
|  | 1388 | if (pos) | 
|  | 1389 | *pos++ = '\0'; | 
|  | 1390 |  | 
|  | 1391 | mnc_len = os_strlen(mnc); | 
|  | 1392 | if (os_strlen(mcc) != 3 || (mnc_len != 2 && mnc_len != 3)) | 
|  | 1393 | goto fail; | 
|  | 1394 |  | 
|  | 1395 | /* BC coded MCC,MNC */ | 
|  | 1396 | /* MCC digit 2 | MCC digit 1 */ | 
|  | 1397 | *ipos++ = ((mcc[1] - '0') << 4) | (mcc[0] - '0'); | 
|  | 1398 | /* MNC digit 3 | MCC digit 3 */ | 
|  | 1399 | *ipos++ = (((mnc_len == 2) ? 0xf0 : ((mnc[2] - '0') << 4))) | | 
|  | 1400 | (mcc[2] - '0'); | 
|  | 1401 | /* MNC digit 2 | MNC digit 1 */ | 
|  | 1402 | *ipos++ = ((mnc[1] - '0') << 4) | (mnc[0] - '0'); | 
|  | 1403 | } | 
|  | 1404 |  | 
|  | 1405 | os_free(bss->anqp_3gpp_cell_net); | 
|  | 1406 | bss->anqp_3gpp_cell_net = info; | 
|  | 1407 | bss->anqp_3gpp_cell_net_len = 2 + 3 + 3 * count; | 
|  | 1408 | wpa_hexdump(MSG_MSGDUMP, "3GPP Cellular Network information", | 
|  | 1409 | bss->anqp_3gpp_cell_net, bss->anqp_3gpp_cell_net_len); | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1410 |  | 
|  | 1411 | return 0; | 
|  | 1412 |  | 
|  | 1413 | fail: | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1414 | wpa_printf(MSG_ERROR, "Line %d: Invalid anqp_3gpp_cell_net: %s", | 
|  | 1415 | line, buf); | 
|  | 1416 | os_free(info); | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 1417 | return -1; | 
|  | 1418 | } | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1419 |  | 
|  | 1420 |  | 
|  | 1421 | static int parse_nai_realm(struct hostapd_bss_config *bss, char *buf, int line) | 
|  | 1422 | { | 
|  | 1423 | struct hostapd_nai_realm_data *realm; | 
|  | 1424 | size_t i, j, len; | 
|  | 1425 | int *offsets; | 
|  | 1426 | char *pos, *end, *rpos; | 
|  | 1427 |  | 
|  | 1428 | offsets = os_calloc(bss->nai_realm_count * MAX_NAI_REALMS, | 
|  | 1429 | sizeof(int)); | 
|  | 1430 | if (offsets == NULL) | 
|  | 1431 | return -1; | 
|  | 1432 |  | 
|  | 1433 | for (i = 0; i < bss->nai_realm_count; i++) { | 
|  | 1434 | realm = &bss->nai_realm_data[i]; | 
|  | 1435 | for (j = 0; j < MAX_NAI_REALMS; j++) { | 
|  | 1436 | offsets[i * MAX_NAI_REALMS + j] = | 
|  | 1437 | realm->realm[j] ? | 
|  | 1438 | realm->realm[j] - realm->realm_buf : -1; | 
|  | 1439 | } | 
|  | 1440 | } | 
|  | 1441 |  | 
|  | 1442 | realm = os_realloc_array(bss->nai_realm_data, bss->nai_realm_count + 1, | 
|  | 1443 | sizeof(struct hostapd_nai_realm_data)); | 
|  | 1444 | if (realm == NULL) { | 
|  | 1445 | os_free(offsets); | 
|  | 1446 | return -1; | 
|  | 1447 | } | 
|  | 1448 | bss->nai_realm_data = realm; | 
|  | 1449 |  | 
|  | 1450 | /* patch the pointers after realloc */ | 
|  | 1451 | for (i = 0; i < bss->nai_realm_count; i++) { | 
|  | 1452 | realm = &bss->nai_realm_data[i]; | 
|  | 1453 | for (j = 0; j < MAX_NAI_REALMS; j++) { | 
|  | 1454 | int offs = offsets[i * MAX_NAI_REALMS + j]; | 
|  | 1455 | if (offs >= 0) | 
|  | 1456 | realm->realm[j] = realm->realm_buf + offs; | 
|  | 1457 | else | 
|  | 1458 | realm->realm[j] = NULL; | 
|  | 1459 | } | 
|  | 1460 | } | 
|  | 1461 | os_free(offsets); | 
|  | 1462 |  | 
|  | 1463 | realm = &bss->nai_realm_data[bss->nai_realm_count]; | 
|  | 1464 | os_memset(realm, 0, sizeof(*realm)); | 
|  | 1465 |  | 
|  | 1466 | pos = buf; | 
|  | 1467 | realm->encoding = atoi(pos); | 
|  | 1468 | pos = os_strchr(pos, ','); | 
|  | 1469 | if (pos == NULL) | 
|  | 1470 | goto fail; | 
|  | 1471 | pos++; | 
|  | 1472 |  | 
|  | 1473 | end = os_strchr(pos, ','); | 
|  | 1474 | if (end) { | 
|  | 1475 | len = end - pos; | 
|  | 1476 | *end = '\0'; | 
|  | 1477 | } else { | 
|  | 1478 | len = os_strlen(pos); | 
|  | 1479 | } | 
|  | 1480 |  | 
|  | 1481 | if (len > MAX_NAI_REALMLEN) { | 
|  | 1482 | wpa_printf(MSG_ERROR, "Too long a realm string (%d > max %d " | 
|  | 1483 | "characters)", (int) len, MAX_NAI_REALMLEN); | 
|  | 1484 | goto fail; | 
|  | 1485 | } | 
|  | 1486 | os_memcpy(realm->realm_buf, pos, len); | 
|  | 1487 |  | 
|  | 1488 | if (end) | 
|  | 1489 | pos = end + 1; | 
|  | 1490 | else | 
|  | 1491 | pos = NULL; | 
|  | 1492 |  | 
|  | 1493 | while (pos && *pos) { | 
|  | 1494 | struct hostapd_nai_realm_eap *eap; | 
|  | 1495 |  | 
|  | 1496 | if (realm->eap_method_count >= MAX_NAI_EAP_METHODS) { | 
|  | 1497 | wpa_printf(MSG_ERROR, "Too many EAP methods"); | 
|  | 1498 | goto fail; | 
|  | 1499 | } | 
|  | 1500 |  | 
|  | 1501 | eap = &realm->eap_method[realm->eap_method_count]; | 
|  | 1502 | realm->eap_method_count++; | 
|  | 1503 |  | 
|  | 1504 | end = os_strchr(pos, ','); | 
|  | 1505 | if (end == NULL) | 
|  | 1506 | end = pos + os_strlen(pos); | 
|  | 1507 |  | 
|  | 1508 | eap->eap_method = atoi(pos); | 
|  | 1509 | for (;;) { | 
|  | 1510 | pos = os_strchr(pos, '['); | 
|  | 1511 | if (pos == NULL || pos > end) | 
|  | 1512 | break; | 
|  | 1513 | pos++; | 
|  | 1514 | if (eap->num_auths >= MAX_NAI_AUTH_TYPES) { | 
|  | 1515 | wpa_printf(MSG_ERROR, "Too many auth params"); | 
|  | 1516 | goto fail; | 
|  | 1517 | } | 
|  | 1518 | eap->auth_id[eap->num_auths] = atoi(pos); | 
|  | 1519 | pos = os_strchr(pos, ':'); | 
|  | 1520 | if (pos == NULL || pos > end) | 
|  | 1521 | goto fail; | 
|  | 1522 | pos++; | 
|  | 1523 | eap->auth_val[eap->num_auths] = atoi(pos); | 
|  | 1524 | pos = os_strchr(pos, ']'); | 
|  | 1525 | if (pos == NULL || pos > end) | 
|  | 1526 | goto fail; | 
|  | 1527 | pos++; | 
|  | 1528 | eap->num_auths++; | 
|  | 1529 | } | 
|  | 1530 |  | 
|  | 1531 | if (*end != ',') | 
|  | 1532 | break; | 
|  | 1533 |  | 
|  | 1534 | pos = end + 1; | 
|  | 1535 | } | 
|  | 1536 |  | 
|  | 1537 | /* Split realm list into null terminated realms */ | 
|  | 1538 | rpos = realm->realm_buf; | 
|  | 1539 | i = 0; | 
|  | 1540 | while (*rpos) { | 
|  | 1541 | if (i >= MAX_NAI_REALMS) { | 
|  | 1542 | wpa_printf(MSG_ERROR, "Too many realms"); | 
|  | 1543 | goto fail; | 
|  | 1544 | } | 
|  | 1545 | realm->realm[i++] = rpos; | 
|  | 1546 | rpos = os_strchr(rpos, ';'); | 
|  | 1547 | if (rpos == NULL) | 
|  | 1548 | break; | 
|  | 1549 | *rpos++ = '\0'; | 
|  | 1550 | } | 
|  | 1551 |  | 
|  | 1552 | bss->nai_realm_count++; | 
|  | 1553 |  | 
|  | 1554 | return 0; | 
|  | 1555 |  | 
|  | 1556 | fail: | 
|  | 1557 | wpa_printf(MSG_ERROR, "Line %d: invalid nai_realm '%s'", line, buf); | 
|  | 1558 | return -1; | 
|  | 1559 | } | 
|  | 1560 |  | 
| Dmitry Shmidt | 051af73 | 2013-10-22 13:52:46 -0700 | [diff] [blame] | 1561 |  | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 1562 | static int parse_anqp_elem(struct hostapd_bss_config *bss, char *buf, int line) | 
|  | 1563 | { | 
|  | 1564 | char *delim; | 
|  | 1565 | u16 infoid; | 
|  | 1566 | size_t len; | 
|  | 1567 | struct wpabuf *payload; | 
|  | 1568 | struct anqp_element *elem; | 
|  | 1569 |  | 
|  | 1570 | delim = os_strchr(buf, ':'); | 
|  | 1571 | if (!delim) | 
|  | 1572 | return -1; | 
|  | 1573 | delim++; | 
|  | 1574 | infoid = atoi(buf); | 
|  | 1575 | len = os_strlen(delim); | 
|  | 1576 | if (len & 1) | 
|  | 1577 | return -1; | 
|  | 1578 | len /= 2; | 
|  | 1579 | payload = wpabuf_alloc(len); | 
|  | 1580 | if (!payload) | 
|  | 1581 | return -1; | 
|  | 1582 | if (hexstr2bin(delim, wpabuf_put(payload, len), len) < 0) { | 
|  | 1583 | wpabuf_free(payload); | 
|  | 1584 | return -1; | 
|  | 1585 | } | 
|  | 1586 |  | 
|  | 1587 | dl_list_for_each(elem, &bss->anqp_elem, struct anqp_element, list) { | 
|  | 1588 | if (elem->infoid == infoid) { | 
|  | 1589 | /* Update existing entry */ | 
|  | 1590 | wpabuf_free(elem->payload); | 
|  | 1591 | elem->payload = payload; | 
|  | 1592 | return 0; | 
|  | 1593 | } | 
|  | 1594 | } | 
|  | 1595 |  | 
|  | 1596 | /* Add a new entry */ | 
|  | 1597 | elem = os_zalloc(sizeof(*elem)); | 
|  | 1598 | if (!elem) { | 
|  | 1599 | wpabuf_free(payload); | 
|  | 1600 | return -1; | 
|  | 1601 | } | 
|  | 1602 | elem->infoid = infoid; | 
|  | 1603 | elem->payload = payload; | 
|  | 1604 | dl_list_add(&bss->anqp_elem, &elem->list); | 
|  | 1605 |  | 
|  | 1606 | return 0; | 
|  | 1607 | } | 
|  | 1608 |  | 
|  | 1609 |  | 
| Dmitry Shmidt | 051af73 | 2013-10-22 13:52:46 -0700 | [diff] [blame] | 1610 | static int parse_qos_map_set(struct hostapd_bss_config *bss, | 
|  | 1611 | char *buf, int line) | 
|  | 1612 | { | 
|  | 1613 | u8 qos_map_set[16 + 2 * 21], count = 0; | 
|  | 1614 | char *pos = buf; | 
|  | 1615 | int val; | 
|  | 1616 |  | 
|  | 1617 | for (;;) { | 
|  | 1618 | if (count == sizeof(qos_map_set)) { | 
|  | 1619 | wpa_printf(MSG_ERROR, "Line %d: Too many qos_map_set " | 
|  | 1620 | "parameters '%s'", line, buf); | 
|  | 1621 | return -1; | 
|  | 1622 | } | 
|  | 1623 |  | 
|  | 1624 | val = atoi(pos); | 
|  | 1625 | if (val > 255 || val < 0) { | 
|  | 1626 | wpa_printf(MSG_ERROR, "Line %d: Invalid qos_map_set " | 
|  | 1627 | "'%s'", line, buf); | 
|  | 1628 | return -1; | 
|  | 1629 | } | 
|  | 1630 |  | 
|  | 1631 | qos_map_set[count++] = val; | 
|  | 1632 | pos = os_strchr(pos, ','); | 
|  | 1633 | if (!pos) | 
|  | 1634 | break; | 
|  | 1635 | pos++; | 
|  | 1636 | } | 
|  | 1637 |  | 
|  | 1638 | if (count < 16 || count & 1) { | 
|  | 1639 | wpa_printf(MSG_ERROR, "Line %d: Invalid qos_map_set '%s'", | 
|  | 1640 | line, buf); | 
|  | 1641 | return -1; | 
|  | 1642 | } | 
|  | 1643 |  | 
|  | 1644 | os_memcpy(bss->qos_map_set, qos_map_set, count); | 
|  | 1645 | bss->qos_map_set_len = count; | 
|  | 1646 |  | 
|  | 1647 | return 0; | 
|  | 1648 | } | 
|  | 1649 |  | 
| Sunil Ravi | 8861141 | 2024-06-28 17:34:56 +0000 | [diff] [blame] | 1650 | #endif /* CONFIG_INTERWORKING */ | 
|  | 1651 |  | 
| Dmitry Shmidt | 1f69aa5 | 2012-01-24 16:10:04 -0800 | [diff] [blame] | 1652 |  | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1653 | #ifdef CONFIG_HS20 | 
|  | 1654 | static int hs20_parse_conn_capab(struct hostapd_bss_config *bss, char *buf, | 
|  | 1655 | int line) | 
|  | 1656 | { | 
|  | 1657 | u8 *conn_cap; | 
|  | 1658 | char *pos; | 
|  | 1659 |  | 
|  | 1660 | if (bss->hs20_connection_capability_len >= 0xfff0) | 
|  | 1661 | return -1; | 
|  | 1662 |  | 
|  | 1663 | conn_cap = os_realloc(bss->hs20_connection_capability, | 
|  | 1664 | bss->hs20_connection_capability_len + 4); | 
|  | 1665 | if (conn_cap == NULL) | 
|  | 1666 | return -1; | 
|  | 1667 |  | 
|  | 1668 | bss->hs20_connection_capability = conn_cap; | 
|  | 1669 | conn_cap += bss->hs20_connection_capability_len; | 
|  | 1670 | pos = buf; | 
|  | 1671 | conn_cap[0] = atoi(pos); | 
|  | 1672 | pos = os_strchr(pos, ':'); | 
|  | 1673 | if (pos == NULL) | 
|  | 1674 | return -1; | 
|  | 1675 | pos++; | 
|  | 1676 | WPA_PUT_LE16(conn_cap + 1, atoi(pos)); | 
|  | 1677 | pos = os_strchr(pos, ':'); | 
|  | 1678 | if (pos == NULL) | 
|  | 1679 | return -1; | 
|  | 1680 | pos++; | 
|  | 1681 | conn_cap[3] = atoi(pos); | 
|  | 1682 | bss->hs20_connection_capability_len += 4; | 
|  | 1683 |  | 
|  | 1684 | return 0; | 
|  | 1685 | } | 
|  | 1686 |  | 
|  | 1687 |  | 
|  | 1688 | static int hs20_parse_wan_metrics(struct hostapd_bss_config *bss, char *buf, | 
|  | 1689 | int line) | 
|  | 1690 | { | 
|  | 1691 | u8 *wan_metrics; | 
|  | 1692 | char *pos; | 
|  | 1693 |  | 
|  | 1694 | /* <WAN Info>:<DL Speed>:<UL Speed>:<DL Load>:<UL Load>:<LMD> */ | 
|  | 1695 |  | 
|  | 1696 | wan_metrics = os_zalloc(13); | 
|  | 1697 | if (wan_metrics == NULL) | 
|  | 1698 | return -1; | 
|  | 1699 |  | 
|  | 1700 | pos = buf; | 
|  | 1701 | /* WAN Info */ | 
|  | 1702 | if (hexstr2bin(pos, wan_metrics, 1) < 0) | 
|  | 1703 | goto fail; | 
|  | 1704 | pos += 2; | 
|  | 1705 | if (*pos != ':') | 
|  | 1706 | goto fail; | 
|  | 1707 | pos++; | 
|  | 1708 |  | 
|  | 1709 | /* Downlink Speed */ | 
|  | 1710 | WPA_PUT_LE32(wan_metrics + 1, atoi(pos)); | 
|  | 1711 | pos = os_strchr(pos, ':'); | 
|  | 1712 | if (pos == NULL) | 
|  | 1713 | goto fail; | 
|  | 1714 | pos++; | 
|  | 1715 |  | 
|  | 1716 | /* Uplink Speed */ | 
|  | 1717 | WPA_PUT_LE32(wan_metrics + 5, atoi(pos)); | 
|  | 1718 | pos = os_strchr(pos, ':'); | 
|  | 1719 | if (pos == NULL) | 
|  | 1720 | goto fail; | 
|  | 1721 | pos++; | 
|  | 1722 |  | 
|  | 1723 | /* Downlink Load */ | 
|  | 1724 | wan_metrics[9] = atoi(pos); | 
|  | 1725 | pos = os_strchr(pos, ':'); | 
|  | 1726 | if (pos == NULL) | 
|  | 1727 | goto fail; | 
|  | 1728 | pos++; | 
|  | 1729 |  | 
|  | 1730 | /* Uplink Load */ | 
|  | 1731 | wan_metrics[10] = atoi(pos); | 
|  | 1732 | pos = os_strchr(pos, ':'); | 
|  | 1733 | if (pos == NULL) | 
|  | 1734 | goto fail; | 
|  | 1735 | pos++; | 
|  | 1736 |  | 
|  | 1737 | /* LMD */ | 
|  | 1738 | WPA_PUT_LE16(wan_metrics + 11, atoi(pos)); | 
|  | 1739 |  | 
|  | 1740 | os_free(bss->hs20_wan_metrics); | 
|  | 1741 | bss->hs20_wan_metrics = wan_metrics; | 
|  | 1742 |  | 
|  | 1743 | return 0; | 
|  | 1744 |  | 
|  | 1745 | fail: | 
|  | 1746 | wpa_printf(MSG_ERROR, "Line %d: Invalid hs20_wan_metrics '%s'", | 
| Dmitry Shmidt | df5a7e4 | 2014-04-02 12:59:59 -0700 | [diff] [blame] | 1747 | line, buf); | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1748 | os_free(wan_metrics); | 
|  | 1749 | return -1; | 
|  | 1750 | } | 
|  | 1751 |  | 
|  | 1752 |  | 
|  | 1753 | static int hs20_parse_oper_friendly_name(struct hostapd_bss_config *bss, | 
|  | 1754 | char *pos, int line) | 
|  | 1755 | { | 
|  | 1756 | if (parse_lang_string(&bss->hs20_oper_friendly_name, | 
|  | 1757 | &bss->hs20_oper_friendly_name_count, pos)) { | 
|  | 1758 | wpa_printf(MSG_ERROR, "Line %d: Invalid " | 
|  | 1759 | "hs20_oper_friendly_name '%s'", line, pos); | 
|  | 1760 | return -1; | 
|  | 1761 | } | 
|  | 1762 | return 0; | 
|  | 1763 | } | 
| Dmitry Shmidt | f21452a | 2014-02-26 10:55:25 -0800 | [diff] [blame] | 1764 |  | 
|  | 1765 |  | 
|  | 1766 | static int hs20_parse_icon(struct hostapd_bss_config *bss, char *pos) | 
|  | 1767 | { | 
|  | 1768 | struct hs20_icon *icon; | 
|  | 1769 | char *end; | 
|  | 1770 |  | 
|  | 1771 | icon = os_realloc_array(bss->hs20_icons, bss->hs20_icons_count + 1, | 
|  | 1772 | sizeof(struct hs20_icon)); | 
|  | 1773 | if (icon == NULL) | 
|  | 1774 | return -1; | 
|  | 1775 | bss->hs20_icons = icon; | 
|  | 1776 | icon = &bss->hs20_icons[bss->hs20_icons_count]; | 
|  | 1777 | os_memset(icon, 0, sizeof(*icon)); | 
|  | 1778 |  | 
|  | 1779 | icon->width = atoi(pos); | 
|  | 1780 | pos = os_strchr(pos, ':'); | 
|  | 1781 | if (pos == NULL) | 
|  | 1782 | return -1; | 
|  | 1783 | pos++; | 
|  | 1784 |  | 
|  | 1785 | icon->height = atoi(pos); | 
|  | 1786 | pos = os_strchr(pos, ':'); | 
|  | 1787 | if (pos == NULL) | 
|  | 1788 | return -1; | 
|  | 1789 | pos++; | 
|  | 1790 |  | 
|  | 1791 | end = os_strchr(pos, ':'); | 
|  | 1792 | if (end == NULL || end - pos > 3) | 
|  | 1793 | return -1; | 
|  | 1794 | os_memcpy(icon->language, pos, end - pos); | 
|  | 1795 | pos = end + 1; | 
|  | 1796 |  | 
|  | 1797 | end = os_strchr(pos, ':'); | 
|  | 1798 | if (end == NULL || end - pos > 255) | 
|  | 1799 | return -1; | 
|  | 1800 | os_memcpy(icon->type, pos, end - pos); | 
|  | 1801 | pos = end + 1; | 
|  | 1802 |  | 
|  | 1803 | end = os_strchr(pos, ':'); | 
|  | 1804 | if (end == NULL || end - pos > 255) | 
|  | 1805 | return -1; | 
|  | 1806 | os_memcpy(icon->name, pos, end - pos); | 
|  | 1807 | pos = end + 1; | 
|  | 1808 |  | 
|  | 1809 | if (os_strlen(pos) > 255) | 
|  | 1810 | return -1; | 
|  | 1811 | os_memcpy(icon->file, pos, os_strlen(pos)); | 
|  | 1812 |  | 
|  | 1813 | bss->hs20_icons_count++; | 
|  | 1814 |  | 
|  | 1815 | return 0; | 
|  | 1816 | } | 
|  | 1817 |  | 
|  | 1818 |  | 
|  | 1819 | static int hs20_parse_osu_ssid(struct hostapd_bss_config *bss, | 
|  | 1820 | char *pos, int line) | 
|  | 1821 | { | 
|  | 1822 | size_t slen; | 
|  | 1823 | char *str; | 
|  | 1824 |  | 
|  | 1825 | str = wpa_config_parse_string(pos, &slen); | 
| Dmitry Shmidt | 9d9e602 | 2015-04-23 10:34:55 -0700 | [diff] [blame] | 1826 | if (str == NULL || slen < 1 || slen > SSID_MAX_LEN) { | 
| Dmitry Shmidt | f21452a | 2014-02-26 10:55:25 -0800 | [diff] [blame] | 1827 | wpa_printf(MSG_ERROR, "Line %d: Invalid SSID '%s'", line, pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 1828 | os_free(str); | 
| Dmitry Shmidt | f21452a | 2014-02-26 10:55:25 -0800 | [diff] [blame] | 1829 | return -1; | 
|  | 1830 | } | 
|  | 1831 |  | 
|  | 1832 | os_memcpy(bss->osu_ssid, str, slen); | 
|  | 1833 | bss->osu_ssid_len = slen; | 
|  | 1834 | os_free(str); | 
|  | 1835 |  | 
|  | 1836 | return 0; | 
|  | 1837 | } | 
|  | 1838 |  | 
|  | 1839 |  | 
|  | 1840 | static int hs20_parse_osu_server_uri(struct hostapd_bss_config *bss, | 
|  | 1841 | char *pos, int line) | 
|  | 1842 | { | 
|  | 1843 | struct hs20_osu_provider *p; | 
|  | 1844 |  | 
|  | 1845 | p = os_realloc_array(bss->hs20_osu_providers, | 
|  | 1846 | bss->hs20_osu_providers_count + 1, sizeof(*p)); | 
|  | 1847 | if (p == NULL) | 
|  | 1848 | return -1; | 
|  | 1849 |  | 
|  | 1850 | bss->hs20_osu_providers = p; | 
|  | 1851 | bss->last_osu = &bss->hs20_osu_providers[bss->hs20_osu_providers_count]; | 
|  | 1852 | bss->hs20_osu_providers_count++; | 
|  | 1853 | os_memset(bss->last_osu, 0, sizeof(*p)); | 
|  | 1854 | bss->last_osu->server_uri = os_strdup(pos); | 
|  | 1855 |  | 
|  | 1856 | return 0; | 
|  | 1857 | } | 
|  | 1858 |  | 
|  | 1859 |  | 
|  | 1860 | static int hs20_parse_osu_friendly_name(struct hostapd_bss_config *bss, | 
|  | 1861 | char *pos, int line) | 
|  | 1862 | { | 
|  | 1863 | if (bss->last_osu == NULL) { | 
|  | 1864 | wpa_printf(MSG_ERROR, "Line %d: Unexpected OSU field", line); | 
|  | 1865 | return -1; | 
|  | 1866 | } | 
|  | 1867 |  | 
|  | 1868 | if (parse_lang_string(&bss->last_osu->friendly_name, | 
|  | 1869 | &bss->last_osu->friendly_name_count, pos)) { | 
|  | 1870 | wpa_printf(MSG_ERROR, "Line %d: Invalid osu_friendly_name '%s'", | 
|  | 1871 | line, pos); | 
|  | 1872 | return -1; | 
|  | 1873 | } | 
|  | 1874 |  | 
|  | 1875 | return 0; | 
|  | 1876 | } | 
|  | 1877 |  | 
|  | 1878 |  | 
|  | 1879 | static int hs20_parse_osu_nai(struct hostapd_bss_config *bss, | 
|  | 1880 | char *pos, int line) | 
|  | 1881 | { | 
|  | 1882 | if (bss->last_osu == NULL) { | 
|  | 1883 | wpa_printf(MSG_ERROR, "Line %d: Unexpected OSU field", line); | 
|  | 1884 | return -1; | 
|  | 1885 | } | 
|  | 1886 |  | 
|  | 1887 | os_free(bss->last_osu->osu_nai); | 
|  | 1888 | bss->last_osu->osu_nai = os_strdup(pos); | 
|  | 1889 | if (bss->last_osu->osu_nai == NULL) | 
|  | 1890 | return -1; | 
|  | 1891 |  | 
|  | 1892 | return 0; | 
|  | 1893 | } | 
|  | 1894 |  | 
|  | 1895 |  | 
| Hai Shalom | 39ba6fc | 2019-01-22 12:40:38 -0800 | [diff] [blame] | 1896 | static int hs20_parse_osu_nai2(struct hostapd_bss_config *bss, | 
|  | 1897 | char *pos, int line) | 
|  | 1898 | { | 
|  | 1899 | if (bss->last_osu == NULL) { | 
|  | 1900 | wpa_printf(MSG_ERROR, "Line %d: Unexpected OSU field", line); | 
|  | 1901 | return -1; | 
|  | 1902 | } | 
|  | 1903 |  | 
|  | 1904 | os_free(bss->last_osu->osu_nai2); | 
|  | 1905 | bss->last_osu->osu_nai2 = os_strdup(pos); | 
|  | 1906 | if (bss->last_osu->osu_nai2 == NULL) | 
|  | 1907 | return -1; | 
|  | 1908 | bss->hs20_osu_providers_nai_count++; | 
|  | 1909 |  | 
|  | 1910 | return 0; | 
|  | 1911 | } | 
|  | 1912 |  | 
|  | 1913 |  | 
| Dmitry Shmidt | f21452a | 2014-02-26 10:55:25 -0800 | [diff] [blame] | 1914 | static int hs20_parse_osu_method_list(struct hostapd_bss_config *bss, char *pos, | 
|  | 1915 | int line) | 
|  | 1916 | { | 
|  | 1917 | if (bss->last_osu == NULL) { | 
|  | 1918 | wpa_printf(MSG_ERROR, "Line %d: Unexpected OSU field", line); | 
|  | 1919 | return -1; | 
|  | 1920 | } | 
|  | 1921 |  | 
|  | 1922 | if (hostapd_parse_intlist(&bss->last_osu->method_list, pos)) { | 
|  | 1923 | wpa_printf(MSG_ERROR, "Line %d: Invalid osu_method_list", line); | 
|  | 1924 | return -1; | 
|  | 1925 | } | 
|  | 1926 |  | 
|  | 1927 | return 0; | 
|  | 1928 | } | 
|  | 1929 |  | 
|  | 1930 |  | 
|  | 1931 | static int hs20_parse_osu_icon(struct hostapd_bss_config *bss, char *pos, | 
|  | 1932 | int line) | 
|  | 1933 | { | 
|  | 1934 | char **n; | 
|  | 1935 | struct hs20_osu_provider *p = bss->last_osu; | 
|  | 1936 |  | 
|  | 1937 | if (p == NULL) { | 
|  | 1938 | wpa_printf(MSG_ERROR, "Line %d: Unexpected OSU field", line); | 
|  | 1939 | return -1; | 
|  | 1940 | } | 
|  | 1941 |  | 
|  | 1942 | n = os_realloc_array(p->icons, p->icons_count + 1, sizeof(char *)); | 
|  | 1943 | if (n == NULL) | 
|  | 1944 | return -1; | 
|  | 1945 | p->icons = n; | 
|  | 1946 | p->icons[p->icons_count] = os_strdup(pos); | 
|  | 1947 | if (p->icons[p->icons_count] == NULL) | 
|  | 1948 | return -1; | 
|  | 1949 | p->icons_count++; | 
|  | 1950 |  | 
|  | 1951 | return 0; | 
|  | 1952 | } | 
|  | 1953 |  | 
|  | 1954 |  | 
|  | 1955 | static int hs20_parse_osu_service_desc(struct hostapd_bss_config *bss, | 
|  | 1956 | char *pos, int line) | 
|  | 1957 | { | 
|  | 1958 | if (bss->last_osu == NULL) { | 
|  | 1959 | wpa_printf(MSG_ERROR, "Line %d: Unexpected OSU field", line); | 
|  | 1960 | return -1; | 
|  | 1961 | } | 
|  | 1962 |  | 
|  | 1963 | if (parse_lang_string(&bss->last_osu->service_desc, | 
|  | 1964 | &bss->last_osu->service_desc_count, pos)) { | 
|  | 1965 | wpa_printf(MSG_ERROR, "Line %d: Invalid osu_service_desc '%s'", | 
|  | 1966 | line, pos); | 
|  | 1967 | return -1; | 
|  | 1968 | } | 
|  | 1969 |  | 
|  | 1970 | return 0; | 
|  | 1971 | } | 
|  | 1972 |  | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 1973 |  | 
|  | 1974 | static int hs20_parse_operator_icon(struct hostapd_bss_config *bss, char *pos, | 
|  | 1975 | int line) | 
|  | 1976 | { | 
|  | 1977 | char **n; | 
|  | 1978 |  | 
|  | 1979 | n = os_realloc_array(bss->hs20_operator_icon, | 
|  | 1980 | bss->hs20_operator_icon_count + 1, sizeof(char *)); | 
|  | 1981 | if (!n) | 
|  | 1982 | return -1; | 
|  | 1983 | bss->hs20_operator_icon = n; | 
|  | 1984 | bss->hs20_operator_icon[bss->hs20_operator_icon_count] = os_strdup(pos); | 
|  | 1985 | if (!bss->hs20_operator_icon[bss->hs20_operator_icon_count]) | 
|  | 1986 | return -1; | 
|  | 1987 | bss->hs20_operator_icon_count++; | 
|  | 1988 |  | 
|  | 1989 | return 0; | 
|  | 1990 | } | 
|  | 1991 |  | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 1992 | #endif /* CONFIG_HS20 */ | 
|  | 1993 |  | 
|  | 1994 |  | 
| Dmitry Shmidt | 7f65602 | 2015-02-25 14:36:37 -0800 | [diff] [blame] | 1995 | #ifdef CONFIG_ACS | 
|  | 1996 | static int hostapd_config_parse_acs_chan_bias(struct hostapd_config *conf, | 
|  | 1997 | char *pos) | 
|  | 1998 | { | 
|  | 1999 | struct acs_bias *bias = NULL, *tmp; | 
|  | 2000 | unsigned int num = 0; | 
|  | 2001 | char *end; | 
|  | 2002 |  | 
|  | 2003 | while (*pos) { | 
|  | 2004 | tmp = os_realloc_array(bias, num + 1, sizeof(*bias)); | 
|  | 2005 | if (!tmp) | 
|  | 2006 | goto fail; | 
|  | 2007 | bias = tmp; | 
|  | 2008 |  | 
|  | 2009 | bias[num].channel = atoi(pos); | 
|  | 2010 | if (bias[num].channel <= 0) | 
|  | 2011 | goto fail; | 
|  | 2012 | pos = os_strchr(pos, ':'); | 
|  | 2013 | if (!pos) | 
|  | 2014 | goto fail; | 
|  | 2015 | pos++; | 
|  | 2016 | bias[num].bias = strtod(pos, &end); | 
|  | 2017 | if (end == pos || bias[num].bias < 0.0) | 
|  | 2018 | goto fail; | 
|  | 2019 | pos = end; | 
|  | 2020 | if (*pos != ' ' && *pos != '\0') | 
|  | 2021 | goto fail; | 
|  | 2022 | num++; | 
|  | 2023 | } | 
|  | 2024 |  | 
|  | 2025 | os_free(conf->acs_chan_bias); | 
|  | 2026 | conf->acs_chan_bias = bias; | 
|  | 2027 | conf->num_acs_chan_bias = num; | 
|  | 2028 |  | 
|  | 2029 | return 0; | 
|  | 2030 | fail: | 
|  | 2031 | os_free(bias); | 
|  | 2032 | return -1; | 
|  | 2033 | } | 
|  | 2034 | #endif /* CONFIG_ACS */ | 
|  | 2035 |  | 
|  | 2036 |  | 
| Dmitry Shmidt | 849734c | 2016-05-27 09:59:01 -0700 | [diff] [blame] | 2037 | static int parse_wpabuf_hex(int line, const char *name, struct wpabuf **buf, | 
|  | 2038 | const char *val) | 
|  | 2039 | { | 
|  | 2040 | struct wpabuf *elems; | 
|  | 2041 |  | 
|  | 2042 | if (val[0] == '\0') { | 
|  | 2043 | wpabuf_free(*buf); | 
|  | 2044 | *buf = NULL; | 
|  | 2045 | return 0; | 
|  | 2046 | } | 
|  | 2047 |  | 
|  | 2048 | elems = wpabuf_parse_bin(val); | 
|  | 2049 | if (!elems) { | 
|  | 2050 | wpa_printf(MSG_ERROR, "Line %d: Invalid %s '%s'", | 
|  | 2051 | line, name, val); | 
|  | 2052 | return -1; | 
|  | 2053 | } | 
|  | 2054 |  | 
|  | 2055 | wpabuf_free(*buf); | 
|  | 2056 | *buf = elems; | 
|  | 2057 |  | 
|  | 2058 | return 0; | 
|  | 2059 | } | 
|  | 2060 |  | 
|  | 2061 |  | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2062 | #ifdef CONFIG_FILS | 
|  | 2063 | static int parse_fils_realm(struct hostapd_bss_config *bss, const char *val) | 
|  | 2064 | { | 
|  | 2065 | struct fils_realm *realm; | 
|  | 2066 | size_t len; | 
|  | 2067 |  | 
|  | 2068 | len = os_strlen(val); | 
|  | 2069 | realm = os_zalloc(sizeof(*realm) + len + 1); | 
|  | 2070 | if (!realm) | 
|  | 2071 | return -1; | 
|  | 2072 |  | 
|  | 2073 | os_memcpy(realm->realm, val, len); | 
|  | 2074 | if (fils_domain_name_hash(val, realm->hash) < 0) { | 
|  | 2075 | os_free(realm); | 
|  | 2076 | return -1; | 
|  | 2077 | } | 
|  | 2078 | dl_list_add_tail(&bss->fils_realms, &realm->list); | 
|  | 2079 |  | 
|  | 2080 | return 0; | 
|  | 2081 | } | 
|  | 2082 | #endif /* CONFIG_FILS */ | 
|  | 2083 |  | 
|  | 2084 |  | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2085 | #ifdef EAP_SERVER | 
|  | 2086 | static unsigned int parse_tls_flags(const char *val) | 
|  | 2087 | { | 
|  | 2088 | unsigned int flags = 0; | 
|  | 2089 |  | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 2090 | /* Disable TLS v1.3 by default for now to avoid interoperability issue. | 
|  | 2091 | * This can be enabled by default once the implementation has been fully | 
|  | 2092 | * completed and tested with other implementations. */ | 
|  | 2093 | flags |= TLS_CONN_DISABLE_TLSv1_3; | 
|  | 2094 |  | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2095 | if (os_strstr(val, "[ALLOW-SIGN-RSA-MD5]")) | 
|  | 2096 | flags |= TLS_CONN_ALLOW_SIGN_RSA_MD5; | 
|  | 2097 | if (os_strstr(val, "[DISABLE-TIME-CHECKS]")) | 
|  | 2098 | flags |= TLS_CONN_DISABLE_TIME_CHECKS; | 
|  | 2099 | if (os_strstr(val, "[DISABLE-TLSv1.0]")) | 
|  | 2100 | flags |= TLS_CONN_DISABLE_TLSv1_0; | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 2101 | if (os_strstr(val, "[ENABLE-TLSv1.0]")) | 
|  | 2102 | flags |= TLS_CONN_ENABLE_TLSv1_0; | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2103 | if (os_strstr(val, "[DISABLE-TLSv1.1]")) | 
|  | 2104 | flags |= TLS_CONN_DISABLE_TLSv1_1; | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 2105 | if (os_strstr(val, "[ENABLE-TLSv1.1]")) | 
|  | 2106 | flags |= TLS_CONN_ENABLE_TLSv1_1; | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2107 | if (os_strstr(val, "[DISABLE-TLSv1.2]")) | 
|  | 2108 | flags |= TLS_CONN_DISABLE_TLSv1_2; | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 2109 | if (os_strstr(val, "[ENABLE-TLSv1.2]")) | 
|  | 2110 | flags |= TLS_CONN_ENABLE_TLSv1_2; | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 2111 | if (os_strstr(val, "[DISABLE-TLSv1.3]")) | 
|  | 2112 | flags |= TLS_CONN_DISABLE_TLSv1_3; | 
|  | 2113 | if (os_strstr(val, "[ENABLE-TLSv1.3]")) | 
|  | 2114 | flags &= ~TLS_CONN_DISABLE_TLSv1_3; | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2115 | if (os_strstr(val, "[SUITEB]")) | 
|  | 2116 | flags |= TLS_CONN_SUITEB; | 
|  | 2117 | if (os_strstr(val, "[SUITEB-NO-ECDH]")) | 
|  | 2118 | flags |= TLS_CONN_SUITEB_NO_ECDH | TLS_CONN_SUITEB; | 
|  | 2119 |  | 
|  | 2120 | return flags; | 
|  | 2121 | } | 
|  | 2122 | #endif /* EAP_SERVER */ | 
|  | 2123 |  | 
|  | 2124 |  | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2125 | #ifdef CONFIG_AIRTIME_POLICY | 
|  | 2126 | static int add_airtime_weight(struct hostapd_bss_config *bss, char *value) | 
|  | 2127 | { | 
|  | 2128 | struct airtime_sta_weight *wt; | 
|  | 2129 | char *pos, *next; | 
|  | 2130 |  | 
|  | 2131 | wt = os_zalloc(sizeof(*wt)); | 
|  | 2132 | if (!wt) | 
|  | 2133 | return -1; | 
|  | 2134 |  | 
|  | 2135 | /* 02:01:02:03:04:05 10 */ | 
|  | 2136 | pos = value; | 
|  | 2137 | next = os_strchr(pos, ' '); | 
|  | 2138 | if (next) | 
|  | 2139 | *next++ = '\0'; | 
|  | 2140 | if (!next || hwaddr_aton(pos, wt->addr)) { | 
|  | 2141 | wpa_printf(MSG_ERROR, "Invalid station address: '%s'", pos); | 
|  | 2142 | os_free(wt); | 
|  | 2143 | return -1; | 
|  | 2144 | } | 
|  | 2145 |  | 
|  | 2146 | pos = next; | 
|  | 2147 | wt->weight = atoi(pos); | 
|  | 2148 | if (!wt->weight) { | 
|  | 2149 | wpa_printf(MSG_ERROR, "Invalid weight: '%s'", pos); | 
|  | 2150 | os_free(wt); | 
|  | 2151 | return -1; | 
|  | 2152 | } | 
|  | 2153 |  | 
|  | 2154 | wt->next = bss->airtime_weight_list; | 
|  | 2155 | bss->airtime_weight_list = wt; | 
|  | 2156 | return 0; | 
|  | 2157 | } | 
|  | 2158 | #endif /* CONFIG_AIRTIME_POLICY */ | 
|  | 2159 |  | 
|  | 2160 |  | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 2161 | #ifdef CONFIG_SAE | 
|  | 2162 | static int parse_sae_password(struct hostapd_bss_config *bss, const char *val) | 
|  | 2163 | { | 
|  | 2164 | struct sae_password_entry *pw; | 
|  | 2165 | const char *pos = val, *pos2, *end = NULL; | 
|  | 2166 |  | 
|  | 2167 | pw = os_zalloc(sizeof(*pw)); | 
|  | 2168 | if (!pw) | 
|  | 2169 | return -1; | 
|  | 2170 | os_memset(pw->peer_addr, 0xff, ETH_ALEN); /* default to wildcard */ | 
|  | 2171 |  | 
|  | 2172 | pos2 = os_strstr(pos, "|mac="); | 
|  | 2173 | if (pos2) { | 
|  | 2174 | end = pos2; | 
|  | 2175 | pos2 += 5; | 
|  | 2176 | if (hwaddr_aton(pos2, pw->peer_addr) < 0) | 
|  | 2177 | goto fail; | 
|  | 2178 | pos = pos2 + ETH_ALEN * 3 - 1; | 
|  | 2179 | } | 
|  | 2180 |  | 
| Hai Shalom | 021b0b5 | 2019-04-10 11:17:58 -0700 | [diff] [blame] | 2181 | pos2 = os_strstr(pos, "|vlanid="); | 
|  | 2182 | if (pos2) { | 
|  | 2183 | if (!end) | 
|  | 2184 | end = pos2; | 
|  | 2185 | pos2 += 8; | 
|  | 2186 | pw->vlan_id = atoi(pos2); | 
|  | 2187 | } | 
|  | 2188 |  | 
| Hai Shalom | 899fcc7 | 2020-10-19 14:38:18 -0700 | [diff] [blame] | 2189 | #ifdef CONFIG_SAE_PK | 
|  | 2190 | pos2 = os_strstr(pos, "|pk="); | 
|  | 2191 | if (pos2) { | 
|  | 2192 | const char *epos; | 
|  | 2193 | char *tmp; | 
|  | 2194 |  | 
|  | 2195 | if (!end) | 
|  | 2196 | end = pos2; | 
|  | 2197 | pos2 += 4; | 
|  | 2198 | epos = os_strchr(pos2, '|'); | 
|  | 2199 | if (epos) { | 
|  | 2200 | tmp = os_malloc(epos - pos2 + 1); | 
|  | 2201 | if (!tmp) | 
|  | 2202 | goto fail; | 
|  | 2203 | os_memcpy(tmp, pos2, epos - pos2); | 
|  | 2204 | tmp[epos - pos2] = '\0'; | 
|  | 2205 | } else { | 
|  | 2206 | tmp = os_strdup(pos2); | 
|  | 2207 | if (!tmp) | 
|  | 2208 | goto fail; | 
|  | 2209 | } | 
|  | 2210 |  | 
|  | 2211 | pw->pk = sae_parse_pk(tmp); | 
|  | 2212 | str_clear_free(tmp); | 
|  | 2213 | if (!pw->pk) | 
|  | 2214 | goto fail; | 
|  | 2215 | } | 
|  | 2216 | #endif /* CONFIG_SAE_PK */ | 
|  | 2217 |  | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 2218 | pos2 = os_strstr(pos, "|id="); | 
|  | 2219 | if (pos2) { | 
|  | 2220 | if (!end) | 
|  | 2221 | end = pos2; | 
|  | 2222 | pos2 += 4; | 
|  | 2223 | pw->identifier = os_strdup(pos2); | 
|  | 2224 | if (!pw->identifier) | 
|  | 2225 | goto fail; | 
|  | 2226 | } | 
|  | 2227 |  | 
|  | 2228 | if (!end) { | 
|  | 2229 | pw->password = os_strdup(val); | 
|  | 2230 | if (!pw->password) | 
|  | 2231 | goto fail; | 
|  | 2232 | } else { | 
|  | 2233 | pw->password = os_malloc(end - val + 1); | 
|  | 2234 | if (!pw->password) | 
|  | 2235 | goto fail; | 
|  | 2236 | os_memcpy(pw->password, val, end - val); | 
|  | 2237 | pw->password[end - val] = '\0'; | 
|  | 2238 | } | 
|  | 2239 |  | 
| Hai Shalom | 899fcc7 | 2020-10-19 14:38:18 -0700 | [diff] [blame] | 2240 | #ifdef CONFIG_SAE_PK | 
|  | 2241 | if (pw->pk && | 
|  | 2242 | #ifdef CONFIG_TESTING_OPTIONS | 
|  | 2243 | !bss->sae_pk_password_check_skip && | 
|  | 2244 | #endif /* CONFIG_TESTING_OPTIONS */ | 
|  | 2245 | !sae_pk_valid_password(pw->password)) { | 
|  | 2246 | wpa_printf(MSG_INFO, | 
|  | 2247 | "Invalid SAE password for a SAE-PK sae_password entry"); | 
|  | 2248 | goto fail; | 
|  | 2249 | } | 
|  | 2250 | #endif /* CONFIG_SAE_PK */ | 
|  | 2251 |  | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 2252 | pw->next = bss->sae_passwords; | 
|  | 2253 | bss->sae_passwords = pw; | 
|  | 2254 |  | 
|  | 2255 | return 0; | 
|  | 2256 | fail: | 
|  | 2257 | str_clear_free(pw->password); | 
|  | 2258 | os_free(pw->identifier); | 
| Hai Shalom | 899fcc7 | 2020-10-19 14:38:18 -0700 | [diff] [blame] | 2259 | #ifdef CONFIG_SAE_PK | 
|  | 2260 | sae_deinit_pk(pw->pk); | 
|  | 2261 | #endif /* CONFIG_SAE_PK */ | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 2262 | os_free(pw); | 
|  | 2263 | return -1; | 
|  | 2264 | } | 
|  | 2265 | #endif /* CONFIG_SAE */ | 
|  | 2266 |  | 
|  | 2267 |  | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2268 | #ifdef CONFIG_DPP2 | 
|  | 2269 | static int hostapd_dpp_controller_parse(struct hostapd_bss_config *bss, | 
|  | 2270 | const char *pos) | 
|  | 2271 | { | 
|  | 2272 | struct dpp_controller_conf *conf; | 
|  | 2273 | char *val; | 
|  | 2274 |  | 
|  | 2275 | conf = os_zalloc(sizeof(*conf)); | 
|  | 2276 | if (!conf) | 
|  | 2277 | return -1; | 
|  | 2278 | val = get_param(pos, "ipaddr="); | 
|  | 2279 | if (!val || hostapd_parse_ip_addr(val, &conf->ipaddr)) | 
|  | 2280 | goto fail; | 
|  | 2281 | os_free(val); | 
|  | 2282 | val = get_param(pos, "pkhash="); | 
|  | 2283 | if (!val || os_strlen(val) != 2 * SHA256_MAC_LEN || | 
|  | 2284 | hexstr2bin(val, conf->pkhash, SHA256_MAC_LEN) < 0) | 
|  | 2285 | goto fail; | 
|  | 2286 | os_free(val); | 
|  | 2287 | conf->next = bss->dpp_controller; | 
|  | 2288 | bss->dpp_controller = conf; | 
|  | 2289 | return 0; | 
|  | 2290 | fail: | 
|  | 2291 | os_free(val); | 
|  | 2292 | os_free(conf); | 
|  | 2293 | return -1; | 
|  | 2294 | } | 
|  | 2295 | #endif /* CONFIG_DPP2 */ | 
|  | 2296 |  | 
|  | 2297 |  | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 2298 | static int get_hex_config(u8 *buf, size_t max_len, int line, | 
|  | 2299 | const char *field, const char *val) | 
|  | 2300 | { | 
|  | 2301 | size_t hlen = os_strlen(val), len = hlen / 2; | 
|  | 2302 | u8 tmp[EXT_CAPA_MAX_LEN]; | 
|  | 2303 |  | 
|  | 2304 | os_memset(tmp, 0, EXT_CAPA_MAX_LEN); | 
|  | 2305 | if (hlen & 1 || len > EXT_CAPA_MAX_LEN || hexstr2bin(val, tmp, len)) { | 
|  | 2306 | wpa_printf(MSG_ERROR, "Line %d: Invalid %s", line, field); | 
|  | 2307 | return -1; | 
|  | 2308 | } | 
|  | 2309 | os_memcpy(buf, tmp, EXT_CAPA_MAX_LEN); | 
|  | 2310 | return 0; | 
|  | 2311 | } | 
|  | 2312 |  | 
|  | 2313 |  | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 2314 | static int hostapd_config_fill(struct hostapd_config *conf, | 
|  | 2315 | struct hostapd_bss_config *bss, | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 2316 | const char *buf, char *pos, int line) | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 2317 | { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2318 | if (os_strcmp(buf, "interface") == 0) { | 
|  | 2319 | os_strlcpy(conf->bss[0]->iface, pos, | 
|  | 2320 | sizeof(conf->bss[0]->iface)); | 
|  | 2321 | } else if (os_strcmp(buf, "bridge") == 0) { | 
|  | 2322 | os_strlcpy(bss->bridge, pos, sizeof(bss->bridge)); | 
| Sunil Ravi | 036cec5 | 2023-03-29 11:35:17 -0700 | [diff] [blame] | 2323 | } else if (os_strcmp(buf, "bridge_hairpin") == 0) { | 
|  | 2324 | bss->bridge_hairpin = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2325 | } else if (os_strcmp(buf, "vlan_bridge") == 0) { | 
|  | 2326 | os_strlcpy(bss->vlan_bridge, pos, sizeof(bss->vlan_bridge)); | 
|  | 2327 | } else if (os_strcmp(buf, "wds_bridge") == 0) { | 
|  | 2328 | os_strlcpy(bss->wds_bridge, pos, sizeof(bss->wds_bridge)); | 
|  | 2329 | } else if (os_strcmp(buf, "driver") == 0) { | 
|  | 2330 | int j; | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2331 | const struct wpa_driver_ops *driver = NULL; | 
|  | 2332 |  | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2333 | for (j = 0; wpa_drivers[j]; j++) { | 
|  | 2334 | if (os_strcmp(pos, wpa_drivers[j]->name) == 0) { | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2335 | driver = wpa_drivers[j]; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2336 | break; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2337 | } | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2338 | } | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2339 | if (!driver) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2340 | wpa_printf(MSG_ERROR, | 
|  | 2341 | "Line %d: invalid/unknown driver '%s'", | 
|  | 2342 | line, pos); | 
|  | 2343 | return 1; | 
|  | 2344 | } | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2345 | conf->driver = driver; | 
| Dmitry Shmidt | 6c0da2b | 2015-01-05 13:08:17 -0800 | [diff] [blame] | 2346 | } else if (os_strcmp(buf, "driver_params") == 0) { | 
|  | 2347 | os_free(conf->driver_params); | 
|  | 2348 | conf->driver_params = os_strdup(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2349 | } else if (os_strcmp(buf, "debug") == 0) { | 
|  | 2350 | wpa_printf(MSG_DEBUG, "Line %d: DEPRECATED: 'debug' configuration variable is not used anymore", | 
|  | 2351 | line); | 
|  | 2352 | } else if (os_strcmp(buf, "logger_syslog_level") == 0) { | 
|  | 2353 | bss->logger_syslog_level = atoi(pos); | 
|  | 2354 | } else if (os_strcmp(buf, "logger_stdout_level") == 0) { | 
|  | 2355 | bss->logger_stdout_level = atoi(pos); | 
|  | 2356 | } else if (os_strcmp(buf, "logger_syslog") == 0) { | 
|  | 2357 | bss->logger_syslog = atoi(pos); | 
|  | 2358 | } else if (os_strcmp(buf, "logger_stdout") == 0) { | 
|  | 2359 | bss->logger_stdout = atoi(pos); | 
|  | 2360 | } else if (os_strcmp(buf, "dump_file") == 0) { | 
|  | 2361 | wpa_printf(MSG_INFO, "Line %d: DEPRECATED: 'dump_file' configuration variable is not used anymore", | 
|  | 2362 | line); | 
|  | 2363 | } else if (os_strcmp(buf, "ssid") == 0) { | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 2364 | struct hostapd_ssid *ssid = &bss->ssid; | 
|  | 2365 |  | 
|  | 2366 | ssid->ssid_len = os_strlen(pos); | 
|  | 2367 | if (ssid->ssid_len > SSID_MAX_LEN || ssid->ssid_len < 1) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2368 | wpa_printf(MSG_ERROR, "Line %d: invalid SSID '%s'", | 
|  | 2369 | line, pos); | 
|  | 2370 | return 1; | 
|  | 2371 | } | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 2372 | os_memcpy(ssid->ssid, pos, ssid->ssid_len); | 
|  | 2373 | ssid->ssid_set = 1; | 
| Sunil Ravi | 89eba10 | 2022-09-13 21:04:37 -0700 | [diff] [blame] | 2374 | ssid->short_ssid = ieee80211_crc32(ssid->ssid, ssid->ssid_len); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2375 | } else if (os_strcmp(buf, "ssid2") == 0) { | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 2376 | struct hostapd_ssid *ssid = &bss->ssid; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2377 | size_t slen; | 
|  | 2378 | char *str = wpa_config_parse_string(pos, &slen); | 
| Dmitry Shmidt | 9d9e602 | 2015-04-23 10:34:55 -0700 | [diff] [blame] | 2379 | if (str == NULL || slen < 1 || slen > SSID_MAX_LEN) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2380 | wpa_printf(MSG_ERROR, "Line %d: invalid SSID '%s'", | 
|  | 2381 | line, pos); | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 2382 | os_free(str); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2383 | return 1; | 
|  | 2384 | } | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 2385 | os_memcpy(ssid->ssid, str, slen); | 
|  | 2386 | ssid->ssid_len = slen; | 
|  | 2387 | ssid->ssid_set = 1; | 
| Sunil Ravi | 89eba10 | 2022-09-13 21:04:37 -0700 | [diff] [blame] | 2388 | ssid->short_ssid = ieee80211_crc32(ssid->ssid, ssid->ssid_len); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2389 | os_free(str); | 
|  | 2390 | } else if (os_strcmp(buf, "utf8_ssid") == 0) { | 
|  | 2391 | bss->ssid.utf8_ssid = atoi(pos) > 0; | 
|  | 2392 | } else if (os_strcmp(buf, "macaddr_acl") == 0) { | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2393 | enum macaddr_acl acl = atoi(pos); | 
|  | 2394 |  | 
|  | 2395 | if (acl != ACCEPT_UNLESS_DENIED && | 
|  | 2396 | acl != DENY_UNLESS_ACCEPTED && | 
|  | 2397 | acl != USE_EXTERNAL_RADIUS_AUTH) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2398 | wpa_printf(MSG_ERROR, "Line %d: unknown macaddr_acl %d", | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2399 | line, acl); | 
|  | 2400 | return 1; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2401 | } | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2402 | bss->macaddr_acl = acl; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2403 | } else if (os_strcmp(buf, "accept_mac_file") == 0) { | 
|  | 2404 | if (hostapd_config_read_maclist(pos, &bss->accept_mac, | 
|  | 2405 | &bss->num_accept_mac)) { | 
|  | 2406 | wpa_printf(MSG_ERROR, "Line %d: Failed to read accept_mac_file '%s'", | 
|  | 2407 | line, pos); | 
|  | 2408 | return 1; | 
|  | 2409 | } | 
|  | 2410 | } else if (os_strcmp(buf, "deny_mac_file") == 0) { | 
|  | 2411 | if (hostapd_config_read_maclist(pos, &bss->deny_mac, | 
|  | 2412 | &bss->num_deny_mac)) { | 
|  | 2413 | wpa_printf(MSG_ERROR, "Line %d: Failed to read deny_mac_file '%s'", | 
|  | 2414 | line, pos); | 
|  | 2415 | return 1; | 
|  | 2416 | } | 
|  | 2417 | } else if (os_strcmp(buf, "wds_sta") == 0) { | 
|  | 2418 | bss->wds_sta = atoi(pos); | 
|  | 2419 | } else if (os_strcmp(buf, "start_disabled") == 0) { | 
|  | 2420 | bss->start_disabled = atoi(pos); | 
|  | 2421 | } else if (os_strcmp(buf, "ap_isolate") == 0) { | 
|  | 2422 | bss->isolate = atoi(pos); | 
|  | 2423 | } else if (os_strcmp(buf, "ap_max_inactivity") == 0) { | 
|  | 2424 | bss->ap_max_inactivity = atoi(pos); | 
|  | 2425 | } else if (os_strcmp(buf, "skip_inactivity_poll") == 0) { | 
|  | 2426 | bss->skip_inactivity_poll = atoi(pos); | 
| Sunil Ravi | 77d572f | 2023-01-17 23:58:31 +0000 | [diff] [blame] | 2427 | } else if (os_strcmp(buf, "config_id") == 0) { | 
|  | 2428 | os_free(bss->config_id); | 
|  | 2429 | bss->config_id = os_strdup(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2430 | } else if (os_strcmp(buf, "country_code") == 0) { | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 2431 | if (pos[0] < 'A' || pos[0] > 'Z' || | 
|  | 2432 | pos[1] < 'A' || pos[1] > 'Z') { | 
|  | 2433 | wpa_printf(MSG_ERROR, | 
|  | 2434 | "Line %d: Invalid country_code '%s'", | 
|  | 2435 | line, pos); | 
|  | 2436 | return 1; | 
|  | 2437 | } | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2438 | os_memcpy(conf->country, pos, 2); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2439 | } else if (os_strcmp(buf, "country3") == 0) { | 
|  | 2440 | conf->country[2] = strtol(pos, NULL, 16); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2441 | } else if (os_strcmp(buf, "ieee80211d") == 0) { | 
|  | 2442 | conf->ieee80211d = atoi(pos); | 
|  | 2443 | } else if (os_strcmp(buf, "ieee80211h") == 0) { | 
|  | 2444 | conf->ieee80211h = atoi(pos); | 
|  | 2445 | } else if (os_strcmp(buf, "ieee8021x") == 0) { | 
|  | 2446 | bss->ieee802_1x = atoi(pos); | 
|  | 2447 | } else if (os_strcmp(buf, "eapol_version") == 0) { | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2448 | int eapol_version = atoi(pos); | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2449 | #ifdef CONFIG_MACSEC | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 2450 | int max_ver = 3; | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2451 | #else /* CONFIG_MACSEC */ | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 2452 | int max_ver = 2; | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2453 | #endif /* CONFIG_MACSEC */ | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 2454 |  | 
|  | 2455 | if (eapol_version < 1 || eapol_version > max_ver) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2456 | wpa_printf(MSG_ERROR, | 
|  | 2457 | "Line %d: invalid EAPOL version (%d): '%s'.", | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2458 | line, eapol_version, pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2459 | return 1; | 
|  | 2460 | } | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2461 | bss->eapol_version = eapol_version; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2462 | wpa_printf(MSG_DEBUG, "eapol_version=%d", bss->eapol_version); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2463 | #ifdef EAP_SERVER | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2464 | } else if (os_strcmp(buf, "eap_authenticator") == 0) { | 
|  | 2465 | bss->eap_server = atoi(pos); | 
|  | 2466 | wpa_printf(MSG_ERROR, "Line %d: obsolete eap_authenticator used; this has been renamed to eap_server", line); | 
|  | 2467 | } else if (os_strcmp(buf, "eap_server") == 0) { | 
|  | 2468 | bss->eap_server = atoi(pos); | 
|  | 2469 | } else if (os_strcmp(buf, "eap_user_file") == 0) { | 
|  | 2470 | if (hostapd_config_read_eap_user(pos, bss)) | 
|  | 2471 | return 1; | 
|  | 2472 | } else if (os_strcmp(buf, "ca_cert") == 0) { | 
|  | 2473 | os_free(bss->ca_cert); | 
|  | 2474 | bss->ca_cert = os_strdup(pos); | 
|  | 2475 | } else if (os_strcmp(buf, "server_cert") == 0) { | 
|  | 2476 | os_free(bss->server_cert); | 
|  | 2477 | bss->server_cert = os_strdup(pos); | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2478 | } else if (os_strcmp(buf, "server_cert2") == 0) { | 
|  | 2479 | os_free(bss->server_cert2); | 
|  | 2480 | bss->server_cert2 = os_strdup(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2481 | } else if (os_strcmp(buf, "private_key") == 0) { | 
|  | 2482 | os_free(bss->private_key); | 
|  | 2483 | bss->private_key = os_strdup(pos); | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2484 | } else if (os_strcmp(buf, "private_key2") == 0) { | 
|  | 2485 | os_free(bss->private_key2); | 
|  | 2486 | bss->private_key2 = os_strdup(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2487 | } else if (os_strcmp(buf, "private_key_passwd") == 0) { | 
|  | 2488 | os_free(bss->private_key_passwd); | 
|  | 2489 | bss->private_key_passwd = os_strdup(pos); | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2490 | } else if (os_strcmp(buf, "private_key_passwd2") == 0) { | 
|  | 2491 | os_free(bss->private_key_passwd2); | 
|  | 2492 | bss->private_key_passwd2 = os_strdup(pos); | 
| Hai Shalom | 021b0b5 | 2019-04-10 11:17:58 -0700 | [diff] [blame] | 2493 | } else if (os_strcmp(buf, "check_cert_subject") == 0) { | 
|  | 2494 | if (!pos[0]) { | 
|  | 2495 | wpa_printf(MSG_ERROR, "Line %d: unknown check_cert_subject '%s'", | 
|  | 2496 | line, pos); | 
|  | 2497 | return 1; | 
|  | 2498 | } | 
|  | 2499 | os_free(bss->check_cert_subject); | 
|  | 2500 | bss->check_cert_subject = os_strdup(pos); | 
|  | 2501 | if (!bss->check_cert_subject) | 
|  | 2502 | return 1; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2503 | } else if (os_strcmp(buf, "check_crl") == 0) { | 
|  | 2504 | bss->check_crl = atoi(pos); | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 2505 | } else if (os_strcmp(buf, "check_crl_strict") == 0) { | 
|  | 2506 | bss->check_crl_strict = atoi(pos); | 
|  | 2507 | } else if (os_strcmp(buf, "crl_reload_interval") == 0) { | 
|  | 2508 | bss->crl_reload_interval = atoi(pos); | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 2509 | } else if (os_strcmp(buf, "tls_session_lifetime") == 0) { | 
|  | 2510 | bss->tls_session_lifetime = atoi(pos); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2511 | } else if (os_strcmp(buf, "tls_flags") == 0) { | 
|  | 2512 | bss->tls_flags = parse_tls_flags(pos); | 
| Hai Shalom | c356592 | 2019-10-28 11:58:20 -0700 | [diff] [blame] | 2513 | } else if (os_strcmp(buf, "max_auth_rounds") == 0) { | 
|  | 2514 | bss->max_auth_rounds = atoi(pos); | 
|  | 2515 | } else if (os_strcmp(buf, "max_auth_rounds_short") == 0) { | 
|  | 2516 | bss->max_auth_rounds_short = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2517 | } else if (os_strcmp(buf, "ocsp_stapling_response") == 0) { | 
|  | 2518 | os_free(bss->ocsp_stapling_response); | 
|  | 2519 | bss->ocsp_stapling_response = os_strdup(pos); | 
| Dmitry Shmidt | 014a3ff | 2015-12-28 13:27:49 -0800 | [diff] [blame] | 2520 | } else if (os_strcmp(buf, "ocsp_stapling_response_multi") == 0) { | 
|  | 2521 | os_free(bss->ocsp_stapling_response_multi); | 
|  | 2522 | bss->ocsp_stapling_response_multi = os_strdup(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2523 | } else if (os_strcmp(buf, "dh_file") == 0) { | 
|  | 2524 | os_free(bss->dh_file); | 
|  | 2525 | bss->dh_file = os_strdup(pos); | 
| Dmitry Shmidt | 6c0da2b | 2015-01-05 13:08:17 -0800 | [diff] [blame] | 2526 | } else if (os_strcmp(buf, "openssl_ciphers") == 0) { | 
|  | 2527 | os_free(bss->openssl_ciphers); | 
|  | 2528 | bss->openssl_ciphers = os_strdup(pos); | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 2529 | } else if (os_strcmp(buf, "openssl_ecdh_curves") == 0) { | 
|  | 2530 | os_free(bss->openssl_ecdh_curves); | 
|  | 2531 | bss->openssl_ecdh_curves = os_strdup(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2532 | } else if (os_strcmp(buf, "fragment_size") == 0) { | 
|  | 2533 | bss->fragment_size = atoi(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2534 | #ifdef EAP_SERVER_FAST | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2535 | } else if (os_strcmp(buf, "pac_opaque_encr_key") == 0) { | 
|  | 2536 | os_free(bss->pac_opaque_encr_key); | 
|  | 2537 | bss->pac_opaque_encr_key = os_malloc(16); | 
|  | 2538 | if (bss->pac_opaque_encr_key == NULL) { | 
|  | 2539 | wpa_printf(MSG_ERROR, | 
|  | 2540 | "Line %d: No memory for pac_opaque_encr_key", | 
|  | 2541 | line); | 
|  | 2542 | return 1; | 
|  | 2543 | } else if (hexstr2bin(pos, bss->pac_opaque_encr_key, 16)) { | 
|  | 2544 | wpa_printf(MSG_ERROR, "Line %d: Invalid pac_opaque_encr_key", | 
|  | 2545 | line); | 
|  | 2546 | return 1; | 
|  | 2547 | } | 
|  | 2548 | } else if (os_strcmp(buf, "eap_fast_a_id") == 0) { | 
|  | 2549 | size_t idlen = os_strlen(pos); | 
|  | 2550 | if (idlen & 1) { | 
|  | 2551 | wpa_printf(MSG_ERROR, "Line %d: Invalid eap_fast_a_id", | 
|  | 2552 | line); | 
|  | 2553 | return 1; | 
|  | 2554 | } | 
|  | 2555 | os_free(bss->eap_fast_a_id); | 
|  | 2556 | bss->eap_fast_a_id = os_malloc(idlen / 2); | 
|  | 2557 | if (bss->eap_fast_a_id == NULL || | 
|  | 2558 | hexstr2bin(pos, bss->eap_fast_a_id, idlen / 2)) { | 
|  | 2559 | wpa_printf(MSG_ERROR, "Line %d: Failed to parse eap_fast_a_id", | 
|  | 2560 | line); | 
|  | 2561 | os_free(bss->eap_fast_a_id); | 
|  | 2562 | bss->eap_fast_a_id = NULL; | 
|  | 2563 | return 1; | 
|  | 2564 | } else { | 
|  | 2565 | bss->eap_fast_a_id_len = idlen / 2; | 
|  | 2566 | } | 
|  | 2567 | } else if (os_strcmp(buf, "eap_fast_a_id_info") == 0) { | 
|  | 2568 | os_free(bss->eap_fast_a_id_info); | 
|  | 2569 | bss->eap_fast_a_id_info = os_strdup(pos); | 
|  | 2570 | } else if (os_strcmp(buf, "eap_fast_prov") == 0) { | 
|  | 2571 | bss->eap_fast_prov = atoi(pos); | 
|  | 2572 | } else if (os_strcmp(buf, "pac_key_lifetime") == 0) { | 
|  | 2573 | bss->pac_key_lifetime = atoi(pos); | 
|  | 2574 | } else if (os_strcmp(buf, "pac_key_refresh_time") == 0) { | 
|  | 2575 | bss->pac_key_refresh_time = atoi(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2576 | #endif /* EAP_SERVER_FAST */ | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2577 | #ifdef EAP_SERVER_TEAP | 
|  | 2578 | } else if (os_strcmp(buf, "eap_teap_auth") == 0) { | 
|  | 2579 | int val = atoi(pos); | 
|  | 2580 |  | 
| Hai Shalom | 899fcc7 | 2020-10-19 14:38:18 -0700 | [diff] [blame] | 2581 | if (val < 0 || val > 2) { | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2582 | wpa_printf(MSG_ERROR, | 
|  | 2583 | "Line %d: Invalid eap_teap_auth value", | 
|  | 2584 | line); | 
|  | 2585 | return 1; | 
|  | 2586 | } | 
|  | 2587 | bss->eap_teap_auth = val; | 
|  | 2588 | } else if (os_strcmp(buf, "eap_teap_pac_no_inner") == 0) { | 
|  | 2589 | bss->eap_teap_pac_no_inner = atoi(pos); | 
| Hai Shalom | c356592 | 2019-10-28 11:58:20 -0700 | [diff] [blame] | 2590 | } else if (os_strcmp(buf, "eap_teap_separate_result") == 0) { | 
|  | 2591 | bss->eap_teap_separate_result = atoi(pos); | 
|  | 2592 | } else if (os_strcmp(buf, "eap_teap_id") == 0) { | 
|  | 2593 | bss->eap_teap_id = atoi(pos); | 
| Sunil Ravi | 77d572f | 2023-01-17 23:58:31 +0000 | [diff] [blame] | 2594 | } else if (os_strcmp(buf, "eap_teap_method_sequence") == 0) { | 
|  | 2595 | bss->eap_teap_method_sequence = atoi(pos); | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 2596 | #endif /* EAP_SERVER_TEAP */ | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2597 | #ifdef EAP_SERVER_SIM | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2598 | } else if (os_strcmp(buf, "eap_sim_db") == 0) { | 
|  | 2599 | os_free(bss->eap_sim_db); | 
|  | 2600 | bss->eap_sim_db = os_strdup(pos); | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 2601 | } else if (os_strcmp(buf, "eap_sim_db_timeout") == 0) { | 
|  | 2602 | bss->eap_sim_db_timeout = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2603 | } else if (os_strcmp(buf, "eap_sim_aka_result_ind") == 0) { | 
|  | 2604 | bss->eap_sim_aka_result_ind = atoi(pos); | 
| Hai Shalom | c356592 | 2019-10-28 11:58:20 -0700 | [diff] [blame] | 2605 | } else if (os_strcmp(buf, "eap_sim_id") == 0) { | 
|  | 2606 | bss->eap_sim_id = atoi(pos); | 
| Sunil Ravi | a04bd25 | 2022-05-02 22:54:18 -0700 | [diff] [blame] | 2607 | } else if (os_strcmp(buf, "imsi_privacy_key") == 0) { | 
|  | 2608 | os_free(bss->imsi_privacy_key); | 
|  | 2609 | bss->imsi_privacy_key = os_strdup(pos); | 
| Sunil Ravi | 2a14cf1 | 2023-11-21 00:54:38 +0000 | [diff] [blame] | 2610 | } else if (os_strcmp(buf, "eap_sim_aka_fast_reauth_limit") == 0) { | 
|  | 2611 | bss->eap_sim_aka_fast_reauth_limit = atoi(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2612 | #endif /* EAP_SERVER_SIM */ | 
|  | 2613 | #ifdef EAP_SERVER_TNC | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2614 | } else if (os_strcmp(buf, "tnc") == 0) { | 
|  | 2615 | bss->tnc = atoi(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2616 | #endif /* EAP_SERVER_TNC */ | 
|  | 2617 | #ifdef EAP_SERVER_PWD | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2618 | } else if (os_strcmp(buf, "pwd_group") == 0) { | 
|  | 2619 | bss->pwd_group = atoi(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2620 | #endif /* EAP_SERVER_PWD */ | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 2621 | #ifdef CONFIG_ERP | 
| Dmitry Shmidt | 6c0da2b | 2015-01-05 13:08:17 -0800 | [diff] [blame] | 2622 | } else if (os_strcmp(buf, "eap_server_erp") == 0) { | 
|  | 2623 | bss->eap_server_erp = atoi(pos); | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 2624 | #endif /* CONFIG_ERP */ | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2625 | #endif /* EAP_SERVER */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2626 | } else if (os_strcmp(buf, "eap_message") == 0) { | 
|  | 2627 | char *term; | 
| Dmitry Shmidt | 21de214 | 2014-04-08 10:50:52 -0700 | [diff] [blame] | 2628 | os_free(bss->eap_req_id_text); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2629 | bss->eap_req_id_text = os_strdup(pos); | 
|  | 2630 | if (bss->eap_req_id_text == NULL) { | 
|  | 2631 | wpa_printf(MSG_ERROR, "Line %d: Failed to allocate memory for eap_req_id_text", | 
|  | 2632 | line); | 
|  | 2633 | return 1; | 
|  | 2634 | } | 
|  | 2635 | bss->eap_req_id_text_len = os_strlen(bss->eap_req_id_text); | 
|  | 2636 | term = os_strstr(bss->eap_req_id_text, "\\0"); | 
|  | 2637 | if (term) { | 
|  | 2638 | *term++ = '\0'; | 
|  | 2639 | os_memmove(term, term + 1, | 
|  | 2640 | bss->eap_req_id_text_len - | 
|  | 2641 | (term - bss->eap_req_id_text) - 1); | 
|  | 2642 | bss->eap_req_id_text_len--; | 
|  | 2643 | } | 
| Dmitry Shmidt | 6c0da2b | 2015-01-05 13:08:17 -0800 | [diff] [blame] | 2644 | } else if (os_strcmp(buf, "erp_send_reauth_start") == 0) { | 
|  | 2645 | bss->erp_send_reauth_start = atoi(pos); | 
|  | 2646 | } else if (os_strcmp(buf, "erp_domain") == 0) { | 
|  | 2647 | os_free(bss->erp_domain); | 
|  | 2648 | bss->erp_domain = os_strdup(pos); | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 2649 | #ifdef CONFIG_WEP | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2650 | } else if (os_strcmp(buf, "wep_key_len_broadcast") == 0) { | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2651 | int val = atoi(pos); | 
|  | 2652 |  | 
|  | 2653 | if (val < 0 || val > 13) { | 
|  | 2654 | wpa_printf(MSG_ERROR, | 
|  | 2655 | "Line %d: invalid WEP key len %d (= %d bits)", | 
|  | 2656 | line, val, val * 8); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2657 | return 1; | 
|  | 2658 | } | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2659 | bss->default_wep_key_len = val; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2660 | } else if (os_strcmp(buf, "wep_key_len_unicast") == 0) { | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2661 | int val = atoi(pos); | 
|  | 2662 |  | 
|  | 2663 | if (val < 0 || val > 13) { | 
|  | 2664 | wpa_printf(MSG_ERROR, | 
|  | 2665 | "Line %d: invalid WEP key len %d (= %d bits)", | 
|  | 2666 | line, val, val * 8); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2667 | return 1; | 
|  | 2668 | } | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 2669 | bss->individual_wep_key_len = val; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2670 | } else if (os_strcmp(buf, "wep_rekey_period") == 0) { | 
|  | 2671 | bss->wep_rekeying_period = atoi(pos); | 
|  | 2672 | if (bss->wep_rekeying_period < 0) { | 
|  | 2673 | wpa_printf(MSG_ERROR, "Line %d: invalid period %d", | 
|  | 2674 | line, bss->wep_rekeying_period); | 
|  | 2675 | return 1; | 
|  | 2676 | } | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 2677 | #endif /* CONFIG_WEP */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2678 | } else if (os_strcmp(buf, "eap_reauth_period") == 0) { | 
|  | 2679 | bss->eap_reauth_period = atoi(pos); | 
|  | 2680 | if (bss->eap_reauth_period < 0) { | 
|  | 2681 | wpa_printf(MSG_ERROR, "Line %d: invalid period %d", | 
|  | 2682 | line, bss->eap_reauth_period); | 
|  | 2683 | return 1; | 
|  | 2684 | } | 
|  | 2685 | } else if (os_strcmp(buf, "eapol_key_index_workaround") == 0) { | 
|  | 2686 | bss->eapol_key_index_workaround = atoi(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2687 | #ifdef CONFIG_IAPP | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2688 | } else if (os_strcmp(buf, "iapp_interface") == 0) { | 
| Hai Shalom | c356592 | 2019-10-28 11:58:20 -0700 | [diff] [blame] | 2689 | wpa_printf(MSG_INFO, "DEPRECATED: iapp_interface not used"); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2690 | #endif /* CONFIG_IAPP */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2691 | } else if (os_strcmp(buf, "own_ip_addr") == 0) { | 
|  | 2692 | if (hostapd_parse_ip_addr(pos, &bss->own_ip_addr)) { | 
|  | 2693 | wpa_printf(MSG_ERROR, | 
|  | 2694 | "Line %d: invalid IP address '%s'", | 
|  | 2695 | line, pos); | 
|  | 2696 | return 1; | 
|  | 2697 | } | 
|  | 2698 | } else if (os_strcmp(buf, "nas_identifier") == 0) { | 
| Dmitry Shmidt | 21de214 | 2014-04-08 10:50:52 -0700 | [diff] [blame] | 2699 | os_free(bss->nas_identifier); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2700 | bss->nas_identifier = os_strdup(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2701 | #ifndef CONFIG_NO_RADIUS | 
| Dmitry Shmidt | 203eadb | 2015-03-05 14:16:04 -0800 | [diff] [blame] | 2702 | } else if (os_strcmp(buf, "radius_client_addr") == 0) { | 
|  | 2703 | if (hostapd_parse_ip_addr(pos, &bss->radius->client_addr)) { | 
|  | 2704 | wpa_printf(MSG_ERROR, | 
|  | 2705 | "Line %d: invalid IP address '%s'", | 
|  | 2706 | line, pos); | 
|  | 2707 | return 1; | 
|  | 2708 | } | 
|  | 2709 | bss->radius->force_client_addr = 1; | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 2710 | } else if (os_strcmp(buf, "radius_client_dev") == 0) { | 
|  | 2711 | os_free(bss->radius->force_client_dev); | 
|  | 2712 | bss->radius->force_client_dev = os_strdup(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2713 | } else if (os_strcmp(buf, "auth_server_addr") == 0) { | 
|  | 2714 | if (hostapd_config_read_radius_addr( | 
|  | 2715 | &bss->radius->auth_servers, | 
|  | 2716 | &bss->radius->num_auth_servers, pos, 1812, | 
|  | 2717 | &bss->radius->auth_server)) { | 
|  | 2718 | wpa_printf(MSG_ERROR, | 
|  | 2719 | "Line %d: invalid IP address '%s'", | 
|  | 2720 | line, pos); | 
|  | 2721 | return 1; | 
|  | 2722 | } | 
|  | 2723 | } else if (bss->radius->auth_server && | 
| Dmitry Shmidt | 203eadb | 2015-03-05 14:16:04 -0800 | [diff] [blame] | 2724 | os_strcmp(buf, "auth_server_addr_replace") == 0) { | 
|  | 2725 | if (hostapd_parse_ip_addr(pos, | 
|  | 2726 | &bss->radius->auth_server->addr)) { | 
|  | 2727 | wpa_printf(MSG_ERROR, | 
|  | 2728 | "Line %d: invalid IP address '%s'", | 
|  | 2729 | line, pos); | 
|  | 2730 | return 1; | 
|  | 2731 | } | 
|  | 2732 | } else if (bss->radius->auth_server && | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2733 | os_strcmp(buf, "auth_server_port") == 0) { | 
|  | 2734 | bss->radius->auth_server->port = atoi(pos); | 
|  | 2735 | } else if (bss->radius->auth_server && | 
|  | 2736 | os_strcmp(buf, "auth_server_shared_secret") == 0) { | 
|  | 2737 | int len = os_strlen(pos); | 
|  | 2738 | if (len == 0) { | 
|  | 2739 | /* RFC 2865, Ch. 3 */ | 
|  | 2740 | wpa_printf(MSG_ERROR, "Line %d: empty shared secret is not allowed", | 
|  | 2741 | line); | 
|  | 2742 | return 1; | 
|  | 2743 | } | 
| Dmitry Shmidt | 21de214 | 2014-04-08 10:50:52 -0700 | [diff] [blame] | 2744 | os_free(bss->radius->auth_server->shared_secret); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2745 | bss->radius->auth_server->shared_secret = (u8 *) os_strdup(pos); | 
|  | 2746 | bss->radius->auth_server->shared_secret_len = len; | 
|  | 2747 | } else if (os_strcmp(buf, "acct_server_addr") == 0) { | 
|  | 2748 | if (hostapd_config_read_radius_addr( | 
|  | 2749 | &bss->radius->acct_servers, | 
|  | 2750 | &bss->radius->num_acct_servers, pos, 1813, | 
|  | 2751 | &bss->radius->acct_server)) { | 
|  | 2752 | wpa_printf(MSG_ERROR, | 
|  | 2753 | "Line %d: invalid IP address '%s'", | 
|  | 2754 | line, pos); | 
|  | 2755 | return 1; | 
|  | 2756 | } | 
|  | 2757 | } else if (bss->radius->acct_server && | 
| Dmitry Shmidt | 203eadb | 2015-03-05 14:16:04 -0800 | [diff] [blame] | 2758 | os_strcmp(buf, "acct_server_addr_replace") == 0) { | 
|  | 2759 | if (hostapd_parse_ip_addr(pos, | 
|  | 2760 | &bss->radius->acct_server->addr)) { | 
|  | 2761 | wpa_printf(MSG_ERROR, | 
|  | 2762 | "Line %d: invalid IP address '%s'", | 
|  | 2763 | line, pos); | 
|  | 2764 | return 1; | 
|  | 2765 | } | 
|  | 2766 | } else if (bss->radius->acct_server && | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2767 | os_strcmp(buf, "acct_server_port") == 0) { | 
|  | 2768 | bss->radius->acct_server->port = atoi(pos); | 
|  | 2769 | } else if (bss->radius->acct_server && | 
|  | 2770 | os_strcmp(buf, "acct_server_shared_secret") == 0) { | 
|  | 2771 | int len = os_strlen(pos); | 
|  | 2772 | if (len == 0) { | 
|  | 2773 | /* RFC 2865, Ch. 3 */ | 
|  | 2774 | wpa_printf(MSG_ERROR, "Line %d: empty shared secret is not allowed", | 
|  | 2775 | line); | 
|  | 2776 | return 1; | 
|  | 2777 | } | 
| Dmitry Shmidt | 21de214 | 2014-04-08 10:50:52 -0700 | [diff] [blame] | 2778 | os_free(bss->radius->acct_server->shared_secret); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2779 | bss->radius->acct_server->shared_secret = (u8 *) os_strdup(pos); | 
|  | 2780 | bss->radius->acct_server->shared_secret_len = len; | 
|  | 2781 | } else if (os_strcmp(buf, "radius_retry_primary_interval") == 0) { | 
|  | 2782 | bss->radius->retry_primary_interval = atoi(pos); | 
|  | 2783 | } else if (os_strcmp(buf, "radius_acct_interim_interval") == 0) { | 
|  | 2784 | bss->acct_interim_interval = atoi(pos); | 
|  | 2785 | } else if (os_strcmp(buf, "radius_request_cui") == 0) { | 
|  | 2786 | bss->radius_request_cui = atoi(pos); | 
|  | 2787 | } else if (os_strcmp(buf, "radius_auth_req_attr") == 0) { | 
|  | 2788 | struct hostapd_radius_attr *attr, *a; | 
|  | 2789 | attr = hostapd_parse_radius_attr(pos); | 
|  | 2790 | if (attr == NULL) { | 
|  | 2791 | wpa_printf(MSG_ERROR, | 
|  | 2792 | "Line %d: invalid radius_auth_req_attr", | 
|  | 2793 | line); | 
|  | 2794 | return 1; | 
|  | 2795 | } else if (bss->radius_auth_req_attr == NULL) { | 
|  | 2796 | bss->radius_auth_req_attr = attr; | 
|  | 2797 | } else { | 
|  | 2798 | a = bss->radius_auth_req_attr; | 
|  | 2799 | while (a->next) | 
|  | 2800 | a = a->next; | 
|  | 2801 | a->next = attr; | 
|  | 2802 | } | 
|  | 2803 | } else if (os_strcmp(buf, "radius_acct_req_attr") == 0) { | 
|  | 2804 | struct hostapd_radius_attr *attr, *a; | 
|  | 2805 | attr = hostapd_parse_radius_attr(pos); | 
|  | 2806 | if (attr == NULL) { | 
|  | 2807 | wpa_printf(MSG_ERROR, | 
|  | 2808 | "Line %d: invalid radius_acct_req_attr", | 
|  | 2809 | line); | 
|  | 2810 | return 1; | 
|  | 2811 | } else if (bss->radius_acct_req_attr == NULL) { | 
|  | 2812 | bss->radius_acct_req_attr = attr; | 
|  | 2813 | } else { | 
|  | 2814 | a = bss->radius_acct_req_attr; | 
|  | 2815 | while (a->next) | 
|  | 2816 | a = a->next; | 
|  | 2817 | a->next = attr; | 
|  | 2818 | } | 
| Hai Shalom | c356592 | 2019-10-28 11:58:20 -0700 | [diff] [blame] | 2819 | } else if (os_strcmp(buf, "radius_req_attr_sqlite") == 0) { | 
|  | 2820 | os_free(bss->radius_req_attr_sqlite); | 
|  | 2821 | bss->radius_req_attr_sqlite = os_strdup(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2822 | } else if (os_strcmp(buf, "radius_das_port") == 0) { | 
|  | 2823 | bss->radius_das_port = atoi(pos); | 
|  | 2824 | } else if (os_strcmp(buf, "radius_das_client") == 0) { | 
|  | 2825 | if (hostapd_parse_das_client(bss, pos) < 0) { | 
|  | 2826 | wpa_printf(MSG_ERROR, "Line %d: invalid DAS client", | 
|  | 2827 | line); | 
|  | 2828 | return 1; | 
|  | 2829 | } | 
|  | 2830 | } else if (os_strcmp(buf, "radius_das_time_window") == 0) { | 
|  | 2831 | bss->radius_das_time_window = atoi(pos); | 
|  | 2832 | } else if (os_strcmp(buf, "radius_das_require_event_timestamp") == 0) { | 
|  | 2833 | bss->radius_das_require_event_timestamp = atoi(pos); | 
| Dmitry Shmidt | 7f2c753 | 2016-08-15 09:48:12 -0700 | [diff] [blame] | 2834 | } else if (os_strcmp(buf, "radius_das_require_message_authenticator") == | 
|  | 2835 | 0) { | 
|  | 2836 | bss->radius_das_require_message_authenticator = atoi(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2837 | #endif /* CONFIG_NO_RADIUS */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2838 | } else if (os_strcmp(buf, "auth_algs") == 0) { | 
|  | 2839 | bss->auth_algs = atoi(pos); | 
|  | 2840 | if (bss->auth_algs == 0) { | 
|  | 2841 | wpa_printf(MSG_ERROR, "Line %d: no authentication algorithms allowed", | 
|  | 2842 | line); | 
|  | 2843 | return 1; | 
|  | 2844 | } | 
|  | 2845 | } else if (os_strcmp(buf, "max_num_sta") == 0) { | 
|  | 2846 | bss->max_num_sta = atoi(pos); | 
|  | 2847 | if (bss->max_num_sta < 0 || | 
|  | 2848 | bss->max_num_sta > MAX_STA_COUNT) { | 
|  | 2849 | wpa_printf(MSG_ERROR, "Line %d: Invalid max_num_sta=%d; allowed range 0..%d", | 
|  | 2850 | line, bss->max_num_sta, MAX_STA_COUNT); | 
|  | 2851 | return 1; | 
|  | 2852 | } | 
|  | 2853 | } else if (os_strcmp(buf, "wpa") == 0) { | 
|  | 2854 | bss->wpa = atoi(pos); | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 2855 | } else if (os_strcmp(buf, "extended_key_id") == 0) { | 
|  | 2856 | int val = atoi(pos); | 
|  | 2857 |  | 
|  | 2858 | if (val < 0 || val > 2) { | 
|  | 2859 | wpa_printf(MSG_ERROR, | 
|  | 2860 | "Line %d: Invalid extended_key_id=%d; allowed range 0..2", | 
|  | 2861 | line, val); | 
|  | 2862 | return 1; | 
|  | 2863 | } | 
|  | 2864 | bss->extended_key_id = val; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2865 | } else if (os_strcmp(buf, "wpa_group_rekey") == 0) { | 
|  | 2866 | bss->wpa_group_rekey = atoi(pos); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2867 | bss->wpa_group_rekey_set = 1; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2868 | } else if (os_strcmp(buf, "wpa_strict_rekey") == 0) { | 
|  | 2869 | bss->wpa_strict_rekey = atoi(pos); | 
|  | 2870 | } else if (os_strcmp(buf, "wpa_gmk_rekey") == 0) { | 
|  | 2871 | bss->wpa_gmk_rekey = atoi(pos); | 
|  | 2872 | } else if (os_strcmp(buf, "wpa_ptk_rekey") == 0) { | 
|  | 2873 | bss->wpa_ptk_rekey = atoi(pos); | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 2874 | } else if (os_strcmp(buf, "wpa_deny_ptk0_rekey") == 0) { | 
|  | 2875 | bss->wpa_deny_ptk0_rekey = atoi(pos); | 
|  | 2876 | if (bss->wpa_deny_ptk0_rekey < 0 || | 
|  | 2877 | bss->wpa_deny_ptk0_rekey > 2) { | 
|  | 2878 | wpa_printf(MSG_ERROR, | 
|  | 2879 | "Line %d: Invalid wpa_deny_ptk0_rekey=%d; allowed range 0..2", | 
|  | 2880 | line, bss->wpa_deny_ptk0_rekey); | 
|  | 2881 | return 1; | 
|  | 2882 | } | 
| Dmitry Shmidt | ebd93af | 2017-02-21 13:40:44 -0800 | [diff] [blame] | 2883 | } else if (os_strcmp(buf, "wpa_group_update_count") == 0) { | 
|  | 2884 | char *endp; | 
|  | 2885 | unsigned long val = strtoul(pos, &endp, 0); | 
|  | 2886 |  | 
|  | 2887 | if (*endp || val < 1 || val > (u32) -1) { | 
|  | 2888 | wpa_printf(MSG_ERROR, | 
|  | 2889 | "Line %d: Invalid wpa_group_update_count=%lu; allowed range 1..4294967295", | 
|  | 2890 | line, val); | 
|  | 2891 | return 1; | 
|  | 2892 | } | 
|  | 2893 | bss->wpa_group_update_count = (u32) val; | 
|  | 2894 | } else if (os_strcmp(buf, "wpa_pairwise_update_count") == 0) { | 
|  | 2895 | char *endp; | 
|  | 2896 | unsigned long val = strtoul(pos, &endp, 0); | 
|  | 2897 |  | 
|  | 2898 | if (*endp || val < 1 || val > (u32) -1) { | 
|  | 2899 | wpa_printf(MSG_ERROR, | 
|  | 2900 | "Line %d: Invalid wpa_pairwise_update_count=%lu; allowed range 1..4294967295", | 
|  | 2901 | line, val); | 
|  | 2902 | return 1; | 
|  | 2903 | } | 
|  | 2904 | bss->wpa_pairwise_update_count = (u32) val; | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2905 | } else if (os_strcmp(buf, "wpa_disable_eapol_key_retries") == 0) { | 
|  | 2906 | bss->wpa_disable_eapol_key_retries = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2907 | } else if (os_strcmp(buf, "wpa_passphrase") == 0) { | 
|  | 2908 | int len = os_strlen(pos); | 
|  | 2909 | if (len < 8 || len > 63) { | 
|  | 2910 | wpa_printf(MSG_ERROR, "Line %d: invalid WPA passphrase length %d (expected 8..63)", | 
|  | 2911 | line, len); | 
|  | 2912 | return 1; | 
|  | 2913 | } | 
|  | 2914 | os_free(bss->ssid.wpa_passphrase); | 
|  | 2915 | bss->ssid.wpa_passphrase = os_strdup(pos); | 
|  | 2916 | if (bss->ssid.wpa_passphrase) { | 
| Dmitry Shmidt | 7f65602 | 2015-02-25 14:36:37 -0800 | [diff] [blame] | 2917 | hostapd_config_clear_wpa_psk(&bss->ssid.wpa_psk); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2918 | bss->ssid.wpa_passphrase_set = 1; | 
|  | 2919 | } | 
|  | 2920 | } else if (os_strcmp(buf, "wpa_psk") == 0) { | 
| Dmitry Shmidt | 7f65602 | 2015-02-25 14:36:37 -0800 | [diff] [blame] | 2921 | hostapd_config_clear_wpa_psk(&bss->ssid.wpa_psk); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2922 | bss->ssid.wpa_psk = os_zalloc(sizeof(struct hostapd_wpa_psk)); | 
|  | 2923 | if (bss->ssid.wpa_psk == NULL) | 
|  | 2924 | return 1; | 
|  | 2925 | if (hexstr2bin(pos, bss->ssid.wpa_psk->psk, PMK_LEN) || | 
|  | 2926 | pos[PMK_LEN * 2] != '\0') { | 
|  | 2927 | wpa_printf(MSG_ERROR, "Line %d: Invalid PSK '%s'.", | 
|  | 2928 | line, pos); | 
| Dmitry Shmidt | 7f65602 | 2015-02-25 14:36:37 -0800 | [diff] [blame] | 2929 | hostapd_config_clear_wpa_psk(&bss->ssid.wpa_psk); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2930 | return 1; | 
|  | 2931 | } | 
|  | 2932 | bss->ssid.wpa_psk->group = 1; | 
|  | 2933 | os_free(bss->ssid.wpa_passphrase); | 
|  | 2934 | bss->ssid.wpa_passphrase = NULL; | 
|  | 2935 | bss->ssid.wpa_psk_set = 1; | 
|  | 2936 | } else if (os_strcmp(buf, "wpa_psk_file") == 0) { | 
|  | 2937 | os_free(bss->ssid.wpa_psk_file); | 
|  | 2938 | bss->ssid.wpa_psk_file = os_strdup(pos); | 
|  | 2939 | if (!bss->ssid.wpa_psk_file) { | 
|  | 2940 | wpa_printf(MSG_ERROR, "Line %d: allocation failed", | 
|  | 2941 | line); | 
|  | 2942 | return 1; | 
|  | 2943 | } | 
|  | 2944 | } else if (os_strcmp(buf, "wpa_key_mgmt") == 0) { | 
|  | 2945 | bss->wpa_key_mgmt = hostapd_config_parse_key_mgmt(line, pos); | 
|  | 2946 | if (bss->wpa_key_mgmt == -1) | 
|  | 2947 | return 1; | 
|  | 2948 | } else if (os_strcmp(buf, "wpa_psk_radius") == 0) { | 
|  | 2949 | bss->wpa_psk_radius = atoi(pos); | 
|  | 2950 | if (bss->wpa_psk_radius != PSK_RADIUS_IGNORED && | 
|  | 2951 | bss->wpa_psk_radius != PSK_RADIUS_ACCEPTED && | 
| Sunil Ravi | a04bd25 | 2022-05-02 22:54:18 -0700 | [diff] [blame] | 2952 | bss->wpa_psk_radius != PSK_RADIUS_REQUIRED && | 
|  | 2953 | bss->wpa_psk_radius != PSK_RADIUS_DURING_4WAY_HS) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2954 | wpa_printf(MSG_ERROR, | 
|  | 2955 | "Line %d: unknown wpa_psk_radius %d", | 
|  | 2956 | line, bss->wpa_psk_radius); | 
|  | 2957 | return 1; | 
|  | 2958 | } | 
|  | 2959 | } else if (os_strcmp(buf, "wpa_pairwise") == 0) { | 
|  | 2960 | bss->wpa_pairwise = hostapd_config_parse_cipher(line, pos); | 
|  | 2961 | if (bss->wpa_pairwise == -1 || bss->wpa_pairwise == 0) | 
|  | 2962 | return 1; | 
|  | 2963 | if (bss->wpa_pairwise & | 
|  | 2964 | (WPA_CIPHER_NONE | WPA_CIPHER_WEP40 | WPA_CIPHER_WEP104)) { | 
|  | 2965 | wpa_printf(MSG_ERROR, "Line %d: unsupported pairwise cipher suite '%s'", | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2966 | line, pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2967 | return 1; | 
|  | 2968 | } | 
|  | 2969 | } else if (os_strcmp(buf, "rsn_pairwise") == 0) { | 
|  | 2970 | bss->rsn_pairwise = hostapd_config_parse_cipher(line, pos); | 
|  | 2971 | if (bss->rsn_pairwise == -1 || bss->rsn_pairwise == 0) | 
|  | 2972 | return 1; | 
|  | 2973 | if (bss->rsn_pairwise & | 
|  | 2974 | (WPA_CIPHER_NONE | WPA_CIPHER_WEP40 | WPA_CIPHER_WEP104)) { | 
|  | 2975 | wpa_printf(MSG_ERROR, "Line %d: unsupported pairwise cipher suite '%s'", | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 2976 | line, pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2977 | return 1; | 
|  | 2978 | } | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 2979 | } else if (os_strcmp(buf, "group_cipher") == 0) { | 
|  | 2980 | bss->group_cipher = hostapd_config_parse_cipher(line, pos); | 
|  | 2981 | if (bss->group_cipher == -1 || bss->group_cipher == 0) | 
|  | 2982 | return 1; | 
|  | 2983 | if (bss->group_cipher != WPA_CIPHER_TKIP && | 
|  | 2984 | bss->group_cipher != WPA_CIPHER_CCMP && | 
|  | 2985 | bss->group_cipher != WPA_CIPHER_GCMP && | 
|  | 2986 | bss->group_cipher != WPA_CIPHER_GCMP_256 && | 
|  | 2987 | bss->group_cipher != WPA_CIPHER_CCMP_256) { | 
|  | 2988 | wpa_printf(MSG_ERROR, | 
|  | 2989 | "Line %d: unsupported group cipher suite '%s'", | 
|  | 2990 | line, pos); | 
|  | 2991 | return 1; | 
|  | 2992 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2993 | #ifdef CONFIG_RSN_PREAUTH | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2994 | } else if (os_strcmp(buf, "rsn_preauth") == 0) { | 
|  | 2995 | bss->rsn_preauth = atoi(pos); | 
|  | 2996 | } else if (os_strcmp(buf, "rsn_preauth_interfaces") == 0) { | 
| Dmitry Shmidt | 21de214 | 2014-04-08 10:50:52 -0700 | [diff] [blame] | 2997 | os_free(bss->rsn_preauth_interfaces); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 2998 | bss->rsn_preauth_interfaces = os_strdup(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 2999 | #endif /* CONFIG_RSN_PREAUTH */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3000 | } else if (os_strcmp(buf, "peerkey") == 0) { | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 3001 | wpa_printf(MSG_INFO, | 
|  | 3002 | "Line %d: Obsolete peerkey parameter ignored", line); | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 3003 | #ifdef CONFIG_IEEE80211R_AP | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3004 | } else if (os_strcmp(buf, "mobility_domain") == 0) { | 
|  | 3005 | if (os_strlen(pos) != 2 * MOBILITY_DOMAIN_ID_LEN || | 
|  | 3006 | hexstr2bin(pos, bss->mobility_domain, | 
|  | 3007 | MOBILITY_DOMAIN_ID_LEN) != 0) { | 
|  | 3008 | wpa_printf(MSG_ERROR, | 
|  | 3009 | "Line %d: Invalid mobility_domain '%s'", | 
|  | 3010 | line, pos); | 
|  | 3011 | return 1; | 
|  | 3012 | } | 
|  | 3013 | } else if (os_strcmp(buf, "r1_key_holder") == 0) { | 
|  | 3014 | if (os_strlen(pos) != 2 * FT_R1KH_ID_LEN || | 
|  | 3015 | hexstr2bin(pos, bss->r1_key_holder, FT_R1KH_ID_LEN) != 0) { | 
|  | 3016 | wpa_printf(MSG_ERROR, | 
|  | 3017 | "Line %d: Invalid r1_key_holder '%s'", | 
|  | 3018 | line, pos); | 
|  | 3019 | return 1; | 
|  | 3020 | } | 
|  | 3021 | } else if (os_strcmp(buf, "r0_key_lifetime") == 0) { | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 3022 | /* DEPRECATED: Use ft_r0_key_lifetime instead. */ | 
|  | 3023 | bss->r0_key_lifetime = atoi(pos) * 60; | 
|  | 3024 | } else if (os_strcmp(buf, "ft_r0_key_lifetime") == 0) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3025 | bss->r0_key_lifetime = atoi(pos); | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 3026 | } else if (os_strcmp(buf, "r1_max_key_lifetime") == 0) { | 
|  | 3027 | bss->r1_max_key_lifetime = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3028 | } else if (os_strcmp(buf, "reassociation_deadline") == 0) { | 
|  | 3029 | bss->reassociation_deadline = atoi(pos); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 3030 | } else if (os_strcmp(buf, "rkh_pos_timeout") == 0) { | 
|  | 3031 | bss->rkh_pos_timeout = atoi(pos); | 
|  | 3032 | } else if (os_strcmp(buf, "rkh_neg_timeout") == 0) { | 
|  | 3033 | bss->rkh_neg_timeout = atoi(pos); | 
|  | 3034 | } else if (os_strcmp(buf, "rkh_pull_timeout") == 0) { | 
|  | 3035 | bss->rkh_pull_timeout = atoi(pos); | 
|  | 3036 | } else if (os_strcmp(buf, "rkh_pull_retries") == 0) { | 
|  | 3037 | bss->rkh_pull_retries = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3038 | } else if (os_strcmp(buf, "r0kh") == 0) { | 
|  | 3039 | if (add_r0kh(bss, pos) < 0) { | 
|  | 3040 | wpa_printf(MSG_DEBUG, "Line %d: Invalid r0kh '%s'", | 
|  | 3041 | line, pos); | 
|  | 3042 | return 1; | 
|  | 3043 | } | 
|  | 3044 | } else if (os_strcmp(buf, "r1kh") == 0) { | 
|  | 3045 | if (add_r1kh(bss, pos) < 0) { | 
|  | 3046 | wpa_printf(MSG_DEBUG, "Line %d: Invalid r1kh '%s'", | 
|  | 3047 | line, pos); | 
|  | 3048 | return 1; | 
|  | 3049 | } | 
|  | 3050 | } else if (os_strcmp(buf, "pmk_r1_push") == 0) { | 
|  | 3051 | bss->pmk_r1_push = atoi(pos); | 
|  | 3052 | } else if (os_strcmp(buf, "ft_over_ds") == 0) { | 
|  | 3053 | bss->ft_over_ds = atoi(pos); | 
| Dmitry Shmidt | 9839ecd | 2016-11-07 11:05:47 -0800 | [diff] [blame] | 3054 | } else if (os_strcmp(buf, "ft_psk_generate_local") == 0) { | 
|  | 3055 | bss->ft_psk_generate_local = atoi(pos); | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 3056 | #endif /* CONFIG_IEEE80211R_AP */ | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3057 | #ifndef CONFIG_NO_CTRL_IFACE | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3058 | } else if (os_strcmp(buf, "ctrl_interface") == 0) { | 
|  | 3059 | os_free(bss->ctrl_interface); | 
|  | 3060 | bss->ctrl_interface = os_strdup(pos); | 
|  | 3061 | } else if (os_strcmp(buf, "ctrl_interface_group") == 0) { | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3062 | #ifndef CONFIG_NATIVE_WINDOWS | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3063 | struct group *grp; | 
|  | 3064 | char *endp; | 
|  | 3065 | const char *group = pos; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3066 |  | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3067 | grp = getgrnam(group); | 
|  | 3068 | if (grp) { | 
|  | 3069 | bss->ctrl_interface_gid = grp->gr_gid; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3070 | bss->ctrl_interface_gid_set = 1; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3071 | wpa_printf(MSG_DEBUG, "ctrl_interface_group=%d (from group name '%s')", | 
|  | 3072 | bss->ctrl_interface_gid, group); | 
|  | 3073 | return 0; | 
|  | 3074 | } | 
|  | 3075 |  | 
|  | 3076 | /* Group name not found - try to parse this as gid */ | 
|  | 3077 | bss->ctrl_interface_gid = strtol(group, &endp, 10); | 
|  | 3078 | if (*group == '\0' || *endp != '\0') { | 
|  | 3079 | wpa_printf(MSG_DEBUG, "Line %d: Invalid group '%s'", | 
|  | 3080 | line, group); | 
|  | 3081 | return 1; | 
|  | 3082 | } | 
|  | 3083 | bss->ctrl_interface_gid_set = 1; | 
|  | 3084 | wpa_printf(MSG_DEBUG, "ctrl_interface_group=%d", | 
|  | 3085 | bss->ctrl_interface_gid); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3086 | #endif /* CONFIG_NATIVE_WINDOWS */ | 
|  | 3087 | #endif /* CONFIG_NO_CTRL_IFACE */ | 
|  | 3088 | #ifdef RADIUS_SERVER | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3089 | } else if (os_strcmp(buf, "radius_server_clients") == 0) { | 
|  | 3090 | os_free(bss->radius_server_clients); | 
|  | 3091 | bss->radius_server_clients = os_strdup(pos); | 
|  | 3092 | } else if (os_strcmp(buf, "radius_server_auth_port") == 0) { | 
|  | 3093 | bss->radius_server_auth_port = atoi(pos); | 
|  | 3094 | } else if (os_strcmp(buf, "radius_server_acct_port") == 0) { | 
|  | 3095 | bss->radius_server_acct_port = atoi(pos); | 
|  | 3096 | } else if (os_strcmp(buf, "radius_server_ipv6") == 0) { | 
|  | 3097 | bss->radius_server_ipv6 = atoi(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3098 | #endif /* RADIUS_SERVER */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3099 | } else if (os_strcmp(buf, "use_pae_group_addr") == 0) { | 
|  | 3100 | bss->use_pae_group_addr = atoi(pos); | 
|  | 3101 | } else if (os_strcmp(buf, "hw_mode") == 0) { | 
|  | 3102 | if (os_strcmp(pos, "a") == 0) | 
|  | 3103 | conf->hw_mode = HOSTAPD_MODE_IEEE80211A; | 
|  | 3104 | else if (os_strcmp(pos, "b") == 0) | 
|  | 3105 | conf->hw_mode = HOSTAPD_MODE_IEEE80211B; | 
|  | 3106 | else if (os_strcmp(pos, "g") == 0) | 
|  | 3107 | conf->hw_mode = HOSTAPD_MODE_IEEE80211G; | 
|  | 3108 | else if (os_strcmp(pos, "ad") == 0) | 
|  | 3109 | conf->hw_mode = HOSTAPD_MODE_IEEE80211AD; | 
| Dmitry Shmidt | b1e5210 | 2015-05-29 12:36:29 -0700 | [diff] [blame] | 3110 | else if (os_strcmp(pos, "any") == 0) | 
|  | 3111 | conf->hw_mode = HOSTAPD_MODE_IEEE80211ANY; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3112 | else { | 
|  | 3113 | wpa_printf(MSG_ERROR, "Line %d: unknown hw_mode '%s'", | 
|  | 3114 | line, pos); | 
|  | 3115 | return 1; | 
|  | 3116 | } | 
| Sunil Ravi | a04bd25 | 2022-05-02 22:54:18 -0700 | [diff] [blame] | 3117 | conf->hw_mode_set = true; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3118 | } else if (os_strcmp(buf, "wps_rf_bands") == 0) { | 
| Dmitry Shmidt | 1d755d0 | 2015-04-28 10:34:29 -0700 | [diff] [blame] | 3119 | if (os_strcmp(pos, "ad") == 0) | 
|  | 3120 | bss->wps_rf_bands = WPS_RF_60GHZ; | 
|  | 3121 | else if (os_strcmp(pos, "a") == 0) | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3122 | bss->wps_rf_bands = WPS_RF_50GHZ; | 
|  | 3123 | else if (os_strcmp(pos, "g") == 0 || | 
|  | 3124 | os_strcmp(pos, "b") == 0) | 
|  | 3125 | bss->wps_rf_bands = WPS_RF_24GHZ; | 
|  | 3126 | else if (os_strcmp(pos, "ag") == 0 || | 
|  | 3127 | os_strcmp(pos, "ga") == 0) | 
|  | 3128 | bss->wps_rf_bands = WPS_RF_24GHZ | WPS_RF_50GHZ; | 
|  | 3129 | else { | 
|  | 3130 | wpa_printf(MSG_ERROR, | 
|  | 3131 | "Line %d: unknown wps_rf_band '%s'", | 
|  | 3132 | line, pos); | 
|  | 3133 | return 1; | 
|  | 3134 | } | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 3135 | } else if (os_strcmp(buf, "acs_exclude_dfs") == 0) { | 
|  | 3136 | conf->acs_exclude_dfs = atoi(pos); | 
| Hai Shalom | c356592 | 2019-10-28 11:58:20 -0700 | [diff] [blame] | 3137 | } else if (os_strcmp(buf, "op_class") == 0) { | 
|  | 3138 | conf->op_class = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3139 | } else if (os_strcmp(buf, "channel") == 0) { | 
|  | 3140 | if (os_strcmp(pos, "acs_survey") == 0) { | 
| Dmitry Shmidt | 391c59f | 2013-09-03 12:16:28 -0700 | [diff] [blame] | 3141 | #ifndef CONFIG_ACS | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3142 | wpa_printf(MSG_ERROR, "Line %d: tries to enable ACS but CONFIG_ACS disabled", | 
|  | 3143 | line); | 
|  | 3144 | return 1; | 
| Dmitry Shmidt | 7832adb | 2014-04-29 10:53:02 -0700 | [diff] [blame] | 3145 | #else /* CONFIG_ACS */ | 
| Dmitry Shmidt | dda10c2 | 2015-03-24 16:05:01 -0700 | [diff] [blame] | 3146 | conf->acs = 1; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3147 | conf->channel = 0; | 
| Dmitry Shmidt | 7832adb | 2014-04-29 10:53:02 -0700 | [diff] [blame] | 3148 | #endif /* CONFIG_ACS */ | 
| Dmitry Shmidt | dda10c2 | 2015-03-24 16:05:01 -0700 | [diff] [blame] | 3149 | } else { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3150 | conf->channel = atoi(pos); | 
| Dmitry Shmidt | dda10c2 | 2015-03-24 16:05:01 -0700 | [diff] [blame] | 3151 | conf->acs = conf->channel == 0; | 
|  | 3152 | } | 
| Hai Shalom | c356592 | 2019-10-28 11:58:20 -0700 | [diff] [blame] | 3153 | } else if (os_strcmp(buf, "edmg_channel") == 0) { | 
|  | 3154 | conf->edmg_channel = atoi(pos); | 
|  | 3155 | } else if (os_strcmp(buf, "enable_edmg") == 0) { | 
|  | 3156 | conf->enable_edmg = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3157 | } else if (os_strcmp(buf, "chanlist") == 0) { | 
| Dmitry Shmidt | dda10c2 | 2015-03-24 16:05:01 -0700 | [diff] [blame] | 3158 | if (hostapd_parse_chanlist(conf, pos)) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3159 | wpa_printf(MSG_ERROR, "Line %d: invalid channel list", | 
|  | 3160 | line); | 
|  | 3161 | return 1; | 
|  | 3162 | } | 
| Ahmed ElArabawy | 0ff61c5 | 2019-12-26 12:38:39 -0800 | [diff] [blame] | 3163 | } else if (os_strcmp(buf, "freqlist") == 0) { | 
|  | 3164 | if (freq_range_list_parse(&conf->acs_freq_list, pos)) { | 
|  | 3165 | wpa_printf(MSG_ERROR, "Line %d: invalid frequency list", | 
|  | 3166 | line); | 
|  | 3167 | return 1; | 
|  | 3168 | } | 
|  | 3169 | conf->acs_freq_list_present = 1; | 
|  | 3170 | } else if (os_strcmp(buf, "acs_exclude_6ghz_non_psc") == 0) { | 
|  | 3171 | conf->acs_exclude_6ghz_non_psc = atoi(pos); | 
| Sunil Ravi | a04bd25 | 2022-05-02 22:54:18 -0700 | [diff] [blame] | 3172 | } else if (os_strcmp(buf, "enable_background_radar") == 0) { | 
|  | 3173 | conf->enable_background_radar = atoi(pos); | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 3174 | } else if (os_strcmp(buf, "min_tx_power") == 0) { | 
|  | 3175 | int val = atoi(pos); | 
|  | 3176 |  | 
|  | 3177 | if (val < 0 || val > 255) { | 
|  | 3178 | wpa_printf(MSG_ERROR, | 
|  | 3179 | "Line %d: invalid min_tx_power %d (expected 0..255)", | 
|  | 3180 | line, val); | 
|  | 3181 | return 1; | 
|  | 3182 | } | 
|  | 3183 | conf->min_tx_power = val; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3184 | } else if (os_strcmp(buf, "beacon_int") == 0) { | 
|  | 3185 | int val = atoi(pos); | 
|  | 3186 | /* MIB defines range as 1..65535, but very small values | 
|  | 3187 | * cause problems with the current implementation. | 
|  | 3188 | * Since it is unlikely that this small numbers are | 
|  | 3189 | * useful in real life scenarios, do not allow beacon | 
| Hai Shalom | 021b0b5 | 2019-04-10 11:17:58 -0700 | [diff] [blame] | 3190 | * period to be set below 10 TU. */ | 
|  | 3191 | if (val < 10 || val > 65535) { | 
|  | 3192 | wpa_printf(MSG_ERROR, | 
|  | 3193 | "Line %d: invalid beacon_int %d (expected 10..65535)", | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3194 | line, val); | 
|  | 3195 | return 1; | 
|  | 3196 | } | 
|  | 3197 | conf->beacon_int = val; | 
| Dmitry Shmidt | 391c59f | 2013-09-03 12:16:28 -0700 | [diff] [blame] | 3198 | #ifdef CONFIG_ACS | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3199 | } else if (os_strcmp(buf, "acs_num_scans") == 0) { | 
|  | 3200 | int val = atoi(pos); | 
|  | 3201 | if (val <= 0 || val > 100) { | 
|  | 3202 | wpa_printf(MSG_ERROR, "Line %d: invalid acs_num_scans %d (expected 1..100)", | 
|  | 3203 | line, val); | 
|  | 3204 | return 1; | 
|  | 3205 | } | 
|  | 3206 | conf->acs_num_scans = val; | 
| Dmitry Shmidt | 7f65602 | 2015-02-25 14:36:37 -0800 | [diff] [blame] | 3207 | } else if (os_strcmp(buf, "acs_chan_bias") == 0) { | 
|  | 3208 | if (hostapd_config_parse_acs_chan_bias(conf, pos)) { | 
|  | 3209 | wpa_printf(MSG_ERROR, "Line %d: invalid acs_chan_bias", | 
|  | 3210 | line); | 
|  | 3211 | return -1; | 
|  | 3212 | } | 
| Dmitry Shmidt | 391c59f | 2013-09-03 12:16:28 -0700 | [diff] [blame] | 3213 | #endif /* CONFIG_ACS */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3214 | } else if (os_strcmp(buf, "dtim_period") == 0) { | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 3215 | int val = atoi(pos); | 
|  | 3216 |  | 
|  | 3217 | if (val < 1 || val > 255) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3218 | wpa_printf(MSG_ERROR, "Line %d: invalid dtim_period %d", | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 3219 | line, val); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3220 | return 1; | 
|  | 3221 | } | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 3222 | bss->dtim_period = val; | 
| Dmitry Shmidt | 6c0da2b | 2015-01-05 13:08:17 -0800 | [diff] [blame] | 3223 | } else if (os_strcmp(buf, "bss_load_update_period") == 0) { | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 3224 | int val = atoi(pos); | 
|  | 3225 |  | 
|  | 3226 | if (val < 0 || val > 100) { | 
| Dmitry Shmidt | 6c0da2b | 2015-01-05 13:08:17 -0800 | [diff] [blame] | 3227 | wpa_printf(MSG_ERROR, | 
|  | 3228 | "Line %d: invalid bss_load_update_period %d", | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 3229 | line, val); | 
| Dmitry Shmidt | 6c0da2b | 2015-01-05 13:08:17 -0800 | [diff] [blame] | 3230 | return 1; | 
|  | 3231 | } | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 3232 | bss->bss_load_update_period = val; | 
|  | 3233 | } else if (os_strcmp(buf, "chan_util_avg_period") == 0) { | 
|  | 3234 | int val = atoi(pos); | 
|  | 3235 |  | 
|  | 3236 | if (val < 0) { | 
|  | 3237 | wpa_printf(MSG_ERROR, | 
|  | 3238 | "Line %d: invalid chan_util_avg_period", | 
|  | 3239 | line); | 
|  | 3240 | return 1; | 
|  | 3241 | } | 
|  | 3242 | bss->chan_util_avg_period = val; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3243 | } else if (os_strcmp(buf, "rts_threshold") == 0) { | 
|  | 3244 | conf->rts_threshold = atoi(pos); | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 3245 | if (conf->rts_threshold < -1 || conf->rts_threshold > 65535) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3246 | wpa_printf(MSG_ERROR, | 
|  | 3247 | "Line %d: invalid rts_threshold %d", | 
|  | 3248 | line, conf->rts_threshold); | 
|  | 3249 | return 1; | 
|  | 3250 | } | 
|  | 3251 | } else if (os_strcmp(buf, "fragm_threshold") == 0) { | 
|  | 3252 | conf->fragm_threshold = atoi(pos); | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 3253 | if (conf->fragm_threshold == -1) { | 
|  | 3254 | /* allow a value of -1 */ | 
|  | 3255 | } else if (conf->fragm_threshold < 256 || | 
|  | 3256 | conf->fragm_threshold > 2346) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3257 | wpa_printf(MSG_ERROR, | 
|  | 3258 | "Line %d: invalid fragm_threshold %d", | 
|  | 3259 | line, conf->fragm_threshold); | 
|  | 3260 | return 1; | 
|  | 3261 | } | 
|  | 3262 | } else if (os_strcmp(buf, "send_probe_response") == 0) { | 
|  | 3263 | int val = atoi(pos); | 
|  | 3264 | if (val != 0 && val != 1) { | 
|  | 3265 | wpa_printf(MSG_ERROR, "Line %d: invalid send_probe_response %d (expected 0 or 1)", | 
|  | 3266 | line, val); | 
|  | 3267 | return 1; | 
|  | 3268 | } | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 3269 | bss->send_probe_response = val; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3270 | } else if (os_strcmp(buf, "supported_rates") == 0) { | 
|  | 3271 | if (hostapd_parse_intlist(&conf->supported_rates, pos)) { | 
|  | 3272 | wpa_printf(MSG_ERROR, "Line %d: invalid rate list", | 
|  | 3273 | line); | 
|  | 3274 | return 1; | 
|  | 3275 | } | 
|  | 3276 | } else if (os_strcmp(buf, "basic_rates") == 0) { | 
|  | 3277 | if (hostapd_parse_intlist(&conf->basic_rates, pos)) { | 
|  | 3278 | wpa_printf(MSG_ERROR, "Line %d: invalid rate list", | 
|  | 3279 | line); | 
|  | 3280 | return 1; | 
|  | 3281 | } | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 3282 | } else if (os_strcmp(buf, "beacon_rate") == 0) { | 
|  | 3283 | int val; | 
|  | 3284 |  | 
|  | 3285 | if (os_strncmp(pos, "ht:", 3) == 0) { | 
|  | 3286 | val = atoi(pos + 3); | 
|  | 3287 | if (val < 0 || val > 31) { | 
|  | 3288 | wpa_printf(MSG_ERROR, | 
|  | 3289 | "Line %d: invalid beacon_rate HT-MCS %d", | 
|  | 3290 | line, val); | 
|  | 3291 | return 1; | 
|  | 3292 | } | 
|  | 3293 | conf->rate_type = BEACON_RATE_HT; | 
|  | 3294 | conf->beacon_rate = val; | 
|  | 3295 | } else if (os_strncmp(pos, "vht:", 4) == 0) { | 
|  | 3296 | val = atoi(pos + 4); | 
|  | 3297 | if (val < 0 || val > 9) { | 
|  | 3298 | wpa_printf(MSG_ERROR, | 
|  | 3299 | "Line %d: invalid beacon_rate VHT-MCS %d", | 
|  | 3300 | line, val); | 
|  | 3301 | return 1; | 
|  | 3302 | } | 
|  | 3303 | conf->rate_type = BEACON_RATE_VHT; | 
|  | 3304 | conf->beacon_rate = val; | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 3305 | } else if (os_strncmp(pos, "he:", 3) == 0) { | 
|  | 3306 | val = atoi(pos + 3); | 
|  | 3307 | if (val < 0 || val > 11) { | 
|  | 3308 | wpa_printf(MSG_ERROR, | 
|  | 3309 | "Line %d: invalid beacon_rate HE-MCS %d", | 
|  | 3310 | line, val); | 
|  | 3311 | return 1; | 
|  | 3312 | } | 
|  | 3313 | conf->rate_type = BEACON_RATE_HE; | 
|  | 3314 | conf->beacon_rate = val; | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 3315 | } else { | 
|  | 3316 | val = atoi(pos); | 
|  | 3317 | if (val < 10 || val > 10000) { | 
|  | 3318 | wpa_printf(MSG_ERROR, | 
|  | 3319 | "Line %d: invalid legacy beacon_rate %d", | 
|  | 3320 | line, val); | 
|  | 3321 | return 1; | 
|  | 3322 | } | 
|  | 3323 | conf->rate_type = BEACON_RATE_LEGACY; | 
|  | 3324 | conf->beacon_rate = val; | 
|  | 3325 | } | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3326 | } else if (os_strcmp(buf, "preamble") == 0) { | 
|  | 3327 | if (atoi(pos)) | 
|  | 3328 | conf->preamble = SHORT_PREAMBLE; | 
|  | 3329 | else | 
|  | 3330 | conf->preamble = LONG_PREAMBLE; | 
|  | 3331 | } else if (os_strcmp(buf, "ignore_broadcast_ssid") == 0) { | 
|  | 3332 | bss->ignore_broadcast_ssid = atoi(pos); | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 3333 | } else if (os_strcmp(buf, "no_probe_resp_if_max_sta") == 0) { | 
|  | 3334 | bss->no_probe_resp_if_max_sta = atoi(pos); | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 3335 | #ifdef CONFIG_WEP | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3336 | } else if (os_strcmp(buf, "wep_default_key") == 0) { | 
|  | 3337 | bss->ssid.wep.idx = atoi(pos); | 
|  | 3338 | if (bss->ssid.wep.idx > 3) { | 
|  | 3339 | wpa_printf(MSG_ERROR, | 
|  | 3340 | "Invalid wep_default_key index %d", | 
|  | 3341 | bss->ssid.wep.idx); | 
|  | 3342 | return 1; | 
|  | 3343 | } | 
|  | 3344 | } else if (os_strcmp(buf, "wep_key0") == 0 || | 
|  | 3345 | os_strcmp(buf, "wep_key1") == 0 || | 
|  | 3346 | os_strcmp(buf, "wep_key2") == 0 || | 
|  | 3347 | os_strcmp(buf, "wep_key3") == 0) { | 
|  | 3348 | if (hostapd_config_read_wep(&bss->ssid.wep, | 
|  | 3349 | buf[7] - '0', pos)) { | 
|  | 3350 | wpa_printf(MSG_ERROR, "Line %d: invalid WEP key '%s'", | 
|  | 3351 | line, buf); | 
|  | 3352 | return 1; | 
|  | 3353 | } | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 3354 | #endif /* CONFIG_WEP */ | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3355 | #ifndef CONFIG_NO_VLAN | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3356 | } else if (os_strcmp(buf, "dynamic_vlan") == 0) { | 
|  | 3357 | bss->ssid.dynamic_vlan = atoi(pos); | 
| Dmitry Shmidt | 57c2d39 | 2016-02-23 13:40:19 -0800 | [diff] [blame] | 3358 | } else if (os_strcmp(buf, "per_sta_vif") == 0) { | 
|  | 3359 | bss->ssid.per_sta_vif = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3360 | } else if (os_strcmp(buf, "vlan_file") == 0) { | 
|  | 3361 | if (hostapd_config_read_vlan_file(bss, pos)) { | 
|  | 3362 | wpa_printf(MSG_ERROR, "Line %d: failed to read VLAN file '%s'", | 
|  | 3363 | line, pos); | 
|  | 3364 | return 1; | 
|  | 3365 | } | 
|  | 3366 | } else if (os_strcmp(buf, "vlan_naming") == 0) { | 
|  | 3367 | bss->ssid.vlan_naming = atoi(pos); | 
|  | 3368 | if (bss->ssid.vlan_naming >= DYNAMIC_VLAN_NAMING_END || | 
|  | 3369 | bss->ssid.vlan_naming < 0) { | 
|  | 3370 | wpa_printf(MSG_ERROR, | 
|  | 3371 | "Line %d: invalid naming scheme %d", | 
|  | 3372 | line, bss->ssid.vlan_naming); | 
|  | 3373 | return 1; | 
|  | 3374 | } | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3375 | #ifdef CONFIG_FULL_DYNAMIC_VLAN | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3376 | } else if (os_strcmp(buf, "vlan_tagged_interface") == 0) { | 
| Dmitry Shmidt | 21de214 | 2014-04-08 10:50:52 -0700 | [diff] [blame] | 3377 | os_free(bss->ssid.vlan_tagged_interface); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3378 | bss->ssid.vlan_tagged_interface = os_strdup(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3379 | #endif /* CONFIG_FULL_DYNAMIC_VLAN */ | 
|  | 3380 | #endif /* CONFIG_NO_VLAN */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3381 | } else if (os_strcmp(buf, "ap_table_max_size") == 0) { | 
|  | 3382 | conf->ap_table_max_size = atoi(pos); | 
|  | 3383 | } else if (os_strcmp(buf, "ap_table_expiration_time") == 0) { | 
|  | 3384 | conf->ap_table_expiration_time = atoi(pos); | 
|  | 3385 | } else if (os_strncmp(buf, "tx_queue_", 9) == 0) { | 
| Hai Shalom | 899fcc7 | 2020-10-19 14:38:18 -0700 | [diff] [blame] | 3386 | if (hostapd_config_tx_queue(conf->tx_queue, buf, pos)) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3387 | wpa_printf(MSG_ERROR, "Line %d: invalid TX queue item", | 
|  | 3388 | line); | 
|  | 3389 | return 1; | 
|  | 3390 | } | 
|  | 3391 | } else if (os_strcmp(buf, "wme_enabled") == 0 || | 
|  | 3392 | os_strcmp(buf, "wmm_enabled") == 0) { | 
|  | 3393 | bss->wmm_enabled = atoi(pos); | 
|  | 3394 | } else if (os_strcmp(buf, "uapsd_advertisement_enabled") == 0) { | 
|  | 3395 | bss->wmm_uapsd = atoi(pos); | 
|  | 3396 | } else if (os_strncmp(buf, "wme_ac_", 7) == 0 || | 
|  | 3397 | os_strncmp(buf, "wmm_ac_", 7) == 0) { | 
|  | 3398 | if (hostapd_config_wmm_ac(conf->wmm_ac_params, buf, pos)) { | 
|  | 3399 | wpa_printf(MSG_ERROR, "Line %d: invalid WMM ac item", | 
|  | 3400 | line); | 
|  | 3401 | return 1; | 
|  | 3402 | } | 
|  | 3403 | } else if (os_strcmp(buf, "bss") == 0) { | 
|  | 3404 | if (hostapd_config_bss(conf, pos)) { | 
|  | 3405 | wpa_printf(MSG_ERROR, "Line %d: invalid bss item", | 
|  | 3406 | line); | 
|  | 3407 | return 1; | 
|  | 3408 | } | 
|  | 3409 | } else if (os_strcmp(buf, "bssid") == 0) { | 
|  | 3410 | if (hwaddr_aton(pos, bss->bssid)) { | 
|  | 3411 | wpa_printf(MSG_ERROR, "Line %d: invalid bssid item", | 
|  | 3412 | line); | 
|  | 3413 | return 1; | 
|  | 3414 | } | 
| Dmitry Shmidt | 31a29cc | 2016-03-09 15:58:17 -0800 | [diff] [blame] | 3415 | } else if (os_strcmp(buf, "use_driver_iface_addr") == 0) { | 
|  | 3416 | conf->use_driver_iface_addr = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3417 | } else if (os_strcmp(buf, "ieee80211w") == 0) { | 
|  | 3418 | bss->ieee80211w = atoi(pos); | 
| Dmitry Shmidt | b36ed7c | 2014-03-17 10:57:26 -0700 | [diff] [blame] | 3419 | } else if (os_strcmp(buf, "group_mgmt_cipher") == 0) { | 
|  | 3420 | if (os_strcmp(pos, "AES-128-CMAC") == 0) { | 
|  | 3421 | bss->group_mgmt_cipher = WPA_CIPHER_AES_128_CMAC; | 
|  | 3422 | } else if (os_strcmp(pos, "BIP-GMAC-128") == 0) { | 
|  | 3423 | bss->group_mgmt_cipher = WPA_CIPHER_BIP_GMAC_128; | 
|  | 3424 | } else if (os_strcmp(pos, "BIP-GMAC-256") == 0) { | 
|  | 3425 | bss->group_mgmt_cipher = WPA_CIPHER_BIP_GMAC_256; | 
|  | 3426 | } else if (os_strcmp(pos, "BIP-CMAC-256") == 0) { | 
|  | 3427 | bss->group_mgmt_cipher = WPA_CIPHER_BIP_CMAC_256; | 
|  | 3428 | } else { | 
|  | 3429 | wpa_printf(MSG_ERROR, "Line %d: invalid group_mgmt_cipher: %s", | 
|  | 3430 | line, pos); | 
|  | 3431 | return 1; | 
|  | 3432 | } | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 3433 | } else if (os_strcmp(buf, "beacon_prot") == 0) { | 
|  | 3434 | bss->beacon_prot = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3435 | } else if (os_strcmp(buf, "assoc_sa_query_max_timeout") == 0) { | 
|  | 3436 | bss->assoc_sa_query_max_timeout = atoi(pos); | 
|  | 3437 | if (bss->assoc_sa_query_max_timeout == 0) { | 
|  | 3438 | wpa_printf(MSG_ERROR, "Line %d: invalid assoc_sa_query_max_timeout", | 
|  | 3439 | line); | 
|  | 3440 | return 1; | 
|  | 3441 | } | 
|  | 3442 | } else if (os_strcmp(buf, "assoc_sa_query_retry_timeout") == 0) { | 
|  | 3443 | bss->assoc_sa_query_retry_timeout = atoi(pos); | 
|  | 3444 | if (bss->assoc_sa_query_retry_timeout == 0) { | 
|  | 3445 | wpa_printf(MSG_ERROR, "Line %d: invalid assoc_sa_query_retry_timeout", | 
|  | 3446 | line); | 
|  | 3447 | return 1; | 
|  | 3448 | } | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 3449 | #ifdef CONFIG_OCV | 
|  | 3450 | } else if (os_strcmp(buf, "ocv") == 0) { | 
|  | 3451 | bss->ocv = atoi(pos); | 
|  | 3452 | if (bss->ocv && !bss->ieee80211w) | 
|  | 3453 | bss->ieee80211w = 1; | 
|  | 3454 | #endif /* CONFIG_OCV */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3455 | } else if (os_strcmp(buf, "ieee80211n") == 0) { | 
|  | 3456 | conf->ieee80211n = atoi(pos); | 
|  | 3457 | } else if (os_strcmp(buf, "ht_capab") == 0) { | 
|  | 3458 | if (hostapd_config_ht_capab(conf, pos) < 0) { | 
|  | 3459 | wpa_printf(MSG_ERROR, "Line %d: invalid ht_capab", | 
|  | 3460 | line); | 
|  | 3461 | return 1; | 
|  | 3462 | } | 
|  | 3463 | } else if (os_strcmp(buf, "require_ht") == 0) { | 
|  | 3464 | conf->require_ht = atoi(pos); | 
|  | 3465 | } else if (os_strcmp(buf, "obss_interval") == 0) { | 
|  | 3466 | conf->obss_interval = atoi(pos); | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 3467 | #ifdef CONFIG_IEEE80211AC | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3468 | } else if (os_strcmp(buf, "ieee80211ac") == 0) { | 
|  | 3469 | conf->ieee80211ac = atoi(pos); | 
|  | 3470 | } else if (os_strcmp(buf, "vht_capab") == 0) { | 
|  | 3471 | if (hostapd_config_vht_capab(conf, pos) < 0) { | 
|  | 3472 | wpa_printf(MSG_ERROR, "Line %d: invalid vht_capab", | 
|  | 3473 | line); | 
|  | 3474 | return 1; | 
|  | 3475 | } | 
|  | 3476 | } else if (os_strcmp(buf, "require_vht") == 0) { | 
|  | 3477 | conf->require_vht = atoi(pos); | 
|  | 3478 | } else if (os_strcmp(buf, "vht_oper_chwidth") == 0) { | 
|  | 3479 | conf->vht_oper_chwidth = atoi(pos); | 
|  | 3480 | } else if (os_strcmp(buf, "vht_oper_centr_freq_seg0_idx") == 0) { | 
|  | 3481 | conf->vht_oper_centr_freq_seg0_idx = atoi(pos); | 
|  | 3482 | } else if (os_strcmp(buf, "vht_oper_centr_freq_seg1_idx") == 0) { | 
|  | 3483 | conf->vht_oper_centr_freq_seg1_idx = atoi(pos); | 
| Dmitry Shmidt | 2f74e36 | 2015-01-21 13:19:05 -0800 | [diff] [blame] | 3484 | } else if (os_strcmp(buf, "vendor_vht") == 0) { | 
|  | 3485 | bss->vendor_vht = atoi(pos); | 
| Dmitry Shmidt | 7d17530 | 2016-09-06 13:11:34 -0700 | [diff] [blame] | 3486 | } else if (os_strcmp(buf, "use_sta_nsts") == 0) { | 
|  | 3487 | bss->use_sta_nsts = atoi(pos); | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 3488 | #endif /* CONFIG_IEEE80211AC */ | 
| Dmitry Shmidt | ebd93af | 2017-02-21 13:40:44 -0800 | [diff] [blame] | 3489 | #ifdef CONFIG_IEEE80211AX | 
|  | 3490 | } else if (os_strcmp(buf, "ieee80211ax") == 0) { | 
|  | 3491 | conf->ieee80211ax = atoi(pos); | 
| Sunil Ravi | 77d572f | 2023-01-17 23:58:31 +0000 | [diff] [blame] | 3492 | } else if (os_strcmp(buf, "require_he") == 0) { | 
|  | 3493 | conf->require_he = atoi(pos); | 
| Dmitry Shmidt | ebd93af | 2017-02-21 13:40:44 -0800 | [diff] [blame] | 3494 | } else if (os_strcmp(buf, "he_su_beamformer") == 0) { | 
|  | 3495 | conf->he_phy_capab.he_su_beamformer = atoi(pos); | 
|  | 3496 | } else if (os_strcmp(buf, "he_su_beamformee") == 0) { | 
|  | 3497 | conf->he_phy_capab.he_su_beamformee = atoi(pos); | 
|  | 3498 | } else if (os_strcmp(buf, "he_mu_beamformer") == 0) { | 
|  | 3499 | conf->he_phy_capab.he_mu_beamformer = atoi(pos); | 
|  | 3500 | } else if (os_strcmp(buf, "he_bss_color") == 0) { | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 3501 | conf->he_op.he_bss_color = atoi(pos) & 0x3f; | 
|  | 3502 | conf->he_op.he_bss_color_disabled = 0; | 
|  | 3503 | } else if (os_strcmp(buf, "he_bss_color_partial") == 0) { | 
|  | 3504 | conf->he_op.he_bss_color_partial = atoi(pos); | 
| Dmitry Shmidt | ebd93af | 2017-02-21 13:40:44 -0800 | [diff] [blame] | 3505 | } else if (os_strcmp(buf, "he_default_pe_duration") == 0) { | 
|  | 3506 | conf->he_op.he_default_pe_duration = atoi(pos); | 
|  | 3507 | } else if (os_strcmp(buf, "he_twt_required") == 0) { | 
|  | 3508 | conf->he_op.he_twt_required = atoi(pos); | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 3509 | } else if (os_strcmp(buf, "he_twt_responder") == 0) { | 
|  | 3510 | conf->he_op.he_twt_responder = atoi(pos); | 
| Dmitry Shmidt | ebd93af | 2017-02-21 13:40:44 -0800 | [diff] [blame] | 3511 | } else if (os_strcmp(buf, "he_rts_threshold") == 0) { | 
|  | 3512 | conf->he_op.he_rts_threshold = atoi(pos); | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 3513 | } else if (os_strcmp(buf, "he_er_su_disable") == 0) { | 
|  | 3514 | conf->he_op.he_er_su_disable = atoi(pos); | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 3515 | } else if (os_strcmp(buf, "he_basic_mcs_nss_set") == 0) { | 
|  | 3516 | conf->he_op.he_basic_mcs_nss_set = atoi(pos); | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 3517 | } else if (os_strcmp(buf, "he_mu_edca_qos_info_param_count") == 0) { | 
|  | 3518 | conf->he_mu_edca.he_qos_info |= | 
|  | 3519 | set_he_cap(atoi(pos), HE_QOS_INFO_EDCA_PARAM_SET_COUNT); | 
|  | 3520 | } else if (os_strcmp(buf, "he_mu_edca_qos_info_q_ack") == 0) { | 
|  | 3521 | conf->he_mu_edca.he_qos_info |= | 
|  | 3522 | set_he_cap(atoi(pos), HE_QOS_INFO_Q_ACK); | 
|  | 3523 | } else if (os_strcmp(buf, "he_mu_edca_qos_info_queue_request") == 0) { | 
|  | 3524 | conf->he_mu_edca.he_qos_info |= | 
|  | 3525 | set_he_cap(atoi(pos), HE_QOS_INFO_QUEUE_REQUEST); | 
|  | 3526 | } else if (os_strcmp(buf, "he_mu_edca_qos_info_txop_request") == 0) { | 
|  | 3527 | conf->he_mu_edca.he_qos_info |= | 
|  | 3528 | set_he_cap(atoi(pos), HE_QOS_INFO_TXOP_REQUEST); | 
|  | 3529 | } else if (os_strcmp(buf, "he_mu_edca_ac_be_aifsn") == 0) { | 
|  | 3530 | conf->he_mu_edca.he_mu_ac_be_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3531 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_AIFSN); | 
|  | 3532 | } else if (os_strcmp(buf, "he_mu_edca_ac_be_acm") == 0) { | 
|  | 3533 | conf->he_mu_edca.he_mu_ac_be_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3534 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ACM); | 
|  | 3535 | } else if (os_strcmp(buf, "he_mu_edca_ac_be_aci") == 0) { | 
|  | 3536 | conf->he_mu_edca.he_mu_ac_be_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3537 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ACI); | 
|  | 3538 | } else if (os_strcmp(buf, "he_mu_edca_ac_be_ecwmin") == 0) { | 
|  | 3539 | conf->he_mu_edca.he_mu_ac_be_param[HE_MU_AC_PARAM_ECW_IDX] |= | 
|  | 3540 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ECWMIN); | 
|  | 3541 | } else if (os_strcmp(buf, "he_mu_edca_ac_be_ecwmax") == 0) { | 
|  | 3542 | conf->he_mu_edca.he_mu_ac_be_param[HE_MU_AC_PARAM_ECW_IDX] |= | 
|  | 3543 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ECWMAX); | 
|  | 3544 | } else if (os_strcmp(buf, "he_mu_edca_ac_be_timer") == 0) { | 
|  | 3545 | conf->he_mu_edca.he_mu_ac_be_param[HE_MU_AC_PARAM_TIMER_IDX] = | 
|  | 3546 | atoi(pos) & 0xff; | 
|  | 3547 | } else if (os_strcmp(buf, "he_mu_edca_ac_bk_aifsn") == 0) { | 
|  | 3548 | conf->he_mu_edca.he_mu_ac_bk_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3549 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_AIFSN); | 
|  | 3550 | } else if (os_strcmp(buf, "he_mu_edca_ac_bk_acm") == 0) { | 
|  | 3551 | conf->he_mu_edca.he_mu_ac_bk_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3552 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ACM); | 
|  | 3553 | } else if (os_strcmp(buf, "he_mu_edca_ac_bk_aci") == 0) { | 
|  | 3554 | conf->he_mu_edca.he_mu_ac_bk_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3555 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ACI); | 
|  | 3556 | } else if (os_strcmp(buf, "he_mu_edca_ac_bk_ecwmin") == 0) { | 
|  | 3557 | conf->he_mu_edca.he_mu_ac_bk_param[HE_MU_AC_PARAM_ECW_IDX] |= | 
|  | 3558 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ECWMIN); | 
|  | 3559 | } else if (os_strcmp(buf, "he_mu_edca_ac_bk_ecwmax") == 0) { | 
|  | 3560 | conf->he_mu_edca.he_mu_ac_bk_param[HE_MU_AC_PARAM_ECW_IDX] |= | 
|  | 3561 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ECWMAX); | 
|  | 3562 | } else if (os_strcmp(buf, "he_mu_edca_ac_bk_timer") == 0) { | 
|  | 3563 | conf->he_mu_edca.he_mu_ac_bk_param[HE_MU_AC_PARAM_TIMER_IDX] = | 
|  | 3564 | atoi(pos) & 0xff; | 
|  | 3565 | } else if (os_strcmp(buf, "he_mu_edca_ac_vi_aifsn") == 0) { | 
|  | 3566 | conf->he_mu_edca.he_mu_ac_vi_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3567 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_AIFSN); | 
|  | 3568 | } else if (os_strcmp(buf, "he_mu_edca_ac_vi_acm") == 0) { | 
|  | 3569 | conf->he_mu_edca.he_mu_ac_vi_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3570 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ACM); | 
|  | 3571 | } else if (os_strcmp(buf, "he_mu_edca_ac_vi_aci") == 0) { | 
|  | 3572 | conf->he_mu_edca.he_mu_ac_vi_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3573 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ACI); | 
|  | 3574 | } else if (os_strcmp(buf, "he_mu_edca_ac_vi_ecwmin") == 0) { | 
|  | 3575 | conf->he_mu_edca.he_mu_ac_vi_param[HE_MU_AC_PARAM_ECW_IDX] |= | 
|  | 3576 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ECWMIN); | 
|  | 3577 | } else if (os_strcmp(buf, "he_mu_edca_ac_vi_ecwmax") == 0) { | 
|  | 3578 | conf->he_mu_edca.he_mu_ac_vi_param[HE_MU_AC_PARAM_ECW_IDX] |= | 
|  | 3579 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ECWMAX); | 
|  | 3580 | } else if (os_strcmp(buf, "he_mu_edca_ac_vi_timer") == 0) { | 
|  | 3581 | conf->he_mu_edca.he_mu_ac_vi_param[HE_MU_AC_PARAM_TIMER_IDX] = | 
|  | 3582 | atoi(pos) & 0xff; | 
|  | 3583 | } else if (os_strcmp(buf, "he_mu_edca_ac_vo_aifsn") == 0) { | 
|  | 3584 | conf->he_mu_edca.he_mu_ac_vo_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3585 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_AIFSN); | 
|  | 3586 | } else if (os_strcmp(buf, "he_mu_edca_ac_vo_acm") == 0) { | 
|  | 3587 | conf->he_mu_edca.he_mu_ac_vo_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3588 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ACM); | 
|  | 3589 | } else if (os_strcmp(buf, "he_mu_edca_ac_vo_aci") == 0) { | 
|  | 3590 | conf->he_mu_edca.he_mu_ac_vo_param[HE_MU_AC_PARAM_ACI_IDX] |= | 
|  | 3591 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ACI); | 
|  | 3592 | } else if (os_strcmp(buf, "he_mu_edca_ac_vo_ecwmin") == 0) { | 
|  | 3593 | conf->he_mu_edca.he_mu_ac_vo_param[HE_MU_AC_PARAM_ECW_IDX] |= | 
|  | 3594 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ECWMIN); | 
|  | 3595 | } else if (os_strcmp(buf, "he_mu_edca_ac_vo_ecwmax") == 0) { | 
|  | 3596 | conf->he_mu_edca.he_mu_ac_vo_param[HE_MU_AC_PARAM_ECW_IDX] |= | 
|  | 3597 | set_he_cap(atoi(pos), HE_MU_AC_PARAM_ECWMAX); | 
|  | 3598 | } else if (os_strcmp(buf, "he_mu_edca_ac_vo_timer") == 0) { | 
|  | 3599 | conf->he_mu_edca.he_mu_ac_vo_param[HE_MU_AC_PARAM_TIMER_IDX] = | 
|  | 3600 | atoi(pos) & 0xff; | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 3601 | } else if (os_strcmp(buf, "he_spr_sr_control") == 0) { | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 3602 | conf->spr.sr_control = atoi(pos) & 0x1f; | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 3603 | } else if (os_strcmp(buf, "he_spr_non_srg_obss_pd_max_offset") == 0) { | 
|  | 3604 | conf->spr.non_srg_obss_pd_max_offset = atoi(pos); | 
|  | 3605 | } else if (os_strcmp(buf, "he_spr_srg_obss_pd_min_offset") == 0) { | 
|  | 3606 | conf->spr.srg_obss_pd_min_offset = atoi(pos); | 
|  | 3607 | } else if (os_strcmp(buf, "he_spr_srg_obss_pd_max_offset") == 0) { | 
|  | 3608 | conf->spr.srg_obss_pd_max_offset = atoi(pos); | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 3609 | } else if (os_strcmp(buf, "he_spr_srg_bss_colors") == 0) { | 
|  | 3610 | if (hostapd_parse_he_srg_bitmap( | 
|  | 3611 | conf->spr.srg_bss_color_bitmap, pos)) { | 
|  | 3612 | wpa_printf(MSG_ERROR, | 
|  | 3613 | "Line %d: Invalid srg bss colors list '%s'", | 
|  | 3614 | line, pos); | 
|  | 3615 | return 1; | 
|  | 3616 | } | 
|  | 3617 | } else if (os_strcmp(buf, "he_spr_srg_partial_bssid") == 0) { | 
|  | 3618 | if (hostapd_parse_he_srg_bitmap( | 
|  | 3619 | conf->spr.srg_partial_bssid_bitmap, pos)) { | 
|  | 3620 | wpa_printf(MSG_ERROR, | 
|  | 3621 | "Line %d: Invalid srg partial bssid list '%s'", | 
|  | 3622 | line, pos); | 
|  | 3623 | return 1; | 
|  | 3624 | } | 
| Sunil Ravi | a04bd25 | 2022-05-02 22:54:18 -0700 | [diff] [blame] | 3625 | } else if (os_strcmp(buf, "he_6ghz_reg_pwr_type") == 0) { | 
|  | 3626 | conf->he_6ghz_reg_pwr_type = atoi(pos); | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 3627 | } else if (os_strcmp(buf, "he_oper_chwidth") == 0) { | 
|  | 3628 | conf->he_oper_chwidth = atoi(pos); | 
|  | 3629 | } else if (os_strcmp(buf, "he_oper_centr_freq_seg0_idx") == 0) { | 
|  | 3630 | conf->he_oper_centr_freq_seg0_idx = atoi(pos); | 
|  | 3631 | } else if (os_strcmp(buf, "he_oper_centr_freq_seg1_idx") == 0) { | 
|  | 3632 | conf->he_oper_centr_freq_seg1_idx = atoi(pos); | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 3633 | } else if (os_strcmp(buf, "he_6ghz_max_mpdu") == 0) { | 
|  | 3634 | conf->he_6ghz_max_mpdu = atoi(pos); | 
|  | 3635 | } else if (os_strcmp(buf, "he_6ghz_max_ampdu_len_exp") == 0) { | 
|  | 3636 | conf->he_6ghz_max_ampdu_len_exp = atoi(pos); | 
|  | 3637 | } else if (os_strcmp(buf, "he_6ghz_rx_ant_pat") == 0) { | 
|  | 3638 | conf->he_6ghz_rx_ant_pat = atoi(pos); | 
|  | 3639 | } else if (os_strcmp(buf, "he_6ghz_tx_ant_pat") == 0) { | 
|  | 3640 | conf->he_6ghz_tx_ant_pat = atoi(pos); | 
|  | 3641 | } else if (os_strcmp(buf, "unsol_bcast_probe_resp_interval") == 0) { | 
|  | 3642 | int val = atoi(pos); | 
|  | 3643 |  | 
|  | 3644 | if (val < 0 || val > 20) { | 
|  | 3645 | wpa_printf(MSG_ERROR, | 
|  | 3646 | "Line %d: invalid unsol_bcast_probe_resp_interval value", | 
|  | 3647 | line); | 
|  | 3648 | return 1; | 
|  | 3649 | } | 
|  | 3650 | bss->unsol_bcast_probe_resp_interval = val; | 
| Sunil Ravi | 77d572f | 2023-01-17 23:58:31 +0000 | [diff] [blame] | 3651 | } else if (os_strcmp(buf, "mbssid") == 0) { | 
|  | 3652 | int mbssid = atoi(pos); | 
|  | 3653 | if (mbssid < 0 || mbssid > ENHANCED_MBSSID_ENABLED) { | 
|  | 3654 | wpa_printf(MSG_ERROR, | 
|  | 3655 | "Line %d: invalid mbssid (%d): '%s'.", | 
|  | 3656 | line, mbssid, pos); | 
|  | 3657 | return 1; | 
|  | 3658 | } | 
|  | 3659 | conf->mbssid = mbssid; | 
| Dmitry Shmidt | ebd93af | 2017-02-21 13:40:44 -0800 | [diff] [blame] | 3660 | #endif /* CONFIG_IEEE80211AX */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3661 | } else if (os_strcmp(buf, "max_listen_interval") == 0) { | 
|  | 3662 | bss->max_listen_interval = atoi(pos); | 
|  | 3663 | } else if (os_strcmp(buf, "disable_pmksa_caching") == 0) { | 
|  | 3664 | bss->disable_pmksa_caching = atoi(pos); | 
|  | 3665 | } else if (os_strcmp(buf, "okc") == 0) { | 
|  | 3666 | bss->okc = atoi(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3667 | #ifdef CONFIG_WPS | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3668 | } else if (os_strcmp(buf, "wps_state") == 0) { | 
|  | 3669 | bss->wps_state = atoi(pos); | 
|  | 3670 | if (bss->wps_state < 0 || bss->wps_state > 2) { | 
|  | 3671 | wpa_printf(MSG_ERROR, "Line %d: invalid wps_state", | 
|  | 3672 | line); | 
|  | 3673 | return 1; | 
|  | 3674 | } | 
|  | 3675 | } else if (os_strcmp(buf, "wps_independent") == 0) { | 
|  | 3676 | bss->wps_independent = atoi(pos); | 
|  | 3677 | } else if (os_strcmp(buf, "ap_setup_locked") == 0) { | 
|  | 3678 | bss->ap_setup_locked = atoi(pos); | 
|  | 3679 | } else if (os_strcmp(buf, "uuid") == 0) { | 
|  | 3680 | if (uuid_str2bin(pos, bss->uuid)) { | 
|  | 3681 | wpa_printf(MSG_ERROR, "Line %d: invalid UUID", line); | 
|  | 3682 | return 1; | 
|  | 3683 | } | 
|  | 3684 | } else if (os_strcmp(buf, "wps_pin_requests") == 0) { | 
|  | 3685 | os_free(bss->wps_pin_requests); | 
|  | 3686 | bss->wps_pin_requests = os_strdup(pos); | 
|  | 3687 | } else if (os_strcmp(buf, "device_name") == 0) { | 
| Dmitry Shmidt | 9d9e602 | 2015-04-23 10:34:55 -0700 | [diff] [blame] | 3688 | if (os_strlen(pos) > WPS_DEV_NAME_MAX_LEN) { | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3689 | wpa_printf(MSG_ERROR, "Line %d: Too long " | 
|  | 3690 | "device_name", line); | 
|  | 3691 | return 1; | 
|  | 3692 | } | 
|  | 3693 | os_free(bss->device_name); | 
|  | 3694 | bss->device_name = os_strdup(pos); | 
|  | 3695 | } else if (os_strcmp(buf, "manufacturer") == 0) { | 
|  | 3696 | if (os_strlen(pos) > 64) { | 
|  | 3697 | wpa_printf(MSG_ERROR, "Line %d: Too long manufacturer", | 
|  | 3698 | line); | 
|  | 3699 | return 1; | 
|  | 3700 | } | 
|  | 3701 | os_free(bss->manufacturer); | 
|  | 3702 | bss->manufacturer = os_strdup(pos); | 
|  | 3703 | } else if (os_strcmp(buf, "model_name") == 0) { | 
|  | 3704 | if (os_strlen(pos) > 32) { | 
|  | 3705 | wpa_printf(MSG_ERROR, "Line %d: Too long model_name", | 
|  | 3706 | line); | 
|  | 3707 | return 1; | 
|  | 3708 | } | 
|  | 3709 | os_free(bss->model_name); | 
|  | 3710 | bss->model_name = os_strdup(pos); | 
|  | 3711 | } else if (os_strcmp(buf, "model_number") == 0) { | 
|  | 3712 | if (os_strlen(pos) > 32) { | 
|  | 3713 | wpa_printf(MSG_ERROR, "Line %d: Too long model_number", | 
|  | 3714 | line); | 
|  | 3715 | return 1; | 
|  | 3716 | } | 
|  | 3717 | os_free(bss->model_number); | 
|  | 3718 | bss->model_number = os_strdup(pos); | 
|  | 3719 | } else if (os_strcmp(buf, "serial_number") == 0) { | 
|  | 3720 | if (os_strlen(pos) > 32) { | 
|  | 3721 | wpa_printf(MSG_ERROR, "Line %d: Too long serial_number", | 
|  | 3722 | line); | 
|  | 3723 | return 1; | 
|  | 3724 | } | 
|  | 3725 | os_free(bss->serial_number); | 
|  | 3726 | bss->serial_number = os_strdup(pos); | 
|  | 3727 | } else if (os_strcmp(buf, "device_type") == 0) { | 
|  | 3728 | if (wps_dev_type_str2bin(pos, bss->device_type)) | 
|  | 3729 | return 1; | 
|  | 3730 | } else if (os_strcmp(buf, "config_methods") == 0) { | 
|  | 3731 | os_free(bss->config_methods); | 
|  | 3732 | bss->config_methods = os_strdup(pos); | 
|  | 3733 | } else if (os_strcmp(buf, "os_version") == 0) { | 
|  | 3734 | if (hexstr2bin(pos, bss->os_version, 4)) { | 
|  | 3735 | wpa_printf(MSG_ERROR, "Line %d: invalid os_version", | 
|  | 3736 | line); | 
|  | 3737 | return 1; | 
|  | 3738 | } | 
|  | 3739 | } else if (os_strcmp(buf, "ap_pin") == 0) { | 
|  | 3740 | os_free(bss->ap_pin); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 3741 | if (*pos == '\0') | 
|  | 3742 | bss->ap_pin = NULL; | 
|  | 3743 | else | 
|  | 3744 | bss->ap_pin = os_strdup(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3745 | } else if (os_strcmp(buf, "skip_cred_build") == 0) { | 
|  | 3746 | bss->skip_cred_build = atoi(pos); | 
|  | 3747 | } else if (os_strcmp(buf, "extra_cred") == 0) { | 
|  | 3748 | os_free(bss->extra_cred); | 
|  | 3749 | bss->extra_cred = (u8 *) os_readfile(pos, &bss->extra_cred_len); | 
|  | 3750 | if (bss->extra_cred == NULL) { | 
|  | 3751 | wpa_printf(MSG_ERROR, "Line %d: could not read Credentials from '%s'", | 
|  | 3752 | line, pos); | 
|  | 3753 | return 1; | 
|  | 3754 | } | 
|  | 3755 | } else if (os_strcmp(buf, "wps_cred_processing") == 0) { | 
|  | 3756 | bss->wps_cred_processing = atoi(pos); | 
| Hai Shalom | 021b0b5 | 2019-04-10 11:17:58 -0700 | [diff] [blame] | 3757 | } else if (os_strcmp(buf, "wps_cred_add_sae") == 0) { | 
|  | 3758 | bss->wps_cred_add_sae = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3759 | } else if (os_strcmp(buf, "ap_settings") == 0) { | 
|  | 3760 | os_free(bss->ap_settings); | 
|  | 3761 | bss->ap_settings = | 
|  | 3762 | (u8 *) os_readfile(pos, &bss->ap_settings_len); | 
|  | 3763 | if (bss->ap_settings == NULL) { | 
|  | 3764 | wpa_printf(MSG_ERROR, "Line %d: could not read AP Settings from '%s'", | 
|  | 3765 | line, pos); | 
|  | 3766 | return 1; | 
|  | 3767 | } | 
| Hai Shalom | 021b0b5 | 2019-04-10 11:17:58 -0700 | [diff] [blame] | 3768 | } else if (os_strcmp(buf, "multi_ap_backhaul_ssid") == 0) { | 
|  | 3769 | size_t slen; | 
|  | 3770 | char *str = wpa_config_parse_string(pos, &slen); | 
|  | 3771 |  | 
|  | 3772 | if (!str || slen < 1 || slen > SSID_MAX_LEN) { | 
|  | 3773 | wpa_printf(MSG_ERROR, "Line %d: invalid SSID '%s'", | 
|  | 3774 | line, pos); | 
|  | 3775 | os_free(str); | 
|  | 3776 | return 1; | 
|  | 3777 | } | 
|  | 3778 | os_memcpy(bss->multi_ap_backhaul_ssid.ssid, str, slen); | 
|  | 3779 | bss->multi_ap_backhaul_ssid.ssid_len = slen; | 
|  | 3780 | bss->multi_ap_backhaul_ssid.ssid_set = 1; | 
|  | 3781 | os_free(str); | 
|  | 3782 | } else if (os_strcmp(buf, "multi_ap_backhaul_wpa_passphrase") == 0) { | 
|  | 3783 | int len = os_strlen(pos); | 
|  | 3784 |  | 
|  | 3785 | if (len < 8 || len > 63) { | 
|  | 3786 | wpa_printf(MSG_ERROR, | 
|  | 3787 | "Line %d: invalid WPA passphrase length %d (expected 8..63)", | 
|  | 3788 | line, len); | 
|  | 3789 | return 1; | 
|  | 3790 | } | 
|  | 3791 | os_free(bss->multi_ap_backhaul_ssid.wpa_passphrase); | 
|  | 3792 | bss->multi_ap_backhaul_ssid.wpa_passphrase = os_strdup(pos); | 
|  | 3793 | if (bss->multi_ap_backhaul_ssid.wpa_passphrase) { | 
|  | 3794 | hostapd_config_clear_wpa_psk( | 
|  | 3795 | &bss->multi_ap_backhaul_ssid.wpa_psk); | 
|  | 3796 | bss->multi_ap_backhaul_ssid.wpa_passphrase_set = 1; | 
|  | 3797 | } | 
|  | 3798 | } else if (os_strcmp(buf, "multi_ap_backhaul_wpa_psk") == 0) { | 
|  | 3799 | hostapd_config_clear_wpa_psk( | 
|  | 3800 | &bss->multi_ap_backhaul_ssid.wpa_psk); | 
|  | 3801 | bss->multi_ap_backhaul_ssid.wpa_psk = | 
|  | 3802 | os_zalloc(sizeof(struct hostapd_wpa_psk)); | 
|  | 3803 | if (!bss->multi_ap_backhaul_ssid.wpa_psk) | 
|  | 3804 | return 1; | 
|  | 3805 | if (hexstr2bin(pos, bss->multi_ap_backhaul_ssid.wpa_psk->psk, | 
|  | 3806 | PMK_LEN) || | 
|  | 3807 | pos[PMK_LEN * 2] != '\0') { | 
|  | 3808 | wpa_printf(MSG_ERROR, "Line %d: Invalid PSK '%s'.", | 
|  | 3809 | line, pos); | 
|  | 3810 | hostapd_config_clear_wpa_psk( | 
|  | 3811 | &bss->multi_ap_backhaul_ssid.wpa_psk); | 
|  | 3812 | return 1; | 
|  | 3813 | } | 
|  | 3814 | bss->multi_ap_backhaul_ssid.wpa_psk->group = 1; | 
|  | 3815 | os_free(bss->multi_ap_backhaul_ssid.wpa_passphrase); | 
|  | 3816 | bss->multi_ap_backhaul_ssid.wpa_passphrase = NULL; | 
|  | 3817 | bss->multi_ap_backhaul_ssid.wpa_psk_set = 1; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3818 | } else if (os_strcmp(buf, "upnp_iface") == 0) { | 
| Dmitry Shmidt | 21de214 | 2014-04-08 10:50:52 -0700 | [diff] [blame] | 3819 | os_free(bss->upnp_iface); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3820 | bss->upnp_iface = os_strdup(pos); | 
|  | 3821 | } else if (os_strcmp(buf, "friendly_name") == 0) { | 
|  | 3822 | os_free(bss->friendly_name); | 
|  | 3823 | bss->friendly_name = os_strdup(pos); | 
|  | 3824 | } else if (os_strcmp(buf, "manufacturer_url") == 0) { | 
|  | 3825 | os_free(bss->manufacturer_url); | 
|  | 3826 | bss->manufacturer_url = os_strdup(pos); | 
|  | 3827 | } else if (os_strcmp(buf, "model_description") == 0) { | 
|  | 3828 | os_free(bss->model_description); | 
|  | 3829 | bss->model_description = os_strdup(pos); | 
|  | 3830 | } else if (os_strcmp(buf, "model_url") == 0) { | 
|  | 3831 | os_free(bss->model_url); | 
|  | 3832 | bss->model_url = os_strdup(pos); | 
|  | 3833 | } else if (os_strcmp(buf, "upc") == 0) { | 
|  | 3834 | os_free(bss->upc); | 
|  | 3835 | bss->upc = os_strdup(pos); | 
|  | 3836 | } else if (os_strcmp(buf, "pbc_in_m1") == 0) { | 
|  | 3837 | bss->pbc_in_m1 = atoi(pos); | 
|  | 3838 | } else if (os_strcmp(buf, "server_id") == 0) { | 
|  | 3839 | os_free(bss->server_id); | 
|  | 3840 | bss->server_id = os_strdup(pos); | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 3841 | } else if (os_strcmp(buf, "wps_application_ext") == 0) { | 
|  | 3842 | wpabuf_free(bss->wps_application_ext); | 
|  | 3843 | bss->wps_application_ext = wpabuf_parse_bin(pos); | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 3844 | #ifdef CONFIG_WPS_NFC | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3845 | } else if (os_strcmp(buf, "wps_nfc_dev_pw_id") == 0) { | 
|  | 3846 | bss->wps_nfc_dev_pw_id = atoi(pos); | 
|  | 3847 | if (bss->wps_nfc_dev_pw_id < 0x10 || | 
|  | 3848 | bss->wps_nfc_dev_pw_id > 0xffff) { | 
|  | 3849 | wpa_printf(MSG_ERROR, "Line %d: Invalid wps_nfc_dev_pw_id value", | 
|  | 3850 | line); | 
|  | 3851 | return 1; | 
|  | 3852 | } | 
|  | 3853 | bss->wps_nfc_pw_from_config = 1; | 
|  | 3854 | } else if (os_strcmp(buf, "wps_nfc_dh_pubkey") == 0) { | 
|  | 3855 | wpabuf_free(bss->wps_nfc_dh_pubkey); | 
| Dmitry Shmidt | 849734c | 2016-05-27 09:59:01 -0700 | [diff] [blame] | 3856 | bss->wps_nfc_dh_pubkey = wpabuf_parse_bin(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3857 | bss->wps_nfc_pw_from_config = 1; | 
|  | 3858 | } else if (os_strcmp(buf, "wps_nfc_dh_privkey") == 0) { | 
|  | 3859 | wpabuf_free(bss->wps_nfc_dh_privkey); | 
| Dmitry Shmidt | 849734c | 2016-05-27 09:59:01 -0700 | [diff] [blame] | 3860 | bss->wps_nfc_dh_privkey = wpabuf_parse_bin(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3861 | bss->wps_nfc_pw_from_config = 1; | 
|  | 3862 | } else if (os_strcmp(buf, "wps_nfc_dev_pw") == 0) { | 
|  | 3863 | wpabuf_free(bss->wps_nfc_dev_pw); | 
| Dmitry Shmidt | 849734c | 2016-05-27 09:59:01 -0700 | [diff] [blame] | 3864 | bss->wps_nfc_dev_pw = wpabuf_parse_bin(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3865 | bss->wps_nfc_pw_from_config = 1; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 3866 | #endif /* CONFIG_WPS_NFC */ | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3867 | #endif /* CONFIG_WPS */ | 
|  | 3868 | #ifdef CONFIG_P2P_MANAGER | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3869 | } else if (os_strcmp(buf, "manage_p2p") == 0) { | 
|  | 3870 | if (atoi(pos)) | 
|  | 3871 | bss->p2p |= P2P_MANAGE; | 
|  | 3872 | else | 
|  | 3873 | bss->p2p &= ~P2P_MANAGE; | 
|  | 3874 | } else if (os_strcmp(buf, "allow_cross_connection") == 0) { | 
|  | 3875 | if (atoi(pos)) | 
|  | 3876 | bss->p2p |= P2P_ALLOW_CROSS_CONNECTION; | 
|  | 3877 | else | 
|  | 3878 | bss->p2p &= ~P2P_ALLOW_CROSS_CONNECTION; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3879 | #endif /* CONFIG_P2P_MANAGER */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3880 | } else if (os_strcmp(buf, "disassoc_low_ack") == 0) { | 
|  | 3881 | bss->disassoc_low_ack = atoi(pos); | 
|  | 3882 | } else if (os_strcmp(buf, "tdls_prohibit") == 0) { | 
|  | 3883 | if (atoi(pos)) | 
|  | 3884 | bss->tdls |= TDLS_PROHIBIT; | 
|  | 3885 | else | 
|  | 3886 | bss->tdls &= ~TDLS_PROHIBIT; | 
|  | 3887 | } else if (os_strcmp(buf, "tdls_prohibit_chan_switch") == 0) { | 
|  | 3888 | if (atoi(pos)) | 
|  | 3889 | bss->tdls |= TDLS_PROHIBIT_CHAN_SWITCH; | 
|  | 3890 | else | 
|  | 3891 | bss->tdls &= ~TDLS_PROHIBIT_CHAN_SWITCH; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3892 | #ifdef CONFIG_RSN_TESTING | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3893 | } else if (os_strcmp(buf, "rsn_testing") == 0) { | 
|  | 3894 | extern int rsn_testing; | 
|  | 3895 | rsn_testing = atoi(pos); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 3896 | #endif /* CONFIG_RSN_TESTING */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3897 | } else if (os_strcmp(buf, "time_advertisement") == 0) { | 
|  | 3898 | bss->time_advertisement = atoi(pos); | 
|  | 3899 | } else if (os_strcmp(buf, "time_zone") == 0) { | 
|  | 3900 | size_t tz_len = os_strlen(pos); | 
|  | 3901 | if (tz_len < 4 || tz_len > 255) { | 
|  | 3902 | wpa_printf(MSG_DEBUG, "Line %d: invalid time_zone", | 
|  | 3903 | line); | 
|  | 3904 | return 1; | 
|  | 3905 | } | 
|  | 3906 | os_free(bss->time_zone); | 
|  | 3907 | bss->time_zone = os_strdup(pos); | 
|  | 3908 | if (bss->time_zone == NULL) | 
|  | 3909 | return 1; | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 3910 | #ifdef CONFIG_WNM_AP | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3911 | } else if (os_strcmp(buf, "wnm_sleep_mode") == 0) { | 
|  | 3912 | bss->wnm_sleep_mode = atoi(pos); | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 3913 | } else if (os_strcmp(buf, "wnm_sleep_mode_no_keys") == 0) { | 
|  | 3914 | bss->wnm_sleep_mode_no_keys = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3915 | } else if (os_strcmp(buf, "bss_transition") == 0) { | 
|  | 3916 | bss->bss_transition = atoi(pos); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 3917 | #endif /* CONFIG_WNM_AP */ | 
| Dmitry Shmidt | 1f69aa5 | 2012-01-24 16:10:04 -0800 | [diff] [blame] | 3918 | #ifdef CONFIG_INTERWORKING | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3919 | } else if (os_strcmp(buf, "interworking") == 0) { | 
|  | 3920 | bss->interworking = atoi(pos); | 
|  | 3921 | } else if (os_strcmp(buf, "access_network_type") == 0) { | 
|  | 3922 | bss->access_network_type = atoi(pos); | 
|  | 3923 | if (bss->access_network_type < 0 || | 
|  | 3924 | bss->access_network_type > 15) { | 
|  | 3925 | wpa_printf(MSG_ERROR, | 
|  | 3926 | "Line %d: invalid access_network_type", | 
|  | 3927 | line); | 
|  | 3928 | return 1; | 
|  | 3929 | } | 
|  | 3930 | } else if (os_strcmp(buf, "internet") == 0) { | 
|  | 3931 | bss->internet = atoi(pos); | 
|  | 3932 | } else if (os_strcmp(buf, "asra") == 0) { | 
|  | 3933 | bss->asra = atoi(pos); | 
|  | 3934 | } else if (os_strcmp(buf, "esr") == 0) { | 
|  | 3935 | bss->esr = atoi(pos); | 
|  | 3936 | } else if (os_strcmp(buf, "uesa") == 0) { | 
|  | 3937 | bss->uesa = atoi(pos); | 
|  | 3938 | } else if (os_strcmp(buf, "venue_group") == 0) { | 
|  | 3939 | bss->venue_group = atoi(pos); | 
|  | 3940 | bss->venue_info_set = 1; | 
|  | 3941 | } else if (os_strcmp(buf, "venue_type") == 0) { | 
|  | 3942 | bss->venue_type = atoi(pos); | 
|  | 3943 | bss->venue_info_set = 1; | 
|  | 3944 | } else if (os_strcmp(buf, "hessid") == 0) { | 
|  | 3945 | if (hwaddr_aton(pos, bss->hessid)) { | 
|  | 3946 | wpa_printf(MSG_ERROR, "Line %d: invalid hessid", line); | 
|  | 3947 | return 1; | 
|  | 3948 | } | 
|  | 3949 | } else if (os_strcmp(buf, "roaming_consortium") == 0) { | 
|  | 3950 | if (parse_roaming_consortium(bss, pos, line) < 0) | 
|  | 3951 | return 1; | 
|  | 3952 | } else if (os_strcmp(buf, "venue_name") == 0) { | 
|  | 3953 | if (parse_venue_name(bss, pos, line) < 0) | 
|  | 3954 | return 1; | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 3955 | } else if (os_strcmp(buf, "venue_url") == 0) { | 
|  | 3956 | if (parse_venue_url(bss, pos, line) < 0) | 
|  | 3957 | return 1; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3958 | } else if (os_strcmp(buf, "network_auth_type") == 0) { | 
|  | 3959 | u8 auth_type; | 
|  | 3960 | u16 redirect_url_len; | 
|  | 3961 | if (hexstr2bin(pos, &auth_type, 1)) { | 
|  | 3962 | wpa_printf(MSG_ERROR, | 
|  | 3963 | "Line %d: Invalid network_auth_type '%s'", | 
|  | 3964 | line, pos); | 
|  | 3965 | return 1; | 
|  | 3966 | } | 
|  | 3967 | if (auth_type == 0 || auth_type == 2) | 
|  | 3968 | redirect_url_len = os_strlen(pos + 2); | 
|  | 3969 | else | 
|  | 3970 | redirect_url_len = 0; | 
|  | 3971 | os_free(bss->network_auth_type); | 
|  | 3972 | bss->network_auth_type = os_malloc(redirect_url_len + 3 + 1); | 
|  | 3973 | if (bss->network_auth_type == NULL) | 
|  | 3974 | return 1; | 
|  | 3975 | *bss->network_auth_type = auth_type; | 
|  | 3976 | WPA_PUT_LE16(bss->network_auth_type + 1, redirect_url_len); | 
|  | 3977 | if (redirect_url_len) | 
|  | 3978 | os_memcpy(bss->network_auth_type + 3, pos + 2, | 
|  | 3979 | redirect_url_len); | 
|  | 3980 | bss->network_auth_type_len = 3 + redirect_url_len; | 
|  | 3981 | } else if (os_strcmp(buf, "ipaddr_type_availability") == 0) { | 
|  | 3982 | if (hexstr2bin(pos, &bss->ipaddr_type_availability, 1)) { | 
|  | 3983 | wpa_printf(MSG_ERROR, "Line %d: Invalid ipaddr_type_availability '%s'", | 
|  | 3984 | line, pos); | 
|  | 3985 | bss->ipaddr_type_configured = 0; | 
|  | 3986 | return 1; | 
|  | 3987 | } | 
|  | 3988 | bss->ipaddr_type_configured = 1; | 
|  | 3989 | } else if (os_strcmp(buf, "domain_name") == 0) { | 
|  | 3990 | int j, num_domains, domain_len, domain_list_len = 0; | 
|  | 3991 | char *tok_start, *tok_prev; | 
|  | 3992 | u8 *domain_list, *domain_ptr; | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 3993 |  | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3994 | domain_list_len = os_strlen(pos) + 1; | 
|  | 3995 | domain_list = os_malloc(domain_list_len); | 
|  | 3996 | if (domain_list == NULL) | 
|  | 3997 | return 1; | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 3998 |  | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 3999 | domain_ptr = domain_list; | 
|  | 4000 | tok_prev = pos; | 
|  | 4001 | num_domains = 1; | 
|  | 4002 | while ((tok_prev = os_strchr(tok_prev, ','))) { | 
|  | 4003 | num_domains++; | 
|  | 4004 | tok_prev++; | 
|  | 4005 | } | 
|  | 4006 | tok_prev = pos; | 
|  | 4007 | for (j = 0; j < num_domains; j++) { | 
|  | 4008 | tok_start = os_strchr(tok_prev, ','); | 
|  | 4009 | if (tok_start) { | 
|  | 4010 | domain_len = tok_start - tok_prev; | 
|  | 4011 | *domain_ptr = domain_len; | 
|  | 4012 | os_memcpy(domain_ptr + 1, tok_prev, domain_len); | 
|  | 4013 | domain_ptr += domain_len + 1; | 
|  | 4014 | tok_prev = ++tok_start; | 
|  | 4015 | } else { | 
|  | 4016 | domain_len = os_strlen(tok_prev); | 
|  | 4017 | *domain_ptr = domain_len; | 
|  | 4018 | os_memcpy(domain_ptr + 1, tok_prev, domain_len); | 
|  | 4019 | domain_ptr += domain_len + 1; | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 4020 | } | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4021 | } | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 4022 |  | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4023 | os_free(bss->domain_name); | 
|  | 4024 | bss->domain_name = domain_list; | 
|  | 4025 | bss->domain_name_len = domain_list_len; | 
|  | 4026 | } else if (os_strcmp(buf, "anqp_3gpp_cell_net") == 0) { | 
|  | 4027 | if (parse_3gpp_cell_net(bss, pos, line) < 0) | 
|  | 4028 | return 1; | 
|  | 4029 | } else if (os_strcmp(buf, "nai_realm") == 0) { | 
|  | 4030 | if (parse_nai_realm(bss, pos, line) < 0) | 
|  | 4031 | return 1; | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 4032 | } else if (os_strcmp(buf, "anqp_elem") == 0) { | 
|  | 4033 | if (parse_anqp_elem(bss, pos, line) < 0) | 
|  | 4034 | return 1; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4035 | } else if (os_strcmp(buf, "gas_frag_limit") == 0) { | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 4036 | int val = atoi(pos); | 
|  | 4037 |  | 
|  | 4038 | if (val <= 0) { | 
|  | 4039 | wpa_printf(MSG_ERROR, | 
|  | 4040 | "Line %d: Invalid gas_frag_limit '%s'", | 
|  | 4041 | line, pos); | 
|  | 4042 | return 1; | 
|  | 4043 | } | 
|  | 4044 | bss->gas_frag_limit = val; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4045 | } else if (os_strcmp(buf, "gas_comeback_delay") == 0) { | 
|  | 4046 | bss->gas_comeback_delay = atoi(pos); | 
|  | 4047 | } else if (os_strcmp(buf, "qos_map_set") == 0) { | 
|  | 4048 | if (parse_qos_map_set(bss, pos, line) < 0) | 
|  | 4049 | return 1; | 
| Sunil Ravi | 8861141 | 2024-06-28 17:34:56 +0000 | [diff] [blame] | 4050 | #endif /* CONFIG_INTERWORKING */ | 
| Dmitry Shmidt | 1f69aa5 | 2012-01-24 16:10:04 -0800 | [diff] [blame] | 4051 | #ifdef CONFIG_RADIUS_TEST | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4052 | } else if (os_strcmp(buf, "dump_msk_file") == 0) { | 
|  | 4053 | os_free(bss->dump_msk_file); | 
|  | 4054 | bss->dump_msk_file = os_strdup(pos); | 
| Dmitry Shmidt | 1f69aa5 | 2012-01-24 16:10:04 -0800 | [diff] [blame] | 4055 | #endif /* CONFIG_RADIUS_TEST */ | 
| Dmitry Shmidt | 55840ad | 2015-12-14 12:45:46 -0800 | [diff] [blame] | 4056 | #ifdef CONFIG_PROXYARP | 
|  | 4057 | } else if (os_strcmp(buf, "proxy_arp") == 0) { | 
|  | 4058 | bss->proxy_arp = atoi(pos); | 
|  | 4059 | #endif /* CONFIG_PROXYARP */ | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 4060 | #ifdef CONFIG_HS20 | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4061 | } else if (os_strcmp(buf, "hs20") == 0) { | 
|  | 4062 | bss->hs20 = atoi(pos); | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 4063 | } else if (os_strcmp(buf, "hs20_release") == 0) { | 
|  | 4064 | int val = atoi(pos); | 
|  | 4065 |  | 
|  | 4066 | if (val < 1 || val > (HS20_VERSION >> 4) + 1) { | 
|  | 4067 | wpa_printf(MSG_ERROR, | 
|  | 4068 | "Line %d: Unsupported hs20_release: %s", | 
|  | 4069 | line, pos); | 
|  | 4070 | return 1; | 
|  | 4071 | } | 
|  | 4072 | bss->hs20_release = val; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4073 | } else if (os_strcmp(buf, "disable_dgaf") == 0) { | 
|  | 4074 | bss->disable_dgaf = atoi(pos); | 
| Dmitry Shmidt | 1d755d0 | 2015-04-28 10:34:29 -0700 | [diff] [blame] | 4075 | } else if (os_strcmp(buf, "na_mcast_to_ucast") == 0) { | 
|  | 4076 | bss->na_mcast_to_ucast = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4077 | } else if (os_strcmp(buf, "osen") == 0) { | 
|  | 4078 | bss->osen = atoi(pos); | 
|  | 4079 | } else if (os_strcmp(buf, "anqp_domain_id") == 0) { | 
|  | 4080 | bss->anqp_domain_id = atoi(pos); | 
|  | 4081 | } else if (os_strcmp(buf, "hs20_deauth_req_timeout") == 0) { | 
|  | 4082 | bss->hs20_deauth_req_timeout = atoi(pos); | 
|  | 4083 | } else if (os_strcmp(buf, "hs20_oper_friendly_name") == 0) { | 
|  | 4084 | if (hs20_parse_oper_friendly_name(bss, pos, line) < 0) | 
|  | 4085 | return 1; | 
|  | 4086 | } else if (os_strcmp(buf, "hs20_wan_metrics") == 0) { | 
|  | 4087 | if (hs20_parse_wan_metrics(bss, pos, line) < 0) | 
|  | 4088 | return 1; | 
|  | 4089 | } else if (os_strcmp(buf, "hs20_conn_capab") == 0) { | 
|  | 4090 | if (hs20_parse_conn_capab(bss, pos, line) < 0) { | 
|  | 4091 | return 1; | 
|  | 4092 | } | 
|  | 4093 | } else if (os_strcmp(buf, "hs20_operating_class") == 0) { | 
|  | 4094 | u8 *oper_class; | 
|  | 4095 | size_t oper_class_len; | 
|  | 4096 | oper_class_len = os_strlen(pos); | 
|  | 4097 | if (oper_class_len < 2 || (oper_class_len & 0x01)) { | 
|  | 4098 | wpa_printf(MSG_ERROR, | 
|  | 4099 | "Line %d: Invalid hs20_operating_class '%s'", | 
|  | 4100 | line, pos); | 
|  | 4101 | return 1; | 
|  | 4102 | } | 
|  | 4103 | oper_class_len /= 2; | 
|  | 4104 | oper_class = os_malloc(oper_class_len); | 
|  | 4105 | if (oper_class == NULL) | 
|  | 4106 | return 1; | 
|  | 4107 | if (hexstr2bin(pos, oper_class, oper_class_len)) { | 
|  | 4108 | wpa_printf(MSG_ERROR, | 
|  | 4109 | "Line %d: Invalid hs20_operating_class '%s'", | 
|  | 4110 | line, pos); | 
|  | 4111 | os_free(oper_class); | 
|  | 4112 | return 1; | 
|  | 4113 | } | 
|  | 4114 | os_free(bss->hs20_operating_class); | 
|  | 4115 | bss->hs20_operating_class = oper_class; | 
|  | 4116 | bss->hs20_operating_class_len = oper_class_len; | 
|  | 4117 | } else if (os_strcmp(buf, "hs20_icon") == 0) { | 
|  | 4118 | if (hs20_parse_icon(bss, pos) < 0) { | 
|  | 4119 | wpa_printf(MSG_ERROR, "Line %d: Invalid hs20_icon '%s'", | 
|  | 4120 | line, pos); | 
|  | 4121 | return 1; | 
|  | 4122 | } | 
|  | 4123 | } else if (os_strcmp(buf, "osu_ssid") == 0) { | 
|  | 4124 | if (hs20_parse_osu_ssid(bss, pos, line) < 0) | 
|  | 4125 | return 1; | 
|  | 4126 | } else if (os_strcmp(buf, "osu_server_uri") == 0) { | 
|  | 4127 | if (hs20_parse_osu_server_uri(bss, pos, line) < 0) | 
|  | 4128 | return 1; | 
|  | 4129 | } else if (os_strcmp(buf, "osu_friendly_name") == 0) { | 
|  | 4130 | if (hs20_parse_osu_friendly_name(bss, pos, line) < 0) | 
|  | 4131 | return 1; | 
|  | 4132 | } else if (os_strcmp(buf, "osu_nai") == 0) { | 
|  | 4133 | if (hs20_parse_osu_nai(bss, pos, line) < 0) | 
|  | 4134 | return 1; | 
| Hai Shalom | 39ba6fc | 2019-01-22 12:40:38 -0800 | [diff] [blame] | 4135 | } else if (os_strcmp(buf, "osu_nai2") == 0) { | 
|  | 4136 | if (hs20_parse_osu_nai2(bss, pos, line) < 0) | 
|  | 4137 | return 1; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4138 | } else if (os_strcmp(buf, "osu_method_list") == 0) { | 
|  | 4139 | if (hs20_parse_osu_method_list(bss, pos, line) < 0) | 
|  | 4140 | return 1; | 
|  | 4141 | } else if (os_strcmp(buf, "osu_icon") == 0) { | 
|  | 4142 | if (hs20_parse_osu_icon(bss, pos, line) < 0) | 
|  | 4143 | return 1; | 
|  | 4144 | } else if (os_strcmp(buf, "osu_service_desc") == 0) { | 
|  | 4145 | if (hs20_parse_osu_service_desc(bss, pos, line) < 0) | 
|  | 4146 | return 1; | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 4147 | } else if (os_strcmp(buf, "operator_icon") == 0) { | 
|  | 4148 | if (hs20_parse_operator_icon(bss, pos, line) < 0) | 
|  | 4149 | return 1; | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4150 | } else if (os_strcmp(buf, "subscr_remediation_url") == 0) { | 
|  | 4151 | os_free(bss->subscr_remediation_url); | 
|  | 4152 | bss->subscr_remediation_url = os_strdup(pos); | 
|  | 4153 | } else if (os_strcmp(buf, "subscr_remediation_method") == 0) { | 
|  | 4154 | bss->subscr_remediation_method = atoi(pos); | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 4155 | } else if (os_strcmp(buf, "hs20_t_c_filename") == 0) { | 
|  | 4156 | os_free(bss->t_c_filename); | 
|  | 4157 | bss->t_c_filename = os_strdup(pos); | 
|  | 4158 | } else if (os_strcmp(buf, "hs20_t_c_timestamp") == 0) { | 
|  | 4159 | bss->t_c_timestamp = strtol(pos, NULL, 0); | 
|  | 4160 | } else if (os_strcmp(buf, "hs20_t_c_server_url") == 0) { | 
|  | 4161 | os_free(bss->t_c_server_url); | 
|  | 4162 | bss->t_c_server_url = os_strdup(pos); | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 4163 | } else if (os_strcmp(buf, "hs20_sim_provisioning_url") == 0) { | 
|  | 4164 | os_free(bss->hs20_sim_provisioning_url); | 
|  | 4165 | bss->hs20_sim_provisioning_url = os_strdup(pos); | 
| Dmitry Shmidt | 61d9df3 | 2012-08-29 16:22:06 -0700 | [diff] [blame] | 4166 | #endif /* CONFIG_HS20 */ | 
| Dmitry Shmidt | 57c2d39 | 2016-02-23 13:40:19 -0800 | [diff] [blame] | 4167 | #ifdef CONFIG_MBO | 
|  | 4168 | } else if (os_strcmp(buf, "mbo") == 0) { | 
|  | 4169 | bss->mbo_enabled = atoi(pos); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 4170 | } else if (os_strcmp(buf, "mbo_cell_data_conn_pref") == 0) { | 
|  | 4171 | bss->mbo_cell_data_conn_pref = atoi(pos); | 
|  | 4172 | } else if (os_strcmp(buf, "oce") == 0) { | 
|  | 4173 | bss->oce = atoi(pos); | 
| Dmitry Shmidt | 57c2d39 | 2016-02-23 13:40:19 -0800 | [diff] [blame] | 4174 | #endif /* CONFIG_MBO */ | 
| Dmitry Shmidt | 8da800a | 2013-04-24 12:57:01 -0700 | [diff] [blame] | 4175 | #ifdef CONFIG_TESTING_OPTIONS | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4176 | #define PARSE_TEST_PROBABILITY(_val)				\ | 
|  | 4177 | } else if (os_strcmp(buf, #_val) == 0) {		\ | 
|  | 4178 | char *end;					\ | 
|  | 4179 | \ | 
|  | 4180 | conf->_val = strtod(pos, &end);			\ | 
| Dmitry Shmidt | 7832adb | 2014-04-29 10:53:02 -0700 | [diff] [blame] | 4181 | if (*end || conf->_val < 0.0 ||			\ | 
|  | 4182 | conf->_val > 1.0) {				\ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4183 | wpa_printf(MSG_ERROR,			\ | 
|  | 4184 | "Line %d: Invalid value '%s'", \ | 
|  | 4185 | line, pos);			\ | 
|  | 4186 | return 1;				\ | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 4187 | } | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4188 | PARSE_TEST_PROBABILITY(ignore_probe_probability) | 
|  | 4189 | PARSE_TEST_PROBABILITY(ignore_auth_probability) | 
|  | 4190 | PARSE_TEST_PROBABILITY(ignore_assoc_probability) | 
|  | 4191 | PARSE_TEST_PROBABILITY(ignore_reassoc_probability) | 
|  | 4192 | PARSE_TEST_PROBABILITY(corrupt_gtk_rekey_mic_probability) | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 4193 | } else if (os_strcmp(buf, "ecsa_ie_only") == 0) { | 
|  | 4194 | conf->ecsa_ie_only = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4195 | } else if (os_strcmp(buf, "bss_load_test") == 0) { | 
|  | 4196 | WPA_PUT_LE16(bss->bss_load_test, atoi(pos)); | 
|  | 4197 | pos = os_strchr(pos, ':'); | 
|  | 4198 | if (pos == NULL) { | 
|  | 4199 | wpa_printf(MSG_ERROR, "Line %d: Invalid bss_load_test", | 
|  | 4200 | line); | 
|  | 4201 | return 1; | 
|  | 4202 | } | 
|  | 4203 | pos++; | 
|  | 4204 | bss->bss_load_test[2] = atoi(pos); | 
|  | 4205 | pos = os_strchr(pos, ':'); | 
|  | 4206 | if (pos == NULL) { | 
|  | 4207 | wpa_printf(MSG_ERROR, "Line %d: Invalid bss_load_test", | 
|  | 4208 | line); | 
|  | 4209 | return 1; | 
|  | 4210 | } | 
|  | 4211 | pos++; | 
|  | 4212 | WPA_PUT_LE16(&bss->bss_load_test[3], atoi(pos)); | 
|  | 4213 | bss->bss_load_test_set = 1; | 
| Dmitry Shmidt | 6c0da2b | 2015-01-05 13:08:17 -0800 | [diff] [blame] | 4214 | } else if (os_strcmp(buf, "radio_measurements") == 0) { | 
| Dmitry Shmidt | 849734c | 2016-05-27 09:59:01 -0700 | [diff] [blame] | 4215 | /* | 
|  | 4216 | * DEPRECATED: This parameter will be removed in the future. | 
|  | 4217 | * Use rrm_neighbor_report instead. | 
|  | 4218 | */ | 
|  | 4219 | int val = atoi(pos); | 
|  | 4220 |  | 
|  | 4221 | if (val & BIT(0)) | 
|  | 4222 | bss->radio_measurements[0] |= | 
|  | 4223 | WLAN_RRM_CAPS_NEIGHBOR_REPORT; | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 4224 | } else if (os_strcmp(buf, "own_ie_override") == 0) { | 
|  | 4225 | struct wpabuf *tmp; | 
|  | 4226 | size_t len = os_strlen(pos) / 2; | 
|  | 4227 |  | 
|  | 4228 | tmp = wpabuf_alloc(len); | 
|  | 4229 | if (!tmp) | 
|  | 4230 | return 1; | 
|  | 4231 |  | 
|  | 4232 | if (hexstr2bin(pos, wpabuf_put(tmp, len), len)) { | 
|  | 4233 | wpabuf_free(tmp); | 
|  | 4234 | wpa_printf(MSG_ERROR, | 
|  | 4235 | "Line %d: Invalid own_ie_override '%s'", | 
|  | 4236 | line, pos); | 
|  | 4237 | return 1; | 
|  | 4238 | } | 
|  | 4239 |  | 
|  | 4240 | wpabuf_free(bss->own_ie_override); | 
|  | 4241 | bss->own_ie_override = tmp; | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 4242 | } else if (os_strcmp(buf, "sae_reflection_attack") == 0) { | 
|  | 4243 | bss->sae_reflection_attack = atoi(pos); | 
| Hai Shalom | 899fcc7 | 2020-10-19 14:38:18 -0700 | [diff] [blame] | 4244 | } else if (os_strcmp(buf, "sae_commit_status") == 0) { | 
|  | 4245 | bss->sae_commit_status = atoi(pos); | 
|  | 4246 | } else if (os_strcmp(buf, "sae_pk_omit") == 0) { | 
|  | 4247 | bss->sae_pk_omit = atoi(pos); | 
|  | 4248 | } else if (os_strcmp(buf, "sae_pk_password_check_skip") == 0) { | 
|  | 4249 | bss->sae_pk_password_check_skip = atoi(pos); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 4250 | } else if (os_strcmp(buf, "sae_commit_override") == 0) { | 
|  | 4251 | wpabuf_free(bss->sae_commit_override); | 
|  | 4252 | bss->sae_commit_override = wpabuf_parse_bin(pos); | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 4253 | } else if (os_strcmp(buf, "rsne_override_eapol") == 0) { | 
|  | 4254 | wpabuf_free(bss->rsne_override_eapol); | 
|  | 4255 | bss->rsne_override_eapol = wpabuf_parse_bin(pos); | 
| Ahmed ElArabawy | 0ff61c5 | 2019-12-26 12:38:39 -0800 | [diff] [blame] | 4256 | } else if (os_strcmp(buf, "rsnxe_override_eapol") == 0) { | 
|  | 4257 | wpabuf_free(bss->rsnxe_override_eapol); | 
|  | 4258 | bss->rsnxe_override_eapol = wpabuf_parse_bin(pos); | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 4259 | } else if (os_strcmp(buf, "rsne_override_ft") == 0) { | 
|  | 4260 | wpabuf_free(bss->rsne_override_ft); | 
|  | 4261 | bss->rsne_override_ft = wpabuf_parse_bin(pos); | 
|  | 4262 | } else if (os_strcmp(buf, "rsnxe_override_ft") == 0) { | 
|  | 4263 | wpabuf_free(bss->rsnxe_override_ft); | 
|  | 4264 | bss->rsnxe_override_ft = wpabuf_parse_bin(pos); | 
|  | 4265 | } else if (os_strcmp(buf, "gtk_rsc_override") == 0) { | 
|  | 4266 | wpabuf_free(bss->gtk_rsc_override); | 
|  | 4267 | bss->gtk_rsc_override = wpabuf_parse_bin(pos); | 
|  | 4268 | } else if (os_strcmp(buf, "igtk_rsc_override") == 0) { | 
|  | 4269 | wpabuf_free(bss->igtk_rsc_override); | 
|  | 4270 | bss->igtk_rsc_override = wpabuf_parse_bin(pos); | 
|  | 4271 | } else if (os_strcmp(buf, "no_beacon_rsnxe") == 0) { | 
|  | 4272 | bss->no_beacon_rsnxe = atoi(pos); | 
|  | 4273 | } else if (os_strcmp(buf, "skip_prune_assoc") == 0) { | 
|  | 4274 | bss->skip_prune_assoc = atoi(pos); | 
| Hai Shalom | b755a2a | 2020-04-23 21:49:02 -0700 | [diff] [blame] | 4275 | } else if (os_strcmp(buf, "ft_rsnxe_used") == 0) { | 
|  | 4276 | bss->ft_rsnxe_used = atoi(pos); | 
| Hai Shalom | 899fcc7 | 2020-10-19 14:38:18 -0700 | [diff] [blame] | 4277 | } else if (os_strcmp(buf, "oci_freq_override_eapol_m3") == 0) { | 
|  | 4278 | bss->oci_freq_override_eapol_m3 = atoi(pos); | 
|  | 4279 | } else if (os_strcmp(buf, "oci_freq_override_eapol_g1") == 0) { | 
|  | 4280 | bss->oci_freq_override_eapol_g1 = atoi(pos); | 
|  | 4281 | } else if (os_strcmp(buf, "oci_freq_override_saquery_req") == 0) { | 
|  | 4282 | bss->oci_freq_override_saquery_req = atoi(pos); | 
|  | 4283 | } else if (os_strcmp(buf, "oci_freq_override_saquery_resp") == 0) { | 
|  | 4284 | bss->oci_freq_override_saquery_resp = atoi(pos); | 
|  | 4285 | } else if (os_strcmp(buf, "oci_freq_override_ft_assoc") == 0) { | 
|  | 4286 | bss->oci_freq_override_ft_assoc = atoi(pos); | 
|  | 4287 | } else if (os_strcmp(buf, "oci_freq_override_fils_assoc") == 0) { | 
|  | 4288 | bss->oci_freq_override_fils_assoc = atoi(pos); | 
|  | 4289 | } else if (os_strcmp(buf, "oci_freq_override_wnm_sleep") == 0) { | 
|  | 4290 | bss->oci_freq_override_wnm_sleep = atoi(pos); | 
| Kai Shi | e75b065 | 2020-11-24 20:31:29 -0800 | [diff] [blame] | 4291 | } else if (os_strcmp(buf, "skip_send_eapol") == 0) { | 
|  | 4292 | conf->skip_send_eapol = atoi(pos); | 
|  | 4293 | } else if (os_strcmp(buf, "enable_eapol_large_timeout") == 0) { | 
|  | 4294 | conf->enable_eapol_large_timeout = atoi(pos); | 
| Sunil Ravi | a04bd25 | 2022-05-02 22:54:18 -0700 | [diff] [blame] | 4295 | } else if (os_strcmp(buf, "eap_skip_prot_success") == 0) { | 
|  | 4296 | bss->eap_skip_prot_success = atoi(pos); | 
| Sunil Ravi | 77d572f | 2023-01-17 23:58:31 +0000 | [diff] [blame] | 4297 | } else if (os_strcmp(buf, "delay_eapol_tx") == 0) { | 
|  | 4298 | conf->delay_eapol_tx = atoi(pos); | 
| Hai Shalom | ce48b4a | 2018-09-05 11:41:35 -0700 | [diff] [blame] | 4299 | #endif /* CONFIG_TESTING_OPTIONS */ | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 4300 | #ifdef CONFIG_SAE | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 4301 | } else if (os_strcmp(buf, "sae_password") == 0) { | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 4302 | if (parse_sae_password(bss, pos) < 0) { | 
|  | 4303 | wpa_printf(MSG_ERROR, "Line %d: Invalid sae_password", | 
|  | 4304 | line); | 
|  | 4305 | return 1; | 
|  | 4306 | } | 
|  | 4307 | #endif /* CONFIG_SAE */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4308 | } else if (os_strcmp(buf, "vendor_elements") == 0) { | 
| Dmitry Shmidt | 849734c | 2016-05-27 09:59:01 -0700 | [diff] [blame] | 4309 | if (parse_wpabuf_hex(line, buf, &bss->vendor_elements, pos)) | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4310 | return 1; | 
| Dmitry Shmidt | 849734c | 2016-05-27 09:59:01 -0700 | [diff] [blame] | 4311 | } else if (os_strcmp(buf, "assocresp_elements") == 0) { | 
|  | 4312 | if (parse_wpabuf_hex(line, buf, &bss->assocresp_elements, pos)) | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4313 | return 1; | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 4314 | } else if (os_strcmp(buf, "sae_anti_clogging_threshold") == 0 || | 
|  | 4315 | os_strcmp(buf, "anti_clogging_threshold") == 0) { | 
|  | 4316 | bss->anti_clogging_threshold = atoi(pos); | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 4317 | } else if (os_strcmp(buf, "sae_sync") == 0) { | 
|  | 4318 | bss->sae_sync = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4319 | } else if (os_strcmp(buf, "sae_groups") == 0) { | 
|  | 4320 | if (hostapd_parse_intlist(&bss->sae_groups, pos)) { | 
|  | 4321 | wpa_printf(MSG_ERROR, | 
|  | 4322 | "Line %d: Invalid sae_groups value '%s'", | 
|  | 4323 | line, pos); | 
|  | 4324 | return 1; | 
|  | 4325 | } | 
| Roshan Pius | 3a1667e | 2018-07-03 15:17:14 -0700 | [diff] [blame] | 4326 | } else if (os_strcmp(buf, "sae_require_mfp") == 0) { | 
|  | 4327 | bss->sae_require_mfp = atoi(pos); | 
| Hai Shalom | c356592 | 2019-10-28 11:58:20 -0700 | [diff] [blame] | 4328 | } else if (os_strcmp(buf, "sae_confirm_immediate") == 0) { | 
|  | 4329 | bss->sae_confirm_immediate = atoi(pos); | 
|  | 4330 | } else if (os_strcmp(buf, "sae_pwe") == 0) { | 
|  | 4331 | bss->sae_pwe = atoi(pos); | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4332 | } else if (os_strcmp(buf, "local_pwr_constraint") == 0) { | 
|  | 4333 | int val = atoi(pos); | 
|  | 4334 | if (val < 0 || val > 255) { | 
|  | 4335 | wpa_printf(MSG_ERROR, "Line %d: Invalid local_pwr_constraint %d (expected 0..255)", | 
|  | 4336 | line, val); | 
|  | 4337 | return 1; | 
|  | 4338 | } | 
|  | 4339 | conf->local_pwr_constraint = val; | 
|  | 4340 | } else if (os_strcmp(buf, "spectrum_mgmt_required") == 0) { | 
|  | 4341 | conf->spectrum_mgmt_required = atoi(pos); | 
| Dmitry Shmidt | 0207e23 | 2014-09-03 14:58:37 -0700 | [diff] [blame] | 4342 | } else if (os_strcmp(buf, "wowlan_triggers") == 0) { | 
|  | 4343 | os_free(bss->wowlan_triggers); | 
|  | 4344 | bss->wowlan_triggers = os_strdup(pos); | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 4345 | #ifdef CONFIG_FST | 
|  | 4346 | } else if (os_strcmp(buf, "fst_group_id") == 0) { | 
|  | 4347 | size_t len = os_strlen(pos); | 
|  | 4348 |  | 
|  | 4349 | if (!len || len >= sizeof(conf->fst_cfg.group_id)) { | 
|  | 4350 | wpa_printf(MSG_ERROR, | 
|  | 4351 | "Line %d: Invalid fst_group_id value '%s'", | 
|  | 4352 | line, pos); | 
|  | 4353 | return 1; | 
|  | 4354 | } | 
|  | 4355 |  | 
|  | 4356 | if (conf->fst_cfg.group_id[0]) { | 
|  | 4357 | wpa_printf(MSG_ERROR, | 
|  | 4358 | "Line %d: Duplicate fst_group value '%s'", | 
|  | 4359 | line, pos); | 
|  | 4360 | return 1; | 
|  | 4361 | } | 
|  | 4362 |  | 
|  | 4363 | os_strlcpy(conf->fst_cfg.group_id, pos, | 
|  | 4364 | sizeof(conf->fst_cfg.group_id)); | 
|  | 4365 | } else if (os_strcmp(buf, "fst_priority") == 0) { | 
|  | 4366 | char *endp; | 
|  | 4367 | long int val; | 
|  | 4368 |  | 
|  | 4369 | if (!*pos) { | 
|  | 4370 | wpa_printf(MSG_ERROR, | 
|  | 4371 | "Line %d: fst_priority value not supplied (expected 1..%u)", | 
|  | 4372 | line, FST_MAX_PRIO_VALUE); | 
|  | 4373 | return -1; | 
|  | 4374 | } | 
|  | 4375 |  | 
|  | 4376 | val = strtol(pos, &endp, 0); | 
|  | 4377 | if (*endp || val < 1 || val > FST_MAX_PRIO_VALUE) { | 
|  | 4378 | wpa_printf(MSG_ERROR, | 
|  | 4379 | "Line %d: Invalid fst_priority %ld (%s) (expected 1..%u)", | 
|  | 4380 | line, val, pos, FST_MAX_PRIO_VALUE); | 
|  | 4381 | return 1; | 
|  | 4382 | } | 
|  | 4383 | conf->fst_cfg.priority = (u8) val; | 
|  | 4384 | } else if (os_strcmp(buf, "fst_llt") == 0) { | 
|  | 4385 | char *endp; | 
|  | 4386 | long int val; | 
|  | 4387 |  | 
|  | 4388 | if (!*pos) { | 
|  | 4389 | wpa_printf(MSG_ERROR, | 
|  | 4390 | "Line %d: fst_llt value not supplied (expected 1..%u)", | 
|  | 4391 | line, FST_MAX_LLT_MS); | 
|  | 4392 | return -1; | 
|  | 4393 | } | 
|  | 4394 | val = strtol(pos, &endp, 0); | 
| Dmitry Shmidt | e466304 | 2016-04-04 10:07:49 -0700 | [diff] [blame] | 4395 | if (*endp || val < 1 || | 
|  | 4396 | (unsigned long int) val > FST_MAX_LLT_MS) { | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 4397 | wpa_printf(MSG_ERROR, | 
|  | 4398 | "Line %d: Invalid fst_llt %ld (%s) (expected 1..%u)", | 
|  | 4399 | line, val, pos, FST_MAX_LLT_MS); | 
|  | 4400 | return 1; | 
|  | 4401 | } | 
|  | 4402 | conf->fst_cfg.llt = (u32) val; | 
|  | 4403 | #endif /* CONFIG_FST */ | 
|  | 4404 | } else if (os_strcmp(buf, "track_sta_max_num") == 0) { | 
|  | 4405 | conf->track_sta_max_num = atoi(pos); | 
|  | 4406 | } else if (os_strcmp(buf, "track_sta_max_age") == 0) { | 
|  | 4407 | conf->track_sta_max_age = atoi(pos); | 
|  | 4408 | } else if (os_strcmp(buf, "no_probe_resp_if_seen_on") == 0) { | 
|  | 4409 | os_free(bss->no_probe_resp_if_seen_on); | 
|  | 4410 | bss->no_probe_resp_if_seen_on = os_strdup(pos); | 
|  | 4411 | } else if (os_strcmp(buf, "no_auth_if_seen_on") == 0) { | 
|  | 4412 | os_free(bss->no_auth_if_seen_on); | 
|  | 4413 | bss->no_auth_if_seen_on = os_strdup(pos); | 
| Dmitry Shmidt | 849734c | 2016-05-27 09:59:01 -0700 | [diff] [blame] | 4414 | } else if (os_strcmp(buf, "lci") == 0) { | 
|  | 4415 | wpabuf_free(conf->lci); | 
|  | 4416 | conf->lci = wpabuf_parse_bin(pos); | 
| Dmitry Shmidt | 9839ecd | 2016-11-07 11:05:47 -0800 | [diff] [blame] | 4417 | if (conf->lci && wpabuf_len(conf->lci) == 0) { | 
|  | 4418 | wpabuf_free(conf->lci); | 
|  | 4419 | conf->lci = NULL; | 
|  | 4420 | } | 
| Dmitry Shmidt | 849734c | 2016-05-27 09:59:01 -0700 | [diff] [blame] | 4421 | } else if (os_strcmp(buf, "civic") == 0) { | 
|  | 4422 | wpabuf_free(conf->civic); | 
|  | 4423 | conf->civic = wpabuf_parse_bin(pos); | 
| Dmitry Shmidt | 9839ecd | 2016-11-07 11:05:47 -0800 | [diff] [blame] | 4424 | if (conf->civic && wpabuf_len(conf->civic) == 0) { | 
|  | 4425 | wpabuf_free(conf->civic); | 
|  | 4426 | conf->civic = NULL; | 
|  | 4427 | } | 
| Dmitry Shmidt | 849734c | 2016-05-27 09:59:01 -0700 | [diff] [blame] | 4428 | } else if (os_strcmp(buf, "rrm_neighbor_report") == 0) { | 
|  | 4429 | if (atoi(pos)) | 
|  | 4430 | bss->radio_measurements[0] |= | 
|  | 4431 | WLAN_RRM_CAPS_NEIGHBOR_REPORT; | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 4432 | } else if (os_strcmp(buf, "rrm_beacon_report") == 0) { | 
|  | 4433 | if (atoi(pos)) | 
|  | 4434 | bss->radio_measurements[0] |= | 
|  | 4435 | WLAN_RRM_CAPS_BEACON_REPORT_PASSIVE | | 
|  | 4436 | WLAN_RRM_CAPS_BEACON_REPORT_ACTIVE | | 
|  | 4437 | WLAN_RRM_CAPS_BEACON_REPORT_TABLE; | 
| Dmitry Shmidt | d5ab1b5 | 2016-06-21 12:38:41 -0700 | [diff] [blame] | 4438 | } else if (os_strcmp(buf, "gas_address3") == 0) { | 
|  | 4439 | bss->gas_address3 = atoi(pos); | 
| Dmitry Shmidt | 9839ecd | 2016-11-07 11:05:47 -0800 | [diff] [blame] | 4440 | } else if (os_strcmp(buf, "stationary_ap") == 0) { | 
|  | 4441 | conf->stationary_ap = atoi(pos); | 
| Dmitry Shmidt | 7d17530 | 2016-09-06 13:11:34 -0700 | [diff] [blame] | 4442 | } else if (os_strcmp(buf, "ftm_responder") == 0) { | 
|  | 4443 | bss->ftm_responder = atoi(pos); | 
|  | 4444 | } else if (os_strcmp(buf, "ftm_initiator") == 0) { | 
|  | 4445 | bss->ftm_initiator = atoi(pos); | 
| Dmitry Shmidt | 9839ecd | 2016-11-07 11:05:47 -0800 | [diff] [blame] | 4446 | #ifdef CONFIG_FILS | 
|  | 4447 | } else if (os_strcmp(buf, "fils_cache_id") == 0) { | 
|  | 4448 | if (hexstr2bin(pos, bss->fils_cache_id, FILS_CACHE_ID_LEN)) { | 
|  | 4449 | wpa_printf(MSG_ERROR, | 
|  | 4450 | "Line %d: Invalid fils_cache_id '%s'", | 
|  | 4451 | line, pos); | 
|  | 4452 | return 1; | 
|  | 4453 | } | 
|  | 4454 | bss->fils_cache_id_set = 1; | 
| Dmitry Shmidt | 2933359 | 2017-01-09 12:27:11 -0800 | [diff] [blame] | 4455 | } else if (os_strcmp(buf, "fils_realm") == 0) { | 
|  | 4456 | if (parse_fils_realm(bss, pos) < 0) | 
|  | 4457 | return 1; | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 4458 | } else if (os_strcmp(buf, "fils_dh_group") == 0) { | 
|  | 4459 | bss->fils_dh_group = atoi(pos); | 
| Dmitry Shmidt | ebd93af | 2017-02-21 13:40:44 -0800 | [diff] [blame] | 4460 | } else if (os_strcmp(buf, "dhcp_server") == 0) { | 
|  | 4461 | if (hostapd_parse_ip_addr(pos, &bss->dhcp_server)) { | 
|  | 4462 | wpa_printf(MSG_ERROR, | 
|  | 4463 | "Line %d: invalid IP address '%s'", | 
|  | 4464 | line, pos); | 
|  | 4465 | return 1; | 
|  | 4466 | } | 
|  | 4467 | } else if (os_strcmp(buf, "dhcp_rapid_commit_proxy") == 0) { | 
|  | 4468 | bss->dhcp_rapid_commit_proxy = atoi(pos); | 
|  | 4469 | } else if (os_strcmp(buf, "fils_hlp_wait_time") == 0) { | 
|  | 4470 | bss->fils_hlp_wait_time = atoi(pos); | 
|  | 4471 | } else if (os_strcmp(buf, "dhcp_server_port") == 0) { | 
|  | 4472 | bss->dhcp_server_port = atoi(pos); | 
|  | 4473 | } else if (os_strcmp(buf, "dhcp_relay_port") == 0) { | 
|  | 4474 | bss->dhcp_relay_port = atoi(pos); | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 4475 | } else if (os_strcmp(buf, "fils_discovery_min_interval") == 0) { | 
|  | 4476 | bss->fils_discovery_min_int = atoi(pos); | 
|  | 4477 | } else if (os_strcmp(buf, "fils_discovery_max_interval") == 0) { | 
|  | 4478 | bss->fils_discovery_max_int = atoi(pos); | 
| Dmitry Shmidt | 9839ecd | 2016-11-07 11:05:47 -0800 | [diff] [blame] | 4479 | #endif /* CONFIG_FILS */ | 
| Dmitry Shmidt | abb90a3 | 2016-12-05 15:34:39 -0800 | [diff] [blame] | 4480 | } else if (os_strcmp(buf, "multicast_to_unicast") == 0) { | 
|  | 4481 | bss->multicast_to_unicast = atoi(pos); | 
| Sunil Ravi | 036cec5 | 2023-03-29 11:35:17 -0700 | [diff] [blame] | 4482 | } else if (os_strcmp(buf, "bridge_multicast_to_unicast") == 0) { | 
|  | 4483 | bss->bridge_multicast_to_unicast = atoi(pos); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 4484 | } else if (os_strcmp(buf, "broadcast_deauth") == 0) { | 
|  | 4485 | bss->broadcast_deauth = atoi(pos); | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 4486 | } else if (os_strcmp(buf, "notify_mgmt_frames") == 0) { | 
|  | 4487 | bss->notify_mgmt_frames = atoi(pos); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 4488 | #ifdef CONFIG_DPP | 
| Hai Shalom | c356592 | 2019-10-28 11:58:20 -0700 | [diff] [blame] | 4489 | } else if (os_strcmp(buf, "dpp_name") == 0) { | 
|  | 4490 | os_free(bss->dpp_name); | 
|  | 4491 | bss->dpp_name = os_strdup(pos); | 
|  | 4492 | } else if (os_strcmp(buf, "dpp_mud_url") == 0) { | 
|  | 4493 | os_free(bss->dpp_mud_url); | 
|  | 4494 | bss->dpp_mud_url = os_strdup(pos); | 
| Sunil Ravi | 89eba10 | 2022-09-13 21:04:37 -0700 | [diff] [blame] | 4495 | } else if (os_strcmp(buf, "dpp_extra_conf_req_name") == 0) { | 
|  | 4496 | os_free(bss->dpp_extra_conf_req_name); | 
|  | 4497 | bss->dpp_extra_conf_req_name = os_strdup(pos); | 
|  | 4498 | } else if (os_strcmp(buf, "dpp_extra_conf_req_value") == 0) { | 
|  | 4499 | os_free(bss->dpp_extra_conf_req_value); | 
|  | 4500 | bss->dpp_extra_conf_req_value = os_strdup(pos); | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 4501 | } else if (os_strcmp(buf, "dpp_connector") == 0) { | 
|  | 4502 | os_free(bss->dpp_connector); | 
|  | 4503 | bss->dpp_connector = os_strdup(pos); | 
|  | 4504 | } else if (os_strcmp(buf, "dpp_netaccesskey") == 0) { | 
|  | 4505 | if (parse_wpabuf_hex(line, buf, &bss->dpp_netaccesskey, pos)) | 
|  | 4506 | return 1; | 
|  | 4507 | } else if (os_strcmp(buf, "dpp_netaccesskey_expiry") == 0) { | 
|  | 4508 | bss->dpp_netaccesskey_expiry = strtol(pos, NULL, 0); | 
|  | 4509 | } else if (os_strcmp(buf, "dpp_csign") == 0) { | 
|  | 4510 | if (parse_wpabuf_hex(line, buf, &bss->dpp_csign, pos)) | 
|  | 4511 | return 1; | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 4512 | #ifdef CONFIG_DPP2 | 
|  | 4513 | } else if (os_strcmp(buf, "dpp_controller") == 0) { | 
|  | 4514 | if (hostapd_dpp_controller_parse(bss, pos)) | 
|  | 4515 | return 1; | 
| Sunil Ravi | 89eba10 | 2022-09-13 21:04:37 -0700 | [diff] [blame] | 4516 | } else if (os_strcmp(buf, "dpp_relay_port") == 0) { | 
|  | 4517 | bss->dpp_relay_port = atoi(pos); | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 4518 | } else if (os_strcmp(buf, "dpp_configurator_connectivity") == 0) { | 
|  | 4519 | bss->dpp_configurator_connectivity = atoi(pos); | 
|  | 4520 | } else if (os_strcmp(buf, "dpp_pfs") == 0) { | 
|  | 4521 | int val = atoi(pos); | 
|  | 4522 |  | 
|  | 4523 | if (val < 0 || val > 2) { | 
|  | 4524 | wpa_printf(MSG_ERROR, | 
|  | 4525 | "Line %d: Invalid dpp_pfs value '%s'", | 
|  | 4526 | line, pos); | 
|  | 4527 | return -1; | 
|  | 4528 | } | 
|  | 4529 | bss->dpp_pfs = val; | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 4530 | #endif /* CONFIG_DPP2 */ | 
| Dmitry Shmidt | d2986c2 | 2017-10-23 14:22:09 -0700 | [diff] [blame] | 4531 | #endif /* CONFIG_DPP */ | 
|  | 4532 | #ifdef CONFIG_OWE | 
|  | 4533 | } else if (os_strcmp(buf, "owe_transition_bssid") == 0) { | 
|  | 4534 | if (hwaddr_aton(pos, bss->owe_transition_bssid)) { | 
|  | 4535 | wpa_printf(MSG_ERROR, | 
|  | 4536 | "Line %d: invalid owe_transition_bssid", | 
|  | 4537 | line); | 
|  | 4538 | return 1; | 
|  | 4539 | } | 
|  | 4540 | } else if (os_strcmp(buf, "owe_transition_ssid") == 0) { | 
|  | 4541 | size_t slen; | 
|  | 4542 | char *str = wpa_config_parse_string(pos, &slen); | 
|  | 4543 |  | 
|  | 4544 | if (!str || slen < 1 || slen > SSID_MAX_LEN) { | 
|  | 4545 | wpa_printf(MSG_ERROR, "Line %d: invalid SSID '%s'", | 
|  | 4546 | line, pos); | 
|  | 4547 | os_free(str); | 
|  | 4548 | return 1; | 
|  | 4549 | } | 
|  | 4550 | os_memcpy(bss->owe_transition_ssid, str, slen); | 
|  | 4551 | bss->owe_transition_ssid_len = slen; | 
|  | 4552 | os_free(str); | 
|  | 4553 | } else if (os_strcmp(buf, "owe_transition_ifname") == 0) { | 
|  | 4554 | os_strlcpy(bss->owe_transition_ifname, pos, | 
|  | 4555 | sizeof(bss->owe_transition_ifname)); | 
|  | 4556 | } else if (os_strcmp(buf, "owe_groups") == 0) { | 
|  | 4557 | if (hostapd_parse_intlist(&bss->owe_groups, pos)) { | 
|  | 4558 | wpa_printf(MSG_ERROR, | 
|  | 4559 | "Line %d: Invalid owe_groups value '%s'", | 
|  | 4560 | line, pos); | 
|  | 4561 | return 1; | 
|  | 4562 | } | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 4563 | } else if (os_strcmp(buf, "owe_ptk_workaround") == 0) { | 
|  | 4564 | bss->owe_ptk_workaround = atoi(pos); | 
|  | 4565 | #endif /* CONFIG_OWE */ | 
| Hai Shalom | 39ba6fc | 2019-01-22 12:40:38 -0800 | [diff] [blame] | 4566 | } else if (os_strcmp(buf, "coloc_intf_reporting") == 0) { | 
|  | 4567 | bss->coloc_intf_reporting = atoi(pos); | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 4568 | } else if (os_strcmp(buf, "multi_ap") == 0) { | 
|  | 4569 | int val = atoi(pos); | 
|  | 4570 |  | 
|  | 4571 | if (val < 0 || val > 3) { | 
|  | 4572 | wpa_printf(MSG_ERROR, "Line %d: Invalid multi_ap '%s'", | 
|  | 4573 | line, buf); | 
|  | 4574 | return -1; | 
|  | 4575 | } | 
|  | 4576 |  | 
|  | 4577 | bss->multi_ap = val; | 
|  | 4578 | } else if (os_strcmp(buf, "rssi_reject_assoc_rssi") == 0) { | 
|  | 4579 | conf->rssi_reject_assoc_rssi = atoi(pos); | 
|  | 4580 | } else if (os_strcmp(buf, "rssi_reject_assoc_timeout") == 0) { | 
|  | 4581 | conf->rssi_reject_assoc_timeout = atoi(pos); | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 4582 | } else if (os_strcmp(buf, "rssi_ignore_probe_request") == 0) { | 
|  | 4583 | conf->rssi_ignore_probe_request = atoi(pos); | 
| Hai Shalom | 74f70d4 | 2019-02-11 14:42:39 -0800 | [diff] [blame] | 4584 | } else if (os_strcmp(buf, "pbss") == 0) { | 
|  | 4585 | bss->pbss = atoi(pos); | 
| Hai Shalom | fdcde76 | 2020-04-02 11:19:20 -0700 | [diff] [blame] | 4586 | } else if (os_strcmp(buf, "transition_disable") == 0) { | 
|  | 4587 | bss->transition_disable = strtol(pos, NULL, 16); | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 4588 | #ifdef CONFIG_AIRTIME_POLICY | 
|  | 4589 | } else if (os_strcmp(buf, "airtime_mode") == 0) { | 
|  | 4590 | int val = atoi(pos); | 
|  | 4591 |  | 
|  | 4592 | if (val < 0 || val > AIRTIME_MODE_MAX) { | 
|  | 4593 | wpa_printf(MSG_ERROR, "Line %d: Unknown airtime_mode", | 
|  | 4594 | line); | 
|  | 4595 | return 1; | 
|  | 4596 | } | 
|  | 4597 | conf->airtime_mode = val; | 
|  | 4598 | } else if (os_strcmp(buf, "airtime_update_interval") == 0) { | 
|  | 4599 | conf->airtime_update_interval = atoi(pos); | 
|  | 4600 | } else if (os_strcmp(buf, "airtime_bss_weight") == 0) { | 
|  | 4601 | bss->airtime_weight = atoi(pos); | 
|  | 4602 | } else if (os_strcmp(buf, "airtime_bss_limit") == 0) { | 
|  | 4603 | int val = atoi(pos); | 
|  | 4604 |  | 
|  | 4605 | if (val < 0 || val > 1) { | 
|  | 4606 | wpa_printf(MSG_ERROR, | 
|  | 4607 | "Line %d: Invalid airtime_bss_limit (must be 0 or 1)", | 
|  | 4608 | line); | 
|  | 4609 | return 1; | 
|  | 4610 | } | 
|  | 4611 | bss->airtime_limit = val; | 
|  | 4612 | } else if (os_strcmp(buf, "airtime_sta_weight") == 0) { | 
|  | 4613 | if (add_airtime_weight(bss, pos) < 0) { | 
|  | 4614 | wpa_printf(MSG_ERROR, | 
|  | 4615 | "Line %d: Invalid airtime weight '%s'", | 
|  | 4616 | line, pos); | 
|  | 4617 | return 1; | 
|  | 4618 | } | 
|  | 4619 | #endif /* CONFIG_AIRTIME_POLICY */ | 
|  | 4620 | #ifdef CONFIG_MACSEC | 
|  | 4621 | } else if (os_strcmp(buf, "macsec_policy") == 0) { | 
|  | 4622 | int macsec_policy = atoi(pos); | 
|  | 4623 |  | 
|  | 4624 | if (macsec_policy < 0 || macsec_policy > 1) { | 
|  | 4625 | wpa_printf(MSG_ERROR, | 
|  | 4626 | "Line %d: invalid macsec_policy (%d): '%s'.", | 
|  | 4627 | line, macsec_policy, pos); | 
|  | 4628 | return 1; | 
|  | 4629 | } | 
|  | 4630 | bss->macsec_policy = macsec_policy; | 
|  | 4631 | } else if (os_strcmp(buf, "macsec_integ_only") == 0) { | 
|  | 4632 | int macsec_integ_only = atoi(pos); | 
|  | 4633 |  | 
|  | 4634 | if (macsec_integ_only < 0 || macsec_integ_only > 1) { | 
|  | 4635 | wpa_printf(MSG_ERROR, | 
|  | 4636 | "Line %d: invalid macsec_integ_only (%d): '%s'.", | 
|  | 4637 | line, macsec_integ_only, pos); | 
|  | 4638 | return 1; | 
|  | 4639 | } | 
|  | 4640 | bss->macsec_integ_only = macsec_integ_only; | 
|  | 4641 | } else if (os_strcmp(buf, "macsec_replay_protect") == 0) { | 
|  | 4642 | int macsec_replay_protect = atoi(pos); | 
|  | 4643 |  | 
|  | 4644 | if (macsec_replay_protect < 0 || macsec_replay_protect > 1) { | 
|  | 4645 | wpa_printf(MSG_ERROR, | 
|  | 4646 | "Line %d: invalid macsec_replay_protect (%d): '%s'.", | 
|  | 4647 | line, macsec_replay_protect, pos); | 
|  | 4648 | return 1; | 
|  | 4649 | } | 
|  | 4650 | bss->macsec_replay_protect = macsec_replay_protect; | 
|  | 4651 | } else if (os_strcmp(buf, "macsec_replay_window") == 0) { | 
|  | 4652 | bss->macsec_replay_window = atoi(pos); | 
| Sunil Ravi | 036cec5 | 2023-03-29 11:35:17 -0700 | [diff] [blame] | 4653 | } else if (os_strcmp(buf, "macsec_offload") == 0) { | 
|  | 4654 | int macsec_offload = atoi(pos); | 
|  | 4655 |  | 
|  | 4656 | if (macsec_offload < 0 || macsec_offload > 2) { | 
|  | 4657 | wpa_printf(MSG_ERROR, | 
|  | 4658 | "Line %d: invalid macsec_offload (%d): '%s'.", | 
|  | 4659 | line, macsec_offload, pos); | 
|  | 4660 | return 1; | 
|  | 4661 | } | 
|  | 4662 | bss->macsec_offload = macsec_offload; | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 4663 | } else if (os_strcmp(buf, "macsec_port") == 0) { | 
|  | 4664 | int macsec_port = atoi(pos); | 
|  | 4665 |  | 
|  | 4666 | if (macsec_port < 1 || macsec_port > 65534) { | 
|  | 4667 | wpa_printf(MSG_ERROR, | 
|  | 4668 | "Line %d: invalid macsec_port (%d): '%s'.", | 
|  | 4669 | line, macsec_port, pos); | 
|  | 4670 | return 1; | 
|  | 4671 | } | 
|  | 4672 | bss->macsec_port = macsec_port; | 
|  | 4673 | } else if (os_strcmp(buf, "mka_priority") == 0) { | 
|  | 4674 | int mka_priority = atoi(pos); | 
|  | 4675 |  | 
|  | 4676 | if (mka_priority < 0 || mka_priority > 255) { | 
|  | 4677 | wpa_printf(MSG_ERROR, | 
|  | 4678 | "Line %d: invalid mka_priority (%d): '%s'.", | 
|  | 4679 | line, mka_priority, pos); | 
|  | 4680 | return 1; | 
|  | 4681 | } | 
|  | 4682 | bss->mka_priority = mka_priority; | 
| Sunil Ravi | a04bd25 | 2022-05-02 22:54:18 -0700 | [diff] [blame] | 4683 | } else if (os_strcmp(buf, "macsec_csindex") == 0) { | 
|  | 4684 | int macsec_csindex = atoi(pos); | 
|  | 4685 |  | 
|  | 4686 | if (macsec_csindex < 0 || macsec_csindex > 1) { | 
|  | 4687 | wpa_printf(MSG_ERROR, | 
|  | 4688 | "Line %d: invalid macsec_csindex (%d): '%s'.", | 
|  | 4689 | line, macsec_csindex, pos); | 
|  | 4690 | return 1; | 
|  | 4691 | } | 
|  | 4692 | bss->macsec_csindex = macsec_csindex; | 
| Hai Shalom | 81f62d8 | 2019-07-22 12:10:00 -0700 | [diff] [blame] | 4693 | } else if (os_strcmp(buf, "mka_cak") == 0) { | 
|  | 4694 | size_t len = os_strlen(pos); | 
|  | 4695 |  | 
|  | 4696 | if (len > 2 * MACSEC_CAK_MAX_LEN || | 
|  | 4697 | (len != 2 * 16 && len != 2 * 32) || | 
|  | 4698 | hexstr2bin(pos, bss->mka_cak, len / 2)) { | 
|  | 4699 | wpa_printf(MSG_ERROR, "Line %d: Invalid MKA-CAK '%s'.", | 
|  | 4700 | line, pos); | 
|  | 4701 | return 1; | 
|  | 4702 | } | 
|  | 4703 | bss->mka_cak_len = len / 2; | 
|  | 4704 | bss->mka_psk_set |= MKA_PSK_SET_CAK; | 
|  | 4705 | } else if (os_strcmp(buf, "mka_ckn") == 0) { | 
|  | 4706 | size_t len = os_strlen(pos); | 
|  | 4707 |  | 
|  | 4708 | if (len > 2 * MACSEC_CKN_MAX_LEN || /* too long */ | 
|  | 4709 | len < 2 || /* too short */ | 
|  | 4710 | len % 2 != 0 /* not an integral number of bytes */) { | 
|  | 4711 | wpa_printf(MSG_ERROR, "Line %d: Invalid MKA-CKN '%s'.", | 
|  | 4712 | line, pos); | 
|  | 4713 | return 1; | 
|  | 4714 | } | 
|  | 4715 | bss->mka_ckn_len = len / 2; | 
|  | 4716 | if (hexstr2bin(pos, bss->mka_ckn, bss->mka_ckn_len)) { | 
|  | 4717 | wpa_printf(MSG_ERROR, "Line %d: Invalid MKA-CKN '%s'.", | 
|  | 4718 | line, pos); | 
|  | 4719 | return -1; | 
|  | 4720 | } | 
|  | 4721 | bss->mka_psk_set |= MKA_PSK_SET_CKN; | 
|  | 4722 | #endif /* CONFIG_MACSEC */ | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 4723 | } else if (os_strcmp(buf, "disable_11n") == 0) { | 
|  | 4724 | bss->disable_11n = !!atoi(pos); | 
|  | 4725 | } else if (os_strcmp(buf, "disable_11ac") == 0) { | 
|  | 4726 | bss->disable_11ac = !!atoi(pos); | 
|  | 4727 | } else if (os_strcmp(buf, "disable_11ax") == 0) { | 
|  | 4728 | bss->disable_11ax = !!atoi(pos); | 
| Sunil Ravi | a04bd25 | 2022-05-02 22:54:18 -0700 | [diff] [blame] | 4729 | } else if (os_strcmp(buf, "disable_11be") == 0) { | 
|  | 4730 | bss->disable_11be = !!atoi(pos); | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 4731 | #ifdef CONFIG_PASN | 
|  | 4732 | #ifdef CONFIG_TESTING_OPTIONS | 
|  | 4733 | } else if (os_strcmp(buf, "force_kdk_derivation") == 0) { | 
|  | 4734 | bss->force_kdk_derivation = atoi(pos); | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 4735 | } else if (os_strcmp(buf, "pasn_corrupt_mic") == 0) { | 
|  | 4736 | bss->pasn_corrupt_mic = atoi(pos); | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 4737 | #endif /* CONFIG_TESTING_OPTIONS */ | 
|  | 4738 | } else if (os_strcmp(buf, "pasn_groups") == 0) { | 
|  | 4739 | if (hostapd_parse_intlist(&bss->pasn_groups, pos)) { | 
|  | 4740 | wpa_printf(MSG_ERROR, | 
|  | 4741 | "Line %d: Invalid pasn_groups value '%s'", | 
|  | 4742 | line, pos); | 
|  | 4743 | return 1; | 
|  | 4744 | } | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 4745 | } else if (os_strcmp(buf, "pasn_comeback_after") == 0) { | 
|  | 4746 | bss->pasn_comeback_after = atoi(pos); | 
| Sunil Ravi | 640215c | 2023-06-28 23:08:09 +0000 | [diff] [blame] | 4747 | } else if (os_strcmp(buf, "pasn_noauth") == 0) { | 
|  | 4748 | bss->pasn_noauth = atoi(pos); | 
| Hai Shalom | 6084025 | 2021-02-19 19:02:11 -0800 | [diff] [blame] | 4749 | #endif /* CONFIG_PASN */ | 
| Hai Shalom | a20dcd7 | 2022-02-04 13:43:00 -0800 | [diff] [blame] | 4750 | } else if (os_strcmp(buf, "ext_capa_mask") == 0) { | 
|  | 4751 | if (get_hex_config(bss->ext_capa_mask, EXT_CAPA_MAX_LEN, | 
|  | 4752 | line, "ext_capa_mask", pos)) | 
|  | 4753 | return 1; | 
|  | 4754 | } else if (os_strcmp(buf, "ext_capa") == 0) { | 
|  | 4755 | if (get_hex_config(bss->ext_capa, EXT_CAPA_MAX_LEN, | 
|  | 4756 | line, "ext_capa", pos)) | 
|  | 4757 | return 1; | 
|  | 4758 | } else if (os_strcmp(buf, "rnr") == 0) { | 
|  | 4759 | bss->rnr = atoi(pos); | 
| Sunil Ravi | a04bd25 | 2022-05-02 22:54:18 -0700 | [diff] [blame] | 4760 | #ifdef CONFIG_IEEE80211BE | 
|  | 4761 | } else if (os_strcmp(buf, "ieee80211be") == 0) { | 
|  | 4762 | conf->ieee80211be = atoi(pos); | 
|  | 4763 | } else if (os_strcmp(buf, "eht_oper_chwidth") == 0) { | 
|  | 4764 | conf->eht_oper_chwidth = atoi(pos); | 
|  | 4765 | } else if (os_strcmp(buf, "eht_oper_centr_freq_seg0_idx") == 0) { | 
|  | 4766 | conf->eht_oper_centr_freq_seg0_idx = atoi(pos); | 
|  | 4767 | } else if (os_strcmp(buf, "eht_su_beamformer") == 0) { | 
|  | 4768 | conf->eht_phy_capab.su_beamformer = atoi(pos); | 
|  | 4769 | } else if (os_strcmp(buf, "eht_su_beamformee") == 0) { | 
|  | 4770 | conf->eht_phy_capab.su_beamformee = atoi(pos); | 
|  | 4771 | } else if (os_strcmp(buf, "eht_mu_beamformer") == 0) { | 
|  | 4772 | conf->eht_phy_capab.mu_beamformer = atoi(pos); | 
| Sunil Ravi | 036cec5 | 2023-03-29 11:35:17 -0700 | [diff] [blame] | 4773 | } else if (os_strcmp(buf, "punct_bitmap") == 0) { | 
| Sunil Ravi | eb83e2a | 2024-06-28 17:34:56 +0000 | [diff] [blame] | 4774 | conf->punct_bitmap = atoi(pos); | 
| Sunil Ravi | 036cec5 | 2023-03-29 11:35:17 -0700 | [diff] [blame] | 4775 | } else if (os_strcmp(buf, "punct_acs_threshold") == 0) { | 
|  | 4776 | int val = atoi(pos); | 
|  | 4777 |  | 
|  | 4778 | if (val < 0 || val > 100) { | 
|  | 4779 | wpa_printf(MSG_ERROR, | 
|  | 4780 | "Line %d: punct_acs_threshold must be between 0 and 100", | 
|  | 4781 | line); | 
|  | 4782 | return 1; | 
|  | 4783 | } | 
|  | 4784 | conf->punct_acs_threshold = val; | 
| Sunil Ravi | 2a14cf1 | 2023-11-21 00:54:38 +0000 | [diff] [blame] | 4785 | } else if (os_strcmp(buf, "mld_ap") == 0) { | 
|  | 4786 | bss->mld_ap = !!atoi(pos); | 
| Sunil Ravi | 8861141 | 2024-06-28 17:34:56 +0000 | [diff] [blame] | 4787 | } else if (os_strcmp(buf, "mld_id") == 0) { | 
|  | 4788 | bss->mld_id = atoi(pos); | 
| Sunil Ravi | 2a14cf1 | 2023-11-21 00:54:38 +0000 | [diff] [blame] | 4789 | } else if (os_strcmp(buf, "mld_addr") == 0) { | 
|  | 4790 | if (hwaddr_aton(pos, bss->mld_addr)) { | 
|  | 4791 | wpa_printf(MSG_ERROR, "Line %d: Invalid mld_addr", | 
|  | 4792 | line); | 
|  | 4793 | return 1; | 
|  | 4794 | } | 
| Sunil Ravi | a04bd25 | 2022-05-02 22:54:18 -0700 | [diff] [blame] | 4795 | #endif /* CONFIG_IEEE80211BE */ | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4796 | } else { | 
|  | 4797 | wpa_printf(MSG_ERROR, | 
|  | 4798 | "Line %d: unknown configuration item '%s'", | 
|  | 4799 | line, buf); | 
|  | 4800 | return 1; | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 4801 | } | 
|  | 4802 |  | 
| Dmitry Shmidt | d5dc24e | 2014-03-12 14:22:04 -0700 | [diff] [blame] | 4803 | return 0; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4804 | } | 
|  | 4805 |  | 
|  | 4806 |  | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4807 | /** | 
|  | 4808 | * hostapd_config_read - Read and parse a configuration file | 
|  | 4809 | * @fname: Configuration file name (including path, if needed) | 
|  | 4810 | * Returns: Allocated configuration data structure | 
|  | 4811 | */ | 
|  | 4812 | struct hostapd_config * hostapd_config_read(const char *fname) | 
|  | 4813 | { | 
|  | 4814 | struct hostapd_config *conf; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4815 | FILE *f; | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 4816 | char buf[4096], *pos; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4817 | int line = 0; | 
|  | 4818 | int errors = 0; | 
|  | 4819 | size_t i; | 
|  | 4820 |  | 
|  | 4821 | f = fopen(fname, "r"); | 
|  | 4822 | if (f == NULL) { | 
|  | 4823 | wpa_printf(MSG_ERROR, "Could not open configuration file '%s' " | 
|  | 4824 | "for reading.", fname); | 
|  | 4825 | return NULL; | 
|  | 4826 | } | 
|  | 4827 |  | 
|  | 4828 | conf = hostapd_config_defaults(); | 
|  | 4829 | if (conf == NULL) { | 
|  | 4830 | fclose(f); | 
|  | 4831 | return NULL; | 
|  | 4832 | } | 
|  | 4833 |  | 
|  | 4834 | /* set default driver based on configuration */ | 
|  | 4835 | conf->driver = wpa_drivers[0]; | 
|  | 4836 | if (conf->driver == NULL) { | 
|  | 4837 | wpa_printf(MSG_ERROR, "No driver wrappers registered!"); | 
|  | 4838 | hostapd_config_free(conf); | 
|  | 4839 | fclose(f); | 
|  | 4840 | return NULL; | 
|  | 4841 | } | 
|  | 4842 |  | 
| Dmitry Shmidt | 661b4f7 | 2014-09-29 14:58:27 -0700 | [diff] [blame] | 4843 | conf->last_bss = conf->bss[0]; | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4844 |  | 
|  | 4845 | while (fgets(buf, sizeof(buf), f)) { | 
| Dmitry Shmidt | 661b4f7 | 2014-09-29 14:58:27 -0700 | [diff] [blame] | 4846 | struct hostapd_bss_config *bss; | 
|  | 4847 |  | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4848 | bss = conf->last_bss; | 
|  | 4849 | line++; | 
|  | 4850 |  | 
|  | 4851 | if (buf[0] == '#') | 
|  | 4852 | continue; | 
|  | 4853 | pos = buf; | 
|  | 4854 | while (*pos != '\0') { | 
|  | 4855 | if (*pos == '\n') { | 
|  | 4856 | *pos = '\0'; | 
|  | 4857 | break; | 
|  | 4858 | } | 
|  | 4859 | pos++; | 
|  | 4860 | } | 
|  | 4861 | if (buf[0] == '\0') | 
|  | 4862 | continue; | 
|  | 4863 |  | 
|  | 4864 | pos = os_strchr(buf, '='); | 
|  | 4865 | if (pos == NULL) { | 
|  | 4866 | wpa_printf(MSG_ERROR, "Line %d: invalid line '%s'", | 
|  | 4867 | line, buf); | 
|  | 4868 | errors++; | 
|  | 4869 | continue; | 
|  | 4870 | } | 
|  | 4871 | *pos = '\0'; | 
|  | 4872 | pos++; | 
|  | 4873 | errors += hostapd_config_fill(conf, bss, buf, pos, line); | 
|  | 4874 | } | 
|  | 4875 |  | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 4876 | fclose(f); | 
|  | 4877 |  | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4878 | for (i = 0; i < conf->num_bss; i++) | 
| Dmitry Shmidt | 7175743 | 2014-06-02 13:50:35 -0700 | [diff] [blame] | 4879 | hostapd_set_security_params(conf->bss[i], 1); | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 4880 |  | 
| Dmitry Shmidt | 344abd3 | 2014-01-14 13:17:00 -0800 | [diff] [blame] | 4881 | if (hostapd_config_check(conf, 1)) | 
| Dmitry Shmidt | 8d520ff | 2011-05-09 14:06:53 -0700 | [diff] [blame] | 4882 | errors++; | 
|  | 4883 |  | 
|  | 4884 | #ifndef WPA_IGNORE_CONFIG_ERRORS | 
|  | 4885 | if (errors) { | 
|  | 4886 | wpa_printf(MSG_ERROR, "%d errors found in configuration file " | 
|  | 4887 | "'%s'", errors, fname); | 
|  | 4888 | hostapd_config_free(conf); | 
|  | 4889 | conf = NULL; | 
|  | 4890 | } | 
|  | 4891 | #endif /* WPA_IGNORE_CONFIG_ERRORS */ | 
|  | 4892 |  | 
|  | 4893 | return conf; | 
|  | 4894 | } | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4895 |  | 
|  | 4896 |  | 
|  | 4897 | int hostapd_set_iface(struct hostapd_config *conf, | 
| Dmitry Shmidt | d80a401 | 2015-11-05 16:35:40 -0800 | [diff] [blame] | 4898 | struct hostapd_bss_config *bss, const char *field, | 
|  | 4899 | char *value) | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4900 | { | 
|  | 4901 | int errors; | 
|  | 4902 | size_t i; | 
|  | 4903 |  | 
|  | 4904 | errors = hostapd_config_fill(conf, bss, field, value, 0); | 
|  | 4905 | if (errors) { | 
|  | 4906 | wpa_printf(MSG_INFO, "Failed to set configuration field '%s' " | 
|  | 4907 | "to value '%s'", field, value); | 
|  | 4908 | return -1; | 
|  | 4909 | } | 
|  | 4910 |  | 
|  | 4911 | for (i = 0; i < conf->num_bss; i++) | 
| Dmitry Shmidt | 7175743 | 2014-06-02 13:50:35 -0700 | [diff] [blame] | 4912 | hostapd_set_security_params(conf->bss[i], 0); | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4913 |  | 
| Dmitry Shmidt | 344abd3 | 2014-01-14 13:17:00 -0800 | [diff] [blame] | 4914 | if (hostapd_config_check(conf, 0)) { | 
| Dmitry Shmidt | 0494959 | 2012-07-19 12:16:46 -0700 | [diff] [blame] | 4915 | wpa_printf(MSG_ERROR, "Configuration check failed"); | 
|  | 4916 | return -1; | 
|  | 4917 | } | 
|  | 4918 |  | 
|  | 4919 | return 0; | 
|  | 4920 | } |