Updated to hostap_2_6
[mech_eap.git] / libeap / src / ap / neighbor_db.c
1 /*
2  * hostapd / Neighboring APs DB
3  * Copyright(c) 2013 - 2016 Intel Mobile Communications GmbH.
4  * Copyright(c) 2011 - 2016 Intel Corporation. All rights reserved.
5  *
6  * This software may be distributed under the terms of the BSD license.
7  * See README for more details.
8  */
9
10 #include "utils/includes.h"
11
12 #include "utils/common.h"
13 #include "hostapd.h"
14 #include "neighbor_db.h"
15
16
17 struct hostapd_neighbor_entry *
18 hostapd_neighbor_get(struct hostapd_data *hapd, const u8 *bssid,
19                      const struct wpa_ssid_value *ssid)
20 {
21         struct hostapd_neighbor_entry *nr;
22
23         dl_list_for_each(nr, &hapd->nr_db, struct hostapd_neighbor_entry,
24                          list) {
25                 if (os_memcmp(bssid, nr->bssid, ETH_ALEN) == 0 &&
26                     (!ssid ||
27                      (ssid->ssid_len == nr->ssid.ssid_len &&
28                       os_memcmp(ssid->ssid, nr->ssid.ssid,
29                                 ssid->ssid_len) == 0)))
30                         return nr;
31         }
32         return NULL;
33 }
34
35
36 static void hostapd_neighbor_clear_entry(struct hostapd_neighbor_entry *nr)
37 {
38         wpabuf_free(nr->nr);
39         nr->nr = NULL;
40         wpabuf_free(nr->lci);
41         nr->lci = NULL;
42         wpabuf_free(nr->civic);
43         nr->civic = NULL;
44         os_memset(nr->bssid, 0, sizeof(nr->bssid));
45         os_memset(&nr->ssid, 0, sizeof(nr->ssid));
46 }
47
48
49 static struct hostapd_neighbor_entry *
50 hostapd_neighbor_add(struct hostapd_data *hapd)
51 {
52         struct hostapd_neighbor_entry *nr;
53
54         nr = os_zalloc(sizeof(struct hostapd_neighbor_entry));
55         if (!nr)
56                 return NULL;
57
58         dl_list_add(&hapd->nr_db, &nr->list);
59
60         return nr;
61 }
62
63
64 int hostapd_neighbor_set(struct hostapd_data *hapd, const u8 *bssid,
65                          const struct wpa_ssid_value *ssid,
66                          const struct wpabuf *nr, const struct wpabuf *lci,
67                          const struct wpabuf *civic)
68 {
69         struct hostapd_neighbor_entry *entry;
70
71         entry = hostapd_neighbor_get(hapd, bssid, ssid);
72         if (!entry)
73                 entry = hostapd_neighbor_add(hapd);
74         if (!entry)
75                 return -1;
76
77         hostapd_neighbor_clear_entry(entry);
78
79         os_memcpy(entry->bssid, bssid, ETH_ALEN);
80         os_memcpy(&entry->ssid, ssid, sizeof(entry->ssid));
81
82         entry->nr = wpabuf_dup(nr);
83         if (!entry->nr)
84                 goto fail;
85
86         if (lci) {
87                 entry->lci = wpabuf_dup(lci);
88                 if (!entry->lci || os_get_time(&entry->lci_date))
89                         goto fail;
90         }
91
92         if (civic) {
93                 entry->civic = wpabuf_dup(civic);
94                 if (!entry->civic)
95                         goto fail;
96         }
97
98         return 0;
99
100 fail:
101         hostapd_neighbor_remove(hapd, bssid, ssid);
102         return -1;
103 }
104
105
106 int hostapd_neighbor_remove(struct hostapd_data *hapd, const u8 *bssid,
107                             const struct wpa_ssid_value *ssid)
108 {
109         struct hostapd_neighbor_entry *nr;
110
111         nr = hostapd_neighbor_get(hapd, bssid, ssid);
112         if (!nr)
113                 return -1;
114
115         hostapd_neighbor_clear_entry(nr);
116         dl_list_del(&nr->list);
117         os_free(nr);
118
119         return 0;
120 }
121
122
123 void hostpad_free_neighbor_db(struct hostapd_data *hapd)
124 {
125         struct hostapd_neighbor_entry *nr, *prev;
126
127         dl_list_for_each_safe(nr, prev, &hapd->nr_db,
128                               struct hostapd_neighbor_entry, list) {
129                 hostapd_neighbor_clear_entry(nr);
130                 dl_list_del(&nr->list);
131                 os_free(nr);
132         }
133 }