]> git.ipfire.org Git - thirdparty/hostap.git/commitdiff
WNM: Simplify how candidate subelements are stored
authorJouni Malinen <j@w1.fi>
Sat, 22 Nov 2014 13:37:27 +0000 (15:37 +0200)
committerJouni Malinen <j@w1.fi>
Sat, 22 Nov 2014 16:06:37 +0000 (18:06 +0200)
There is no need to use a separately allocated data structures for this.
A bitfield indicating which information is present and variables within
struct neighbor_report are simpler to use and more efficient.

Signed-off-by: Jouni Malinen <j@w1.fi>
wpa_supplicant/wnm_sta.c
wpa_supplicant/wnm_sta.h

index aa22223a0c41eb54a651bacb6c06af04d2052f0d..8dea07ade421a18a6f803bb9d14c77be0e831ac0 100644 (file)
@@ -309,13 +309,7 @@ void wnm_deallocate_memory(struct wpa_supplicant *wpa_s)
        int i;
 
        for (i = 0; i < wpa_s->wnm_num_neighbor_report; i++) {
-               os_free(wpa_s->wnm_neighbor_report_elements[i].tsf_info);
-               os_free(wpa_s->wnm_neighbor_report_elements[i].con_coun_str);
-               os_free(wpa_s->wnm_neighbor_report_elements[i].bss_tran_can);
-               os_free(wpa_s->wnm_neighbor_report_elements[i].bss_term_dur);
-               os_free(wpa_s->wnm_neighbor_report_elements[i].bearing);
                os_free(wpa_s->wnm_neighbor_report_elements[i].meas_pilot);
-               os_free(wpa_s->wnm_neighbor_report_elements[i].rrm_cap);
                os_free(wpa_s->wnm_neighbor_report_elements[i].mul_bssid);
        }
 
@@ -334,12 +328,9 @@ static void wnm_parse_neighbor_report_elem(struct neighbor_report *rep,
                        wpa_printf(MSG_DEBUG, "WNM: Too short TSF");
                        break;
                }
-               os_free(rep->tsf_info);
-               rep->tsf_info = os_zalloc(sizeof(struct tsf_info));
-               if (rep->tsf_info == NULL)
-                       break;
-               os_memcpy(rep->tsf_info->tsf_offset, pos, 2);
-               os_memcpy(rep->tsf_info->beacon_interval, pos + 2, 2);
+               rep->tsf_offset = WPA_GET_LE16(pos);
+               rep->beacon_int = WPA_GET_LE16(pos + 2);
+               rep->tsf_present = 1;
                break;
        case WNM_NEIGHBOR_CONDENSED_COUNTRY_STRING:
                if (elen < 2) {
@@ -347,12 +338,8 @@ static void wnm_parse_neighbor_report_elem(struct neighbor_report *rep,
                                   "country string");
                        break;
                }
-               os_free(rep->con_coun_str);
-               rep->con_coun_str =
-                       os_zalloc(sizeof(struct condensed_country_string));
-               if (rep->con_coun_str == NULL)
-                       break;
-               os_memcpy(rep->con_coun_str->country_string, pos, 2);
+               os_memcpy(rep->country, pos, 2);
+               rep->country_present = 1;
                break;
        case WNM_NEIGHBOR_BSS_TRANSITION_CANDIDATE:
                if (elen < 1) {
@@ -360,25 +347,13 @@ static void wnm_parse_neighbor_report_elem(struct neighbor_report *rep,
                                   "candidate");
                        break;
                }
-               os_free(rep->bss_tran_can);
-               rep->bss_tran_can =
-                       os_zalloc(sizeof(struct bss_transition_candidate));
-               if (rep->bss_tran_can == NULL)
-                       break;
-               rep->bss_tran_can->preference = pos[0];
+               rep->preference = pos[0];
+               rep->preference_present = 1;
                break;
        case WNM_NEIGHBOR_BSS_TERMINATION_DURATION:
-               if (elen < 10) {
-                       wpa_printf(MSG_DEBUG, "WNM: Too short BSS termination "
-                                  "duration");
-                       break;
-               }
-               os_free(rep->bss_term_dur);
-               rep->bss_term_dur =
-                       os_zalloc(sizeof(struct bss_termination_duration));
-               if (rep->bss_term_dur == NULL)
-                       break;
-               os_memcpy(rep->bss_term_dur->duration, pos, 10);
+               rep->bss_term_tsf = WPA_GET_LE64(pos);
+               rep->bss_term_dur = WPA_GET_LE16(pos + 8);
+               rep->bss_term_present = 1;
                break;
        case WNM_NEIGHBOR_BEARING:
                if (elen < 8) {
@@ -386,11 +361,10 @@ static void wnm_parse_neighbor_report_elem(struct neighbor_report *rep,
                                   "bearing");
                        break;
                }
-               os_free(rep->bearing);
-               rep->bearing = os_zalloc(sizeof(struct bearing));
-               if (rep->bearing == NULL)
-                       break;
-               os_memcpy(rep->bearing->bearing, pos, 8);
+               rep->bearing = WPA_GET_LE16(pos);
+               rep->distance = WPA_GET_LE32(pos + 2);
+               rep->rel_height = WPA_GET_LE16(pos + 2 + 4);
+               rep->bearing_present = 1;
                break;
        case WNM_NEIGHBOR_MEASUREMENT_PILOT:
                if (elen < 1) {
@@ -412,12 +386,8 @@ static void wnm_parse_neighbor_report_elem(struct neighbor_report *rep,
                                   "capabilities");
                        break;
                }
-               os_free(rep->rrm_cap);
-               rep->rrm_cap =
-                       os_zalloc(sizeof(struct rrm_enabled_capabilities));
-               if (rep->rrm_cap == NULL)
-                       break;
-               os_memcpy(rep->rrm_cap->capabilities, pos, 5);
+               os_memcpy(rep->rm_capab, pos, 5);
+               rep->rm_capab_present = 1;
                break;
        case WNM_NEIGHBOR_MULTIPLE_BSSID:
                if (elen < 1) {
@@ -632,8 +602,7 @@ static void wnm_dump_cand_list(struct wpa_supplicant *wpa_s)
                           i, MAC2STR(nei->bssid), nei->bssid_info,
                           nei->regulatory_class,
                           nei->channel_number, nei->phy_type,
-                          nei->bss_tran_can ? nei->bss_tran_can->preference :
-                          -1);
+                          nei->preference_present ? nei->preference : -1);
        }
 }
 
index 22a0730fa704e5a1cb3e2169cc66bc881a604a5d..1117c825852bd658a842dce6d9fbf5255f59b702 100644 (file)
@@ -9,37 +9,12 @@
 #ifndef WNM_STA_H
 #define WNM_STA_H
 
-struct tsf_info {
-       u8 tsf_offset[2];
-       u8 beacon_interval[2];
-};
-
-struct condensed_country_string {
-       u8 country_string[2];
-};
-
-struct bss_transition_candidate {
-       u8 preference;
-};
-
-struct bss_termination_duration {
-       u8 duration[10];
-};
-
-struct bearing {
-       u8 bearing[8];
-};
-
 struct measurement_pilot {
        u8 measurement_pilot;
        u8 subelem_len;
        u8 subelems[255];
 };
 
-struct rrm_enabled_capabilities {
-       u8 capabilities[5];
-};
-
 struct multiple_bssid {
        u8 max_bssid_indicator;
        u8 subelem_len;
@@ -52,13 +27,23 @@ struct neighbor_report {
        u8 regulatory_class;
        u8 channel_number;
        u8 phy_type;
-       struct tsf_info *tsf_info;
-       struct condensed_country_string *con_coun_str;
-       struct bss_transition_candidate *bss_tran_can;
-       struct bss_termination_duration *bss_term_dur;
-       struct bearing *bearing;
+       u8 preference; /* valid if preference_present=1 */
+       u16 tsf_offset; /* valid if tsf_present=1 */
+       u16 beacon_int; /* valid if tsf_present=1 */
+       char country[2]; /* valid if country_present=1 */
+       u8 rm_capab[5]; /* valid if rm_capab_present=1 */
+       u16 bearing; /* valid if bearing_present=1 */
+       u16 rel_height; /* valid if bearing_present=1 */
+       u32 distance; /* valid if bearing_present=1 */
+       u64 bss_term_tsf; /* valid if bss_term_present=1 */
+       u16 bss_term_dur; /* valid if bss_term_present=1 */
+       unsigned int preference_present:1;
+       unsigned int tsf_present:1;
+       unsigned int country_present:1;
+       unsigned int rm_capab_present:1;
+       unsigned int bearing_present:1;
+       unsigned int bss_term_present:1;
        struct measurement_pilot *meas_pilot;
-       struct rrm_enabled_capabilities *rrm_cap;
        struct multiple_bssid *mul_bssid;
 };