diff --git a/hostapd/config_file.c b/hostapd/config_file.c index 4b4967241..77950150d 100644 --- a/hostapd/config_file.c +++ b/hostapd/config_file.c @@ -3510,6 +3510,8 @@ static int hostapd_config_fill(struct hostapd_config *conf, WLAN_RRM_CAPS_NEIGHBOR_REPORT; } else if (os_strcmp(buf, "gas_address3") == 0) { bss->gas_address3 = atoi(pos); + } else if (os_strcmp(buf, "stationary_ap") == 0) { + conf->stationary_ap = atoi(pos); } else if (os_strcmp(buf, "ftm_responder") == 0) { bss->ftm_responder = atoi(pos); } else if (os_strcmp(buf, "ftm_initiator") == 0) { diff --git a/hostapd/ctrl_iface.c b/hostapd/ctrl_iface.c index 68751decf..0d86b4a4f 100644 --- a/hostapd/ctrl_iface.c +++ b/hostapd/ctrl_iface.c @@ -2174,6 +2174,7 @@ static int hostapd_ctrl_iface_set_neighbor(struct hostapd_data *hapd, char *buf) struct wpa_ssid_value ssid; u8 bssid[ETH_ALEN]; struct wpabuf *nr, *lci = NULL, *civic = NULL; + int stationary = 0; char *tmp; int ret; @@ -2252,8 +2253,15 @@ static int hostapd_ctrl_iface_set_neighbor(struct hostapd_data *hapd, char *buf) } } + if (!buf) + goto set; + + if (os_strstr(buf, "stat")) + stationary = 1; + set: - ret = hostapd_neighbor_set(hapd, bssid, &ssid, nr, lci, civic); + ret = hostapd_neighbor_set(hapd, bssid, &ssid, nr, lci, civic, + stationary); wpabuf_free(nr); wpabuf_free(lci); diff --git a/hostapd/hostapd.conf b/hostapd/hostapd.conf index 0574fa474..54c8b95e3 100644 --- a/hostapd/hostapd.conf +++ b/hostapd/hostapd.conf @@ -1940,6 +1940,12 @@ own_ip_addr=127.0.0.1 # This parameter only controls publishing via Extended Capabilities element. # Actual functionality is managed outside hostapd. #ftm_initiator=0 +# +# Stationary AP config indicates that the AP doesn't move hence location data +# can be considered as always up to date. If configured, LCI data will be sent +# as a radio measurement even if the request doesn't contain a max age element +# that allows sending of such data. Default: 0. +#stationary_ap=0 ##### TESTING OPTIONS ######################################################### # diff --git a/hostapd/hostapd_cli.c b/hostapd/hostapd_cli.c index 9a6e3cb77..8b8d7f92f 100644 --- a/hostapd/hostapd_cli.c +++ b/hostapd/hostapd_cli.c @@ -1255,14 +1255,14 @@ static int hostapd_cli_cmd_set_neighbor(struct wpa_ctrl *ctrl, int argc, char cmd[2048]; int res; - if (argc < 3 || argc > 5) { - printf("Invalid set_neighbor command: needs 3-5 arguments\n"); + if (argc < 3 || argc > 6) { + printf("Invalid set_neighbor command: needs 3-6 arguments\n"); return -1; } - res = os_snprintf(cmd, sizeof(cmd), "SET_NEIGHBOR %s %s %s %s %s", + res = os_snprintf(cmd, sizeof(cmd), "SET_NEIGHBOR %s %s %s %s %s %s", argv[0], argv[1], argv[2], argc >= 4 ? argv[3] : "", - argc == 5 ? argv[4] : ""); + argc >= 5 ? argv[4] : "", argc == 6 ? argv[5] : ""); if (os_snprintf_error(sizeof(cmd), res)) { printf("Too long SET_NEIGHBOR command.\n"); return -1; diff --git a/src/ap/ap_config.h b/src/ap/ap_config.h index 04b90b84a..ec476070f 100644 --- a/src/ap/ap_config.h +++ b/src/ap/ap_config.h @@ -713,6 +713,7 @@ struct hostapd_config { struct wpabuf *lci; struct wpabuf *civic; + int stationary_ap; }; diff --git a/src/ap/hostapd.c b/src/ap/hostapd.c index 9fafc7f45..f03db292e 100644 --- a/src/ap/hostapd.c +++ b/src/ap/hostapd.c @@ -1645,7 +1645,7 @@ static void hostapd_set_own_neighbor_report(struct hostapd_data *hapd) wpabuf_put_u8(nr, center_freq2); hostapd_neighbor_set(hapd, hapd->own_addr, &ssid, nr, hapd->iconf->lci, - hapd->iconf->civic); + hapd->iconf->civic, hapd->iconf->stationary_ap); wpabuf_free(nr); #endif /* NEED_AP_MLME */ diff --git a/src/ap/hostapd.h b/src/ap/hostapd.h index 919b18534..fd5aaedcc 100644 --- a/src/ap/hostapd.h +++ b/src/ap/hostapd.h @@ -109,6 +109,7 @@ struct hostapd_neighbor_entry { struct wpabuf *civic; /* LCI update time */ struct os_time lci_date; + int stationary; }; /** diff --git a/src/ap/neighbor_db.c b/src/ap/neighbor_db.c index c6cdbfce2..b8fd5924b 100644 --- a/src/ap/neighbor_db.c +++ b/src/ap/neighbor_db.c @@ -43,6 +43,7 @@ static void hostapd_neighbor_clear_entry(struct hostapd_neighbor_entry *nr) nr->civic = NULL; os_memset(nr->bssid, 0, sizeof(nr->bssid)); os_memset(&nr->ssid, 0, sizeof(nr->ssid)); + nr->stationary = 0; } @@ -64,7 +65,7 @@ hostapd_neighbor_add(struct hostapd_data *hapd) int hostapd_neighbor_set(struct hostapd_data *hapd, const u8 *bssid, const struct wpa_ssid_value *ssid, const struct wpabuf *nr, const struct wpabuf *lci, - const struct wpabuf *civic) + const struct wpabuf *civic, int stationary) { struct hostapd_neighbor_entry *entry; @@ -95,6 +96,8 @@ int hostapd_neighbor_set(struct hostapd_data *hapd, const u8 *bssid, goto fail; } + entry->stationary = stationary; + return 0; fail: diff --git a/src/ap/neighbor_db.h b/src/ap/neighbor_db.h index c22e043c1..ba46d8843 100644 --- a/src/ap/neighbor_db.h +++ b/src/ap/neighbor_db.h @@ -16,7 +16,7 @@ hostapd_neighbor_get(struct hostapd_data *hapd, const u8 *bssid, int hostapd_neighbor_set(struct hostapd_data *hapd, const u8 *bssid, const struct wpa_ssid_value *ssid, const struct wpabuf *nr, const struct wpabuf *lci, - const struct wpabuf *civic); + const struct wpabuf *civic, int stationary); int hostapd_neighbor_remove(struct hostapd_data *hapd, const u8 *bssid, const struct wpa_ssid_value *ssid); void hostpad_free_neighbor_db(struct hostapd_data *hapd); diff --git a/src/ap/rrm.c b/src/ap/rrm.c index 3569f955b..5ca87c0be 100644 --- a/src/ap/rrm.c +++ b/src/ap/rrm.c @@ -129,12 +129,12 @@ static int hostapd_check_lci_age(struct hostapd_neighbor_entry *nr, u16 max_age) struct os_time curr, diff; unsigned long diff_l; + if (nr->stationary || max_age == 0xffff) + return 1; + if (!max_age) return 0; - if (max_age == 0xffff) - return 1; - if (os_get_time(&curr)) return 0;