From e1023a388e29e6e4ba2fa65f71566afcd5c9cefb Mon Sep 17 00:00:00 2001 From: vemax78 Date: Fri, 25 Apr 2014 22:05:36 +0200 Subject: [PATCH] Add business logic of Authentication/Association in SplitMAC mode. --- src/ac/ac_dfa_configure.c | 28 +++ src/ac/ac_dfa_run.c | 2 +- src/ac/ac_execute.c | 6 +- src/ac/ac_ieee80211_data.c | 168 +++++++++++-- src/ac/ac_session.c | 4 + src/ac/ac_session.h | 8 +- src/ac/ac_session_data.c | 24 +- src/ac/ac_wlans.c | 292 ++++++++++++----------- src/ac/ac_wlans.h | 58 +++-- src/common/binding/ieee80211/ieee80211.h | 2 + src/wtp/binding/ieee80211/wifi_drivers.c | 156 +++++++----- src/wtp/binding/ieee80211/wifi_drivers.h | 5 +- src/wtp/binding/ieee80211/wifi_nl80211.c | 7 +- src/wtp/wtp_radio.c | 2 +- 14 files changed, 498 insertions(+), 264 deletions(-) diff --git a/src/ac/ac_dfa_configure.c b/src/ac/ac_dfa_configure.c index 911afb7..3ae8006 100644 --- a/src/ac/ac_dfa_configure.c +++ b/src/ac/ac_dfa_configure.c @@ -3,9 +3,34 @@ #include "capwap_array.h" #include "ac_session.h" #include "ac_json.h" +#include "ac_wlans.h" #include #include +/* */ +static void ac_dfa_state_configure_set_radio_configuration(struct ac_session_t* session, struct ac_json_ieee80211_wtpradio* wtpradio) { + int i; + + for (i = 0; i < RADIOID_MAX_COUNT; i++) { + struct ac_json_ieee80211_item* item = &wtpradio->items[i]; + + if (item->valid) { + struct ac_device* device = &session->wlans->devices[i]; + + /* Set rates */ + if (item->rateset || item->supportedrates) { + if (item->rateset) { + memcpy(device->supportedrates, item->rateset->rateset, item->rateset->ratesetcount); + device->supportedratescount = item->rateset->ratesetcount; + } else if (item->supportedrates) { + memcpy(device->supportedrates, item->supportedrates->supportedrates, item->supportedrates->supportedratescount); + device->supportedratescount = item->supportedrates->supportedratescount; + } + } + } + } +} + /* */ static struct ac_soap_response* ac_dfa_state_configure_parsing_request(struct ac_session_t* session, struct capwap_parsed_packet* packet) { int i; @@ -690,6 +715,9 @@ static uint32_t ac_dfa_state_configure_create_response(struct ac_session_t* sess if (ac_json_ieee80211_parsingjson(&wtpradio, jsonelement)) { /* Add IEEE802.11 message elements to packet */ ac_json_ieee80211_buildpacket(&wtpradio, txmngpacket); + + /* Retrieve frequency and rates configuration */ + ac_dfa_state_configure_set_radio_configuration(session, &wtpradio); } } diff --git a/src/ac/ac_dfa_run.c b/src/ac/ac_dfa_run.c index a8b52dc..7ada3f0 100644 --- a/src/ac/ac_dfa_run.c +++ b/src/ac/ac_dfa_run.c @@ -75,7 +75,7 @@ static void execute_ieee80211_wlan_configuration_addwlan(struct ac_session_t* se /* Get BSSID */ assignbssid = (struct capwap_80211_assignbssid_element*)capwap_get_message_element_data(packet, CAPWAP_ELEMENT_80211_ASSIGN_BSSID); if (assignbssid && (assignbssid->radioid == addwlan->radioid) && (assignbssid->wlanid == addwlan->wlanid)) { - wlan = ac_wlans_create_bssid(assignbssid->radioid, assignbssid->wlanid, assignbssid->bssid, addwlan); + wlan = ac_wlans_create_bssid(&session->wlans->devices[assignbssid->radioid - 1], assignbssid->wlanid, assignbssid->bssid, addwlan); /* Assign BSSID to session */ ac_session_data_send_action(session->sessiondata, AC_SESSION_DATA_ACTION_ASSIGN_BSSID, 0, &wlan, sizeof(struct ac_wlan*)); diff --git a/src/ac/ac_execute.c b/src/ac/ac_execute.c index 411e3d2..a883f93 100644 --- a/src/ac/ac_execute.c +++ b/src/ac/ac_execute.c @@ -532,6 +532,9 @@ static struct ac_session_t* ac_create_session(struct sockaddr_storage* wtpaddres memcpy(&session->connection.localaddr, acaddress, sizeof(struct sockaddr_storage)); memcpy(&session->connection.remoteaddr, wtpaddress, sizeof(struct sockaddr_storage)); + /* */ + ac_wlans_init(session); + /* */ session->count = 2; capwap_event_init(&session->changereference); @@ -618,9 +621,6 @@ static struct ac_session_data_t* ac_create_session_data(struct sockaddr_storage* sessiondata->count = 2; capwap_event_init(&sessiondata->changereference); - /* */ - ac_wlans_init(sessiondata); - /* */ sessiondata->timeout = capwap_timeout_init(); sessiondata->idtimercontrol = capwap_timeout_createtimer(sessiondata->timeout); diff --git a/src/ac/ac_ieee80211_data.c b/src/ac/ac_ieee80211_data.c index df1b7e2..e640398 100644 --- a/src/ac/ac_ieee80211_data.c +++ b/src/ac/ac_ieee80211_data.c @@ -26,6 +26,7 @@ static void ac_ieee80211_mgmt_authentication_packet(struct ac_session_data_t* se int ielength; struct ieee80211_ie_items ieitems; struct ac_station* station; + struct ac_wlan* wlan; /* Parsing Information Elements */ ielength = mgmtlength - (sizeof(struct ieee80211_header) + sizeof(mgmt->authetication)); @@ -35,24 +36,79 @@ static void ac_ieee80211_mgmt_authentication_packet(struct ac_session_data_t* se /* */ if (memcmp(mgmt->bssid, mgmt->sa, MACADDRESS_EUI48_LENGTH) && !memcmp(mgmt->bssid, mgmt->da, MACADDRESS_EUI48_LENGTH)) { - station = ac_stations_create_station(sessiondata, radioid, mgmt->bssid, mgmt->sa); + station = ac_stations_create_station(sessiondata->session, radioid, mgmt->bssid, mgmt->sa); + if (!station || !station->wlan) { + return; + } /* */ capwap_logging_info("Receive IEEE802.11 Authentication Request from %s station", station->addrtext); /* A station is removed if the association does not complete within a given period of time */ station->timeoutaction = AC_STATION_TIMEOUT_ACTION_DEAUTHENTICATE; - station->idtimeout = capwap_timeout_set(sessiondata->timeout, station->idtimeout, AC_STATION_TIMEOUT_ASSOCIATION_COMPLETE, ac_stations_timeout, station, sessiondata); + station->idtimeout = capwap_timeout_set(sessiondata->timeout, station->idtimeout, AC_STATION_TIMEOUT_ASSOCIATION_COMPLETE, ac_stations_timeout, station, sessiondata->session); /* */ - if (station->wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_LOCAL) { - /* TODO */ - } else if (station->wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_SPLIT) { + wlan = station->wlan; + if (wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_LOCAL) { /* TODO */ + } else if (wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_SPLIT) { + uint16_t algorithm; + uint16_t transactionseqnumber; + uint16_t responsestatuscode; + uint8_t buffer[IEEE80211_MTU]; + struct ieee80211_authentication_params ieee80211_params; + int responselength; + + /* Parsing Information Elements */ + if (ieee80211_retrieve_information_elements_position(&ieitems, &mgmt->authetication.ie[0], ielength)) { + capwap_logging_info("Invalid IEEE802.11 Authentication Request from %s station", station->addrtext); + return; + } + + /* */ + algorithm = __le16_to_cpu(mgmt->authetication.algorithm); + transactionseqnumber = __le16_to_cpu(mgmt->authetication.transactionseqnumber); + + /* */ + responsestatuscode = IEEE80211_STATUS_NOT_SUPPORTED_AUTHENTICATION_ALGORITHM; + if ((algorithm == IEEE80211_AUTHENTICATION_ALGORITHM_OPEN) && (wlan->authmode == CAPWAP_ADD_WLAN_AUTHTYPE_OPEN)) { + if (transactionseqnumber == 1) { + responsestatuscode = IEEE80211_STATUS_SUCCESS; + station->authalgorithm = IEEE80211_AUTHENTICATION_ALGORITHM_OPEN; + } else { + responsestatuscode = IEEE80211_STATUS_UNKNOWN_AUTHENTICATION_TRANSACTION; + } + } else if ((algorithm == IEEE80211_AUTHENTICATION_ALGORITHM_SHARED_KEY) && (wlan->authmode == CAPWAP_ADD_WLAN_AUTHTYPE_WEP)) { + /* TODO */ + } + + /* Create authentication packet */ + memset(&ieee80211_params, 0, sizeof(struct ieee80211_authentication_params)); + memcpy(ieee80211_params.bssid, wlan->address, MACADDRESS_EUI48_LENGTH); + memcpy(ieee80211_params.station, mgmt->sa, MACADDRESS_EUI48_LENGTH); + ieee80211_params.algorithm = algorithm; + ieee80211_params.transactionseqnumber = transactionseqnumber + 1; + ieee80211_params.statuscode = responsestatuscode; + + responselength = ieee80211_create_authentication_response(buffer, sizeof(buffer), &ieee80211_params); + if (responselength > 0) { + /* Send authentication response */ + if (!ac_session_data_send_data_packet(sessiondata, wlan->device->radioid, wlan->wlanid, buffer, responselength, 1)) { + capwap_logging_info("Sent IEEE802.11 Authentication Response to %s station with %d status code", station->addrtext, (int)responsestatuscode); + station->flags |= AC_STATION_FLAGS_AUTHENTICATED; + } else { + capwap_logging_warning("Unable to send IEEE802.11 Authentication Response to %s station", station->addrtext); + ac_stations_delete_station(sessiondata->session, station); + } + } else { + capwap_logging_warning("Unable to create IEEE802.11 Authentication Response to %s station", station->addrtext); + ac_stations_delete_station(sessiondata->session, station); + } } } else if (!memcmp(mgmt->bssid, mgmt->sa, MACADDRESS_EUI48_LENGTH) && memcmp(mgmt->bssid, mgmt->da, MACADDRESS_EUI48_LENGTH)) { - station = ac_stations_get_station(sessiondata, radioid, mgmt->bssid, mgmt->da); - if (station && (station->wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_LOCAL)) { + station = ac_stations_get_station(sessiondata->session, radioid, mgmt->bssid, mgmt->da); + if (station && station->wlan && (station->wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_LOCAL)) { uint16_t algorithm; uint16_t transactionseqnumber; uint16_t statuscode; @@ -83,6 +139,7 @@ static void ac_ieee80211_mgmt_association_request_packet(struct ac_session_data_ int ielength; struct ieee80211_ie_items ieitems; struct ac_station* station; + struct ac_wlan* wlan; /* Parsing Information Elements */ ielength = mgmtlength - (sizeof(struct ieee80211_header) + sizeof(mgmt->associationrequest)); @@ -92,11 +149,23 @@ static void ac_ieee80211_mgmt_association_request_packet(struct ac_session_data_ /* Get station */ if (memcmp(mgmt->bssid, mgmt->sa, MACADDRESS_EUI48_LENGTH) && !memcmp(mgmt->bssid, mgmt->da, MACADDRESS_EUI48_LENGTH)) { - station = ac_stations_get_station(sessiondata, radioid, mgmt->bssid, mgmt->sa); + station = ac_stations_get_station(sessiondata->session, radioid, mgmt->bssid, mgmt->sa); + if (!station || !station->wlan) { + return; + } /* */ capwap_logging_info("Receive IEEE802.11 Association Request from %s station", station->addrtext); + /* */ + wlan = station->wlan; + if (!(station->flags & AC_STATION_FLAGS_AUTHENTICATED)) { + /* Invalid station, delete station */ + capwap_logging_info("Receive IEEE802.11 Association Request from %s unauthorized station", station->addrtext); + ac_stations_delete_station(sessiondata->session, station); + return; + } + /* Get Station Info */ station->capability = __le16_to_cpu(mgmt->associationrequest.capability); station->listeninterval = __le16_to_cpu(mgmt->associationrequest.listeninterval); @@ -111,13 +180,76 @@ static void ac_ieee80211_mgmt_association_request_packet(struct ac_session_data_ } /* */ - if (station->wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_LOCAL) { - /* TODO */ - } else if (station->wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_SPLIT) { + if (wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_LOCAL) { /* TODO */ + } else if (wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_SPLIT) { + int responselength; + struct ieee80211_ie_items ieitems; + struct ieee80211_associationresponse_params ieee80211_params; + uint16_t resultstatuscode; + uint8_t buffer[IEEE80211_MTU]; - /* Active Station */ - ac_stations_authorize_station(sessiondata, station); + /* Parsing Information Elements */ + if (ieee80211_retrieve_information_elements_position(&ieitems, &mgmt->associationrequest.ie[0], ielength)) { + capwap_logging_info("Invalid IEEE802.11 Association Request from %s station", station->addrtext); + ac_stations_delete_station(sessiondata->session, station); + return; + } + + /* Verify SSID */ + if (ieee80211_is_valid_ssid(wlan->ssid, ieitems.ssid, NULL) != IEEE80211_VALID_SSID) { + resultstatuscode = IEEE80211_STATUS_UNSPECIFIED_FAILURE; + } else { + /* Check supported rates */ + if (!ieitems.supported_rates || ((ieitems.supported_rates->len + (ieitems.extended_supported_rates ? ieitems.extended_supported_rates->len : 0)) > sizeof(station->supportedrates))) { + resultstatuscode = IEEE80211_STATUS_UNSPECIFIED_FAILURE; + } else { + station->capability = __le16_to_cpu(mgmt->associationrequest.capability); + station->listeninterval = __le16_to_cpu(mgmt->associationrequest.listeninterval); + if (ieee80211_aid_create(wlan->aidbitfield, &station->aid)) { + resultstatuscode = IEEE80211_STATUS_AP_UNABLE_TO_HANDLE_NEW_STA; + } else { + /* Get supported rates */ + station->supportedratescount = ieitems.supported_rates->len; + memcpy(station->supportedrates, ieitems.supported_rates->rates, ieitems.supported_rates->len); + if (ieitems.extended_supported_rates) { + station->supportedratescount += ieitems.extended_supported_rates->len; + memcpy(&station->supportedrates[ieitems.supported_rates->len], ieitems.extended_supported_rates->rates, ieitems.extended_supported_rates->len); + } + + /* */ + resultstatuscode = IEEE80211_STATUS_SUCCESS; + } + } + } + + /* Create association response packet */ + memset(&ieee80211_params, 0, sizeof(struct ieee80211_authentication_params)); + memcpy(ieee80211_params.bssid, wlan->address, ETH_ALEN); + memcpy(ieee80211_params.station, mgmt->sa, ETH_ALEN); + ieee80211_params.capability = wlan->capability; + ieee80211_params.statuscode = resultstatuscode; + ieee80211_params.aid = IEEE80211_AID_FIELD | station->aid; + memcpy(ieee80211_params.supportedrates, wlan->device->supportedrates, wlan->device->supportedratescount); + ieee80211_params.supportedratescount = wlan->device->supportedratescount; + + responselength = ieee80211_create_associationresponse_response(buffer, sizeof(buffer), &ieee80211_params); + if (responselength > 0) { + /* Send association response */ + if (!ac_session_data_send_data_packet(sessiondata, wlan->device->radioid, wlan->wlanid, buffer, responselength, 1)) { + capwap_logging_info("Sent IEEE802.11 Association Response to %s station with %d status code", station->addrtext, (int)resultstatuscode); + + /* Active Station */ + station->flags |= AC_STATION_FLAGS_ASSOCIATE; + ac_stations_authorize_station(sessiondata->session, station); + } else { + capwap_logging_warning("Unable to send IEEE802.11 Association Response to %s station", station->addrtext); + ac_stations_delete_station(sessiondata->session, station); + } + } else { + capwap_logging_warning("Unable to create IEEE802.11 Association Response to %s station", station->addrtext); + ac_stations_delete_station(sessiondata->session, station); + } } } } @@ -137,8 +269,8 @@ static void ac_ieee80211_mgmt_association_response_packet(struct ac_session_data /* Get station */ if (!memcmp(mgmt->bssid, mgmt->sa, MACADDRESS_EUI48_LENGTH) && memcmp(mgmt->bssid, mgmt->da, MACADDRESS_EUI48_LENGTH)) { - station = ac_stations_get_station(sessiondata, radioid, mgmt->bssid, mgmt->da); - if (station && (station->wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_LOCAL)) { + station = ac_stations_get_station(sessiondata->session, radioid, mgmt->bssid, mgmt->da); + if (station && station->wlan && (station->wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_LOCAL)) { capwap_logging_info("Receive IEEE802.11 Association Response to %s station with %d status code", station->addrtext, (int)mgmt->associationresponse.statuscode); if (mgmt->associationresponse.statuscode == IEEE80211_STATUS_SUCCESS) { @@ -157,7 +289,7 @@ static void ac_ieee80211_mgmt_association_response_packet(struct ac_session_data } /* Active Station */ - ac_stations_authorize_station(sessiondata, station); + ac_stations_authorize_station(sessiondata->session, station); } } } @@ -223,10 +355,10 @@ static void ac_ieee80211_mgmt_deauthentication_packet(struct ac_session_data_t* stationaddress = (memcmp(mgmt->bssid, mgmt->sa, MACADDRESS_EUI48_LENGTH) ? mgmt->sa : mgmt->da); /* Delete station */ - station = ac_stations_get_station(sessiondata, radioid, NULL, stationaddress); + station = ac_stations_get_station(sessiondata->session, radioid, NULL, stationaddress); if (station) { station->flags &= ~(AC_STATION_FLAGS_AUTHORIZED | AC_STATION_FLAGS_AUTHENTICATED | AC_STATION_FLAGS_ASSOCIATE); - ac_stations_delete_station(sessiondata, station); + ac_stations_delete_station(sessiondata->session, station); } } diff --git a/src/ac/ac_session.c b/src/ac/ac_session.c index 91e5815..0d462c6 100644 --- a/src/ac/ac_session.c +++ b/src/ac/ac_session.c @@ -2,6 +2,7 @@ #include "ac.h" #include "capwap_dfa.h" #include "ac_session.h" +#include "ac_wlans.h" #include "ac_backend.h" #include @@ -530,6 +531,9 @@ static void ac_session_destroy(struct ac_session_t* session) { capwap_itemlist_free(capwap_itemlist_remove_head(session->packets)); } + /* Free WLANS */ + ac_wlans_destroy(session); + /* */ capwap_event_destroy(&session->changereference); capwap_event_destroy(&session->waitpacket); diff --git a/src/ac/ac_session.h b/src/ac/ac_session.h index 80873d9..2601b52 100644 --- a/src/ac/ac_session.h +++ b/src/ac/ac_session.h @@ -123,9 +123,6 @@ struct ac_session_data_t { long count; capwap_event_t changereference; - /* WLAN Reference */ - struct ac_wlans* wlans; - /* */ int enabledtls; unsigned short mtu; @@ -161,6 +158,9 @@ struct ac_session_t { /* Soap */ struct ac_http_soap_request* soaprequest; + /* WLAN Reference */ + struct ac_wlans* wlans; + /* */ char* wtpid; unsigned long state; @@ -208,7 +208,7 @@ void ac_session_data_close(struct ac_session_data_t* sessiondata); void ac_session_data_send_action(struct ac_session_data_t* sessiondata, long action, long param, void* data, long length); void ac_session_data_release_reference(struct ac_session_data_t* sessiondata); -void ac_session_data_send_data_packet(struct ac_session_data_t* sessiondata, uint8_t radioid, uint8_t wlanid, const uint8_t* data, int length, int leavenativeframe); +int ac_session_data_send_data_packet(struct ac_session_data_t* sessiondata, uint8_t radioid, uint8_t wlanid, const uint8_t* data, int length, int leavenativeframe); /* IEEE802.11 Packet */ void ac_ieee80211_packet(struct ac_session_data_t* sessiondata, uint8_t radioid, const struct ieee80211_header* header, int length); diff --git a/src/ac/ac_session_data.c b/src/ac/ac_session_data.c index caa7b53..31c078a 100644 --- a/src/ac/ac_session_data.c +++ b/src/ac/ac_session_data.c @@ -15,9 +15,9 @@ static int ac_session_data_action_add_station_status(struct ac_session_data_t* s struct ac_wlan* wlan; struct ac_station* station; - wlan = ac_wlans_get_bssid_with_wlanid(sessiondata, notify->radioid, notify->wlanid); + wlan = ac_wlans_get_bssid_with_wlanid(sessiondata->session, notify->radioid, notify->wlanid); if (wlan) { - station = ac_stations_get_station(sessiondata, notify->radioid, wlan->bssid, notify->address); + station = ac_stations_get_station(sessiondata->session, notify->radioid, wlan->address, notify->address); if (station) { if (CAPWAP_RESULTCODE_OK(notify->statuscode)) { capwap_logging_info("Authorized station: %s", station->addrtext); @@ -27,7 +27,7 @@ static int ac_session_data_action_add_station_status(struct ac_session_data_t* s capwap_timeout_deletetimer(sessiondata->timeout, station->idtimeout); station->idtimeout = CAPWAP_TIMEOUT_INDEX_NO_SET; } else { - ac_stations_delete_station(sessiondata, station); + ac_stations_delete_station(sessiondata->session, station); } } } @@ -39,12 +39,12 @@ static int ac_session_data_action_add_station_status(struct ac_session_data_t* s static int ac_session_data_action_delete_station_status(struct ac_session_data_t* sessiondata, struct ac_notify_delete_station_status* notify) { struct ac_station* station; - station = ac_stations_get_station(sessiondata, notify->radioid, NULL, notify->address); + station = ac_stations_get_station(sessiondata->session, notify->radioid, NULL, notify->address); if (station) { capwap_logging_info("Deauthorized station: %s with %d result code", station->addrtext, (int)notify->statuscode); /* */ - ac_stations_delete_station(sessiondata, station); + ac_stations_delete_station(sessiondata->session, station); } return AC_ERROR_ACTION_SESSION; @@ -59,16 +59,16 @@ static int ac_session_data_action_execute(struct ac_session_data_t* sessiondata, struct ac_station* station; /* Delete station */ - station = ac_stations_get_station(sessiondata, RADIOID_ANY, NULL, (uint8_t*)action->data); + station = ac_stations_get_station(sessiondata->session, RADIOID_ANY, NULL, (uint8_t*)action->data); if (station) { - ac_stations_delete_station(sessiondata, station); + ac_stations_delete_station(sessiondata->session, station); } break; } case AC_SESSION_DATA_ACTION_ASSIGN_BSSID: { - ac_wlans_assign_bssid(sessiondata, *(struct ac_wlan**)action->data); + ac_wlans_assign_bssid(sessiondata->session, *(struct ac_wlan**)action->data); break; } @@ -312,9 +312,6 @@ static void ac_session_data_destroy(struct ac_session_data_t* sessiondata) { /* Free DTLS */ capwap_crypt_freesession(&sessiondata->dtls); - /* Free WLANS */ - ac_wlans_destroy(sessiondata); - /* Free resource */ while (sessiondata->packets->count > 0) { capwap_itemlist_free(capwap_itemlist_remove_head(sessiondata->packets)); @@ -492,7 +489,8 @@ void* ac_session_data_thread(void* param) { } /* */ -void ac_session_data_send_data_packet(struct ac_session_data_t* sessiondata, uint8_t radioid, uint8_t wlanid, const uint8_t* data, int length, int leavenativeframe) { +int ac_session_data_send_data_packet(struct ac_session_data_t* sessiondata, uint8_t radioid, uint8_t wlanid, const uint8_t* data, int length, int leavenativeframe) { + int result = 0; struct capwap_list* txfragpacket; struct capwap_header_data capwapheader; struct capwap_packet_txmng* txmngpacket; @@ -519,9 +517,11 @@ void ac_session_data_send_data_packet(struct ac_session_data_t* sessiondata, uin /* */ if (!capwap_crypt_sendto_fragmentpacket(&sessiondata->dtls, sessiondata->connection.socket.socket[sessiondata->connection.socket.type], txfragpacket, &sessiondata->connection.localaddr, &sessiondata->connection.remoteaddr)) { capwap_logging_debug("Warning: error to send data packet"); + result = -1; } /* Free packets manager */ capwap_list_free(txfragpacket); capwap_packet_txmng_free(txmngpacket); + return result; } diff --git a/src/ac/ac_wlans.c b/src/ac/ac_wlans.c index cea9a7c..492c8c1 100644 --- a/src/ac/ac_wlans.c +++ b/src/ac/ac_wlans.c @@ -4,18 +4,18 @@ #include "ac_backend.h" /* */ -static void ac_stations_delete_station_from_global_cache(struct ac_session_data_t* sessiondata, uint8_t* address) { - struct ac_session_data_t* ownersession; +static void ac_stations_delete_station_from_global_cache(struct ac_session_t* session, uint8_t* address) { + struct ac_session_t* ownersession; - ASSERT(sessiondata != NULL); + ASSERT(session != NULL); ASSERT(address != NULL); /* */ capwap_rwlock_wrlock(&g_ac.stationslock); /* Can delete global reference only if match session handler */ - ownersession = (struct ac_session_data_t*)capwap_hash_search(g_ac.stations, address); - if (ownersession == sessiondata) { + ownersession = (struct ac_session_t*)capwap_hash_search(g_ac.stations, address); + if (ownersession == session) { capwap_hash_delete(g_ac.stations, address); } @@ -23,18 +23,26 @@ static void ac_stations_delete_station_from_global_cache(struct ac_session_data_ } /* */ -static void ac_stations_reset_station(struct ac_session_data_t* sessiondata, struct ac_station* station, struct ac_wlan* wlan) { - ASSERT(sessiondata != NULL); +static void ac_stations_reset_station(struct ac_session_t* session, struct ac_station* station, struct ac_wlan* wlan) { + ASSERT(session != NULL); ASSERT(station != NULL); - /* Remove reference from current WLAN */ if (station->wlan) { + if (station->aid) { + if (station->wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_SPLIT) { + ieee80211_aid_free(station->wlan->aidbitfield, station->aid); + } + + station->aid = 0; + } + + /* Remove reference from current WLAN */ capwap_itemlist_remove(station->wlan->stations, station->wlanitem); } /* Remove timers */ if (station->idtimeout != CAPWAP_TIMEOUT_INDEX_NO_SET) { - capwap_timeout_deletetimer(sessiondata->timeout, station->idtimeout); + capwap_timeout_deletetimer(session->sessiondata->timeout, station->idtimeout); station->idtimeout = CAPWAP_TIMEOUT_INDEX_NO_SET; } @@ -49,21 +57,21 @@ static void ac_stations_reset_station(struct ac_session_data_t* sessiondata, str } /* */ -static void ac_stations_destroy_station(struct ac_session_data_t* sessiondata, struct ac_station* station) { - ASSERT(sessiondata != NULL); +static void ac_stations_destroy_station(struct ac_session_t* session, struct ac_station* station) { + ASSERT(session != NULL); ASSERT(station != NULL); /* */ capwap_logging_info("Destroy station: %s", station->addrtext); /* Remove reference from Global Cache Stations List */ - ac_stations_delete_station_from_global_cache(sessiondata, station->address); + ac_stations_delete_station_from_global_cache(session, station->address); /* Remove reference from WLAN */ - ac_stations_reset_station(sessiondata, station, NULL); + ac_stations_reset_station(session, station, NULL); /* */ - capwap_hash_delete(sessiondata->wlans->stations, station->address); + capwap_hash_delete(session->wlans->stations, station->address); /* Free station reference with itemlist */ capwap_itemlist_free(station->wlanitem); @@ -79,33 +87,39 @@ static unsigned long ac_wlans_item_gethash(const void* key, unsigned long keysiz } /* */ -void ac_wlans_init(struct ac_session_data_t* sessiondata) { - ASSERT(sessiondata != NULL); +void ac_wlans_init(struct ac_session_t* session) { + int i; + + ASSERT(session != NULL); + ASSERT(session->wlans == NULL); /* */ - sessiondata->wlans = (struct ac_wlans*)capwap_alloc(sizeof(struct ac_wlans)); - memset(sessiondata->wlans, 0, sizeof(struct ac_wlans)); + session->wlans = (struct ac_wlans*)capwap_alloc(sizeof(struct ac_wlans)); + memset(session->wlans, 0, sizeof(struct ac_wlans)); /* */ - sessiondata->wlans->stations = capwap_hash_create(AC_WLANS_STATIONS_HASH_SIZE, AC_WLANS_STATIONS_KEY_SIZE, ac_wlans_item_gethash, NULL, NULL); + session->wlans->stations = capwap_hash_create(AC_WLANS_STATIONS_HASH_SIZE, AC_WLANS_STATIONS_KEY_SIZE, ac_wlans_item_gethash, NULL, NULL); + for (i = 0; i < RADIOID_MAX_COUNT; i++) { + session->wlans->devices[i].radioid = i + 1; + } } /* */ -void ac_wlans_destroy(struct ac_session_data_t* sessiondata) { +void ac_wlans_destroy(struct ac_session_t* session) { int i; struct capwap_list* items; - ASSERT(sessiondata != NULL); - ASSERT(sessiondata->wlans != NULL); + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); /* */ for (i = 0; i < RADIOID_MAX_COUNT; i++) { - if (sessiondata->wlans->wlans[i]) { - items = sessiondata->wlans->wlans[i]; + if (session->wlans->devices[i].wlans) { + items = session->wlans->devices[i].wlans; /* Delete WLANS */ while (items->first) { - ac_wlans_delete_bssid(sessiondata, i + 1, ((struct ac_wlan*)items->first->item)->bssid); + ac_wlans_delete_bssid(session, i + 1, ((struct ac_wlan*)items->first->item)->address); } /* */ @@ -114,51 +128,52 @@ void ac_wlans_destroy(struct ac_session_data_t* sessiondata) { } /* */ - ASSERT(sessiondata->wlans->stations->count == 0); + ASSERT(session->wlans->stations->count == 0); /* */ - capwap_hash_free(sessiondata->wlans->stations); - capwap_free(sessiondata->wlans); + capwap_hash_free(session->wlans->stations); + capwap_free(session->wlans); } /* */ -int ac_wlans_assign_bssid(struct ac_session_data_t* sessiondata, struct ac_wlan* wlan) { +int ac_wlans_assign_bssid(struct ac_session_t* session, struct ac_wlan* wlan) { char buffer[CAPWAP_MACADDRESS_EUI48_BUFFER]; - ASSERT(sessiondata != NULL); - ASSERT(sessiondata->wlans != NULL); + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); ASSERT(wlan != NULL); - ASSERT(IS_VALID_RADIOID(wlan->radioid)); + ASSERT(wlan->device != NULL); + ASSERT(IS_VALID_RADIOID(wlan->device->radioid)); ASSERT(IS_VALID_WLANID(wlan->wlanid)); /* */ - if (ac_wlans_get_bssid(sessiondata, wlan->radioid, wlan->bssid)) { + if (ac_wlans_get_bssid(session, wlan->device->radioid, wlan->address)) { return 0; } /* */ - wlan->session = sessiondata->session; - wlan->sessiondata = sessiondata; + wlan->session = session; + wlan->sessiondata = session->sessiondata; /* Create WLAN list */ - if (!sessiondata->wlans->wlans[wlan->radioid - 1]) { - sessiondata->wlans->wlans[wlan->radioid - 1] = capwap_list_create(); + if (!session->wlans->devices[wlan->device->radioid - 1].wlans) { + session->wlans->devices[wlan->device->radioid - 1].wlans = capwap_list_create(); } /* Append WLAN to list */ - capwap_itemlist_insert_after(sessiondata->wlans->wlans[wlan->radioid - 1], NULL, wlan->wlanitem); + capwap_itemlist_insert_after(session->wlans->devices[wlan->device->radioid - 1].wlans, NULL, wlan->wlanitem); /* */ - capwap_logging_info("Added new wlan with radioid: %d, wlanid: %d, bssid: %s", (int)wlan->radioid, (int)wlan->wlanid, capwap_printf_macaddress(buffer, wlan->bssid, MACADDRESS_EUI48_LENGTH)); + capwap_logging_info("Added new wlan with radioid: %d, wlanid: %d, bssid: %s", (int)wlan->device->radioid, (int)wlan->wlanid, capwap_printf_macaddress(buffer, wlan->address, MACADDRESS_EUI48_LENGTH)); return 1; } /* */ -struct ac_wlan* ac_wlans_create_bssid(uint8_t radioid, uint8_t wlanid, const uint8_t* bssid, struct capwap_80211_addwlan_element* addwlan) { +struct ac_wlan* ac_wlans_create_bssid(struct ac_device* device, uint8_t wlanid, const uint8_t* bssid, struct capwap_80211_addwlan_element* addwlan) { struct ac_wlan* wlan; struct capwap_list_item* wlanitem; - ASSERT(IS_VALID_RADIOID(radioid)); + ASSERT(device != NULL); ASSERT(IS_VALID_WLANID(wlanid)); ASSERT(bssid != NULL); @@ -169,8 +184,8 @@ struct ac_wlan* ac_wlans_create_bssid(uint8_t radioid, uint8_t wlanid, const uin /* Init WLAN */ wlan->wlanitem = wlanitem; - memcpy(wlan->bssid, bssid, MACADDRESS_EUI48_LENGTH); - wlan->radioid = radioid; + memcpy(wlan->address, bssid, MACADDRESS_EUI48_LENGTH); + wlan->device = device; wlan->wlanid = wlanid; wlan->stations = capwap_list_create(); @@ -192,34 +207,30 @@ struct ac_wlan* ac_wlans_create_bssid(uint8_t radioid, uint8_t wlanid, const uin wlan->tunnelmode = addwlan->tunnelmode; wlan->suppressssid = addwlan->suppressssid; - wlan->ssid = (uint8_t*)capwap_duplicate_string((const char*)addwlan->ssid); + strcpy(wlan->ssid, (const char*)addwlan->ssid); return wlan; } /* */ -struct ac_wlan* ac_wlans_get_bssid(struct ac_session_data_t* sessiondata, uint8_t radioid, const uint8_t* bssid) { +struct ac_wlan* ac_wlans_get_bssid(struct ac_session_t* session, uint8_t radioid, const uint8_t* bssid) { struct capwap_list_item* search; struct ac_wlan* wlan = NULL; - ASSERT(sessiondata != NULL); - ASSERT(sessiondata->wlans != NULL); + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); ASSERT(IS_VALID_RADIOID(radioid)); ASSERT(bssid != NULL); /* */ - if (sessiondata->wlans->wlans[radioid - 1]) { - search = sessiondata->wlans->wlans[radioid - 1]->first; - while (search) { + if (session->wlans->devices[radioid - 1].wlans) { + for (search = session->wlans->devices[radioid - 1].wlans->first; search; search = search->next) { struct ac_wlan* item = (struct ac_wlan*)search->item; - if (!memcmp(bssid, item->bssid, MACADDRESS_EUI48_LENGTH)) { + if (!memcmp(bssid, item->address, MACADDRESS_EUI48_LENGTH)) { wlan = item; break; } - - /* Next */ - search = search->next; } } @@ -227,28 +238,24 @@ struct ac_wlan* ac_wlans_get_bssid(struct ac_session_data_t* sessiondata, uint8_ } /* */ -struct ac_wlan* ac_wlans_get_bssid_with_wlanid(struct ac_session_data_t* sessiondata, uint8_t radioid, uint8_t wlanid) { +struct ac_wlan* ac_wlans_get_bssid_with_wlanid(struct ac_session_t* session, uint8_t radioid, uint8_t wlanid) { struct capwap_list_item* search; struct ac_wlan* wlan = NULL; - ASSERT(sessiondata != NULL); - ASSERT(sessiondata->wlans != NULL); + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); ASSERT(IS_VALID_RADIOID(radioid)); ASSERT(IS_VALID_WLANID(wlanid)); /* */ - if (sessiondata->wlans->wlans[radioid - 1]) { - search = sessiondata->wlans->wlans[radioid - 1]->first; - while (search) { + if (session->wlans->devices[radioid - 1].wlans) { + for (search = session->wlans->devices[radioid - 1].wlans->first; search; search = search->next) { struct ac_wlan* item = (struct ac_wlan*)search->item; if (wlanid == item->wlanid) { wlan = item; break; } - - /* Next */ - search = search->next; } } @@ -256,19 +263,19 @@ struct ac_wlan* ac_wlans_get_bssid_with_wlanid(struct ac_session_data_t* session } /* */ -static void ac_wlans_destroy_bssid(struct ac_session_data_t* sessiondata, struct ac_wlan* wlan) { +static void ac_wlans_destroy_bssid(struct ac_session_t* session, struct ac_wlan* wlan) { + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); + ASSERT(wlan != NULL); + /* Free capability */ if (wlan->key) { capwap_free(wlan->key); } - if (wlan->ssid) { - capwap_free(wlan->ssid); - } - /* Remove stations */ while (wlan->stations->first) { - ac_stations_destroy_station(sessiondata, (struct ac_station*)wlan->stations->first->item); + ac_stations_destroy_station(session, (struct ac_station*)wlan->stations->first->item); } /* */ @@ -276,43 +283,39 @@ static void ac_wlans_destroy_bssid(struct ac_session_data_t* sessiondata, struct } /* */ -void ac_wlans_delete_bssid(struct ac_session_data_t* sessiondata, uint8_t radioid, const uint8_t* bssid) { +void ac_wlans_delete_bssid(struct ac_session_t* session, uint8_t radioid, const uint8_t* bssid) { struct capwap_list_item* search; - ASSERT(sessiondata != NULL); - ASSERT(sessiondata->wlans != NULL); + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); ASSERT(IS_VALID_RADIOID(radioid)); ASSERT(bssid != NULL); /* */ - if (sessiondata->wlans->wlans[radioid - 1]) { - search = sessiondata->wlans->wlans[radioid - 1]->first; - while (search) { + if (session->wlans->devices[radioid - 1].wlans) { + for (search = session->wlans->devices[radioid - 1].wlans->first; search; search = search->next) { struct ac_wlan* item = (struct ac_wlan*)search->item; - if (!memcmp(bssid, item->bssid, MACADDRESS_EUI48_LENGTH)) { - ac_wlans_destroy_bssid(sessiondata, item); - capwap_itemlist_free(capwap_itemlist_remove(sessiondata->wlans->wlans[radioid - 1], search)); + if (!memcmp(bssid, item->address, MACADDRESS_EUI48_LENGTH)) { + ac_wlans_destroy_bssid(session, item); + capwap_itemlist_free(capwap_itemlist_remove(session->wlans->devices[radioid - 1].wlans, search)); break; } - - /* Next */ - search = search->next; } } } /* */ -struct ac_station* ac_stations_get_station(struct ac_session_data_t* sessiondata, uint8_t radioid, const uint8_t* bssid, const uint8_t* address) { +struct ac_station* ac_stations_get_station(struct ac_session_t* session, uint8_t radioid, const uint8_t* bssid, const uint8_t* address) { struct ac_station* station; - ASSERT(sessiondata != NULL); - ASSERT(sessiondata->wlans != NULL); + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); ASSERT(address != NULL); /* Get station */ - station = (struct ac_station*)capwap_hash_search(sessiondata->wlans->stations, address); - if (station && (station->flags & AC_STATION_FLAGS_ENABLED) && ((radioid == RADIOID_ANY) || (radioid == station->wlan->radioid)) && (!bssid || !memcmp(bssid, station->wlan->bssid, MACADDRESS_EUI48_LENGTH))) { + station = (struct ac_station*)capwap_hash_search(session->wlans->stations, address); + if (station && (station->flags & AC_STATION_FLAGS_ENABLED) && ((radioid == RADIOID_ANY) || (radioid == station->wlan->device->radioid)) && (!bssid || !memcmp(bssid, station->wlan->address, MACADDRESS_EUI48_LENGTH))) { return station; } @@ -320,16 +323,16 @@ struct ac_station* ac_stations_get_station(struct ac_session_data_t* sessiondata } /* */ -struct ac_station* ac_stations_create_station(struct ac_session_data_t* sessiondata, uint8_t radioid, const uint8_t* bssid, const uint8_t* address) { +struct ac_station* ac_stations_create_station(struct ac_session_t* session, uint8_t radioid, const uint8_t* bssid, const uint8_t* address) { char buffer1[CAPWAP_MACADDRESS_EUI48_BUFFER]; char buffer2[CAPWAP_MACADDRESS_EUI48_BUFFER]; struct ac_wlan* wlan; - struct ac_session_data_t* ownersession; - struct ac_station* station; + struct ac_session_t* ownersession; struct capwap_list_item* stationitem; + struct ac_station* station = NULL; - ASSERT(sessiondata != NULL); - ASSERT(sessiondata->wlans != NULL); + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); ASSERT(IS_VALID_RADIOID(radioid)); ASSERT(bssid != NULL); ASSERT(address != NULL); @@ -339,74 +342,79 @@ struct ac_station* ac_stations_create_station(struct ac_session_data_t* sessiond capwap_printf_macaddress(buffer2, address, MACADDRESS_EUI48_LENGTH); capwap_logging_info("Create station to radioid: %d, bssid: %s, station address: %s", (int)radioid, buffer1, buffer2); - /* Get session that owns the station */ - capwap_rwlock_rdlock(&g_ac.stationslock); - ownersession = (struct ac_session_data_t*)capwap_hash_search(g_ac.stations, address); - capwap_rwlock_exit(&g_ac.stationslock); + /* */ + wlan = ac_wlans_get_bssid(session, radioid, bssid); + if (wlan) { + /* Get session that owns the station */ + capwap_rwlock_rdlock(&g_ac.stationslock); + ownersession = (struct ac_session_t*)capwap_hash_search(g_ac.stations, address); + capwap_rwlock_exit(&g_ac.stationslock); - /* If request change owner of station */ - if (ownersession != sessiondata) { - /* Release station from old owner */ - if (ownersession) { - ac_session_data_send_action(ownersession, AC_SESSION_DATA_ACTION_ROAMING_STATION, 0, (void*)address, MACADDRESS_EUI48_LENGTH); + /* If request change owner of station */ + if (ownersession != session) { + /* Release station from old owner */ + if (ownersession) { + ac_session_data_send_action(ownersession->sessiondata, AC_SESSION_DATA_ACTION_ROAMING_STATION, 0, (void*)address, MACADDRESS_EUI48_LENGTH); + } + + /* Set station into Global Cache Stations List */ + capwap_rwlock_wrlock(&g_ac.stationslock); + capwap_hash_add(g_ac.stations, address, session); + capwap_rwlock_exit(&g_ac.stationslock); } - /* Set station into Global Cache Stations List */ - capwap_rwlock_wrlock(&g_ac.stationslock); - capwap_hash_add(g_ac.stations, address, sessiondata); - capwap_rwlock_exit(&g_ac.stationslock); - } - - /* */ - wlan = ac_wlans_get_bssid(sessiondata, radioid, bssid); - station = (struct ac_station*)capwap_hash_search(sessiondata->wlans->stations, address); - if (!station) { - stationitem = capwap_itemlist_create(sizeof(struct ac_station)); - station = (struct ac_station*)stationitem->item; - memset(station, 0, sizeof(struct ac_station)); - /* */ - station->idtimeout = CAPWAP_TIMEOUT_INDEX_NO_SET; - memcpy(station->address, address, MACADDRESS_EUI48_LENGTH); - capwap_printf_macaddress(station->addrtext, address, MACADDRESS_EUI48_LENGTH); - station->wlanitem = stationitem; + station = (struct ac_station*)capwap_hash_search(session->wlans->stations, address); + if (!station) { + stationitem = capwap_itemlist_create(sizeof(struct ac_station)); + station = (struct ac_station*)stationitem->item; + memset(station, 0, sizeof(struct ac_station)); - /* */ - capwap_hash_add(sessiondata->wlans->stations, address, station); + /* */ + station->idtimeout = CAPWAP_TIMEOUT_INDEX_NO_SET; + memcpy(station->address, address, MACADDRESS_EUI48_LENGTH); + capwap_printf_macaddress(station->addrtext, address, MACADDRESS_EUI48_LENGTH); + station->wlanitem = stationitem; + + /* */ + capwap_hash_add(session->wlans->stations, address, station); + } + + /* Set station to WLAN */ + ac_stations_reset_station(session, station, wlan); + station->flags |= AC_STATION_FLAGS_ENABLED; + } else { + capwap_logging_warning("Unable to find radioid: %d, bssid: %s", (int)radioid, buffer1); } - /* Set station to WLAN */ - ac_stations_reset_station(sessiondata, station, wlan); - station->flags |= AC_STATION_FLAGS_ENABLED; - return station; } /* */ -void ac_stations_delete_station(struct ac_session_data_t* sessiondata, struct ac_station* station) { - ASSERT(sessiondata != NULL); - ASSERT(sessiondata->wlans != NULL); +void ac_stations_delete_station(struct ac_session_t* session, struct ac_station* station) { + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); ASSERT(station != NULL); /* Deauthorize station */ - ac_stations_deauthorize_station(sessiondata, station); + ac_stations_deauthorize_station(session, station); /* Destroy station reference */ - ac_stations_destroy_station(sessiondata, station); + ac_stations_destroy_station(session, station); } /* */ -void ac_stations_authorize_station(struct ac_session_data_t* sessiondata, struct ac_station* station) { +void ac_stations_authorize_station(struct ac_session_t* session, struct ac_station* station) { struct ac_notify_station_configuration_ieee8011_add_station notify; - ASSERT(sessiondata != NULL); - ASSERT(sessiondata->wlans != NULL); + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); ASSERT(station != NULL); /* Active Station only if Authenticated, Associated and not Authrizated */ if ((station->flags & AC_STATION_FLAGS_AUTHENTICATED) && (station->flags & AC_STATION_FLAGS_ASSOCIATE) && !(station->flags & AC_STATION_FLAGS_AUTHORIZED)) { memset(¬ify, 0, sizeof(struct ac_notify_station_configuration_ieee8011_add_station)); - notify.radioid = station->wlan->radioid; + notify.radioid = station->wlan->device->radioid; memcpy(notify.address, station->address, MACADDRESS_EUI48_LENGTH); notify.wlanid = station->wlan->wlanid; notify.associationid = station->aid; @@ -414,34 +422,34 @@ void ac_stations_authorize_station(struct ac_session_data_t* sessiondata, struct notify.supportedratescount = station->supportedratescount; memcpy(notify.supportedrates, station->supportedrates, station->supportedratescount); - ac_session_send_action(sessiondata->session, AC_SESSION_ACTION_STATION_CONFIGURATION_IEEE80211_ADD_STATION, 0, ¬ify, sizeof(struct ac_notify_station_configuration_ieee8011_add_station)); + ac_session_send_action(session, AC_SESSION_ACTION_STATION_CONFIGURATION_IEEE80211_ADD_STATION, 0, ¬ify, sizeof(struct ac_notify_station_configuration_ieee8011_add_station)); } } /* */ -void ac_stations_deauthorize_station(struct ac_session_data_t* sessiondata, struct ac_station* station) { +void ac_stations_deauthorize_station(struct ac_session_t* session, struct ac_station* station) { int responselength; uint8_t buffer[IEEE80211_MTU]; struct ieee80211_deauthentication_params ieee80211_params; struct ac_notify_station_configuration_ieee8011_delete_station notify; - ASSERT(sessiondata != NULL); - ASSERT(sessiondata->wlans != NULL); + ASSERT(session != NULL); + ASSERT(session->wlans != NULL); ASSERT(station != NULL); if (station->flags & AC_STATION_FLAGS_AUTHORIZED) { /* Deauthorize station */ memset(¬ify, 0, sizeof(struct ac_notify_station_configuration_ieee8011_delete_station)); - notify.radioid = station->wlan->radioid; + notify.radioid = station->wlan->device->radioid; memcpy(notify.address, station->address, MACADDRESS_EUI48_LENGTH); /* */ station->flags &= ~(AC_STATION_FLAGS_AUTHENTICATED | AC_STATION_FLAGS_ASSOCIATE | AC_STATION_FLAGS_AUTHORIZED); - ac_session_send_action(sessiondata->session, AC_SESSION_ACTION_STATION_CONFIGURATION_IEEE80211_DELETE_STATION, 0, ¬ify, sizeof(struct ac_notify_station_configuration_ieee8011_delete_station)); + ac_session_send_action(session, AC_SESSION_ACTION_STATION_CONFIGURATION_IEEE80211_DELETE_STATION, 0, ¬ify, sizeof(struct ac_notify_station_configuration_ieee8011_delete_station)); } else if (station->flags & AC_STATION_FLAGS_AUTHENTICATED) { /* Create deauthentication packet */ memset(&ieee80211_params, 0, sizeof(struct ieee80211_deauthentication_params)); - memcpy(ieee80211_params.bssid, station->wlan->bssid, MACADDRESS_EUI48_LENGTH); + memcpy(ieee80211_params.bssid, station->wlan->address, MACADDRESS_EUI48_LENGTH); memcpy(ieee80211_params.station, station->address, MACADDRESS_EUI48_LENGTH); ieee80211_params.reasoncode = IEEE80211_REASON_PREV_AUTH_NOT_VALID; @@ -449,7 +457,7 @@ void ac_stations_deauthorize_station(struct ac_session_data_t* sessiondata, stru responselength = ieee80211_create_deauthentication(buffer, IEEE80211_MTU, &ieee80211_params); if (responselength > 0) { station->flags &= ~(AC_STATION_FLAGS_AUTHENTICATED | AC_STATION_FLAGS_ASSOCIATE); - ac_session_data_send_data_packet(sessiondata, station->wlan->radioid, station->wlan->wlanid, buffer, responselength, 1); + ac_session_data_send_data_packet(session->sessiondata, station->wlan->device->radioid, station->wlan->wlanid, buffer, responselength, 1); } } } @@ -464,7 +472,7 @@ void ac_stations_timeout(struct capwap_timeout* timeout, unsigned long index, vo switch (station->timeoutaction) { case AC_STATION_TIMEOUT_ACTION_DEAUTHENTICATE: { capwap_logging_warning("The %s station has not completed the association in time", station->addrtext); - ac_stations_delete_station((struct ac_session_data_t*)param, station); + ac_stations_delete_station((struct ac_session_t*)param, station); break; } } diff --git a/src/ac/ac_wlans.h b/src/ac/ac_wlans.h index 249c799..3340065 100644 --- a/src/ac/ac_wlans.h +++ b/src/ac/ac_wlans.h @@ -13,15 +13,17 @@ /* AC WLAN */ struct ac_wlan { struct capwap_list_item* wlanitem; + struct ac_device* device; - uint8_t bssid[MACADDRESS_EUI48_LENGTH]; - uint8_t radioid; + uint8_t address[MACADDRESS_EUI48_LENGTH]; uint8_t wlanid; /* CAPWAP Session */ struct ac_session_t* session; struct ac_session_data_t* sessiondata; + uint32_t aidbitfield[IEEE80211_AID_BITFIELD_SIZE]; + /* Stations reference */ struct capwap_list* stations; @@ -37,7 +39,25 @@ struct ac_wlan { uint8_t macmode; uint8_t tunnelmode; uint8_t suppressssid; - uint8_t* ssid; + char ssid[IEEE80211_SSID_MAX_LENGTH + 1]; +}; + +/* */ +struct ac_device { + uint8_t radioid; + struct capwap_list* wlans; + + /* Rates */ + unsigned long supportedratescount; + uint8_t supportedrates[IEEE80211_SUPPORTEDRATE_MAX_COUNT]; +}; + +/* */ +struct ac_wlans { + struct ac_device devices[RADIOID_MAX_COUNT]; + + /* Stations */ + struct capwap_hash* stations; }; /* */ @@ -81,31 +101,23 @@ struct ac_station { uint16_t authalgorithm; }; -/* */ -struct ac_wlans { - struct capwap_list* wlans[RADIOID_MAX_COUNT]; - - /* Stations */ - struct capwap_hash* stations; -}; - /* Management WLANS */ -void ac_wlans_init(struct ac_session_data_t* sessiondata); -void ac_wlans_destroy(struct ac_session_data_t* sessiondata); +void ac_wlans_init(struct ac_session_t* session); +void ac_wlans_destroy(struct ac_session_t* session); /* */ -struct ac_wlan* ac_wlans_create_bssid(uint8_t radioid, uint8_t wlanid, const uint8_t* bssid, struct capwap_80211_addwlan_element* addwlan); -int ac_wlans_assign_bssid(struct ac_session_data_t* sessiondata, struct ac_wlan* wlan); -struct ac_wlan* ac_wlans_get_bssid(struct ac_session_data_t* sessiondata, uint8_t radioid, const uint8_t* bssid); -struct ac_wlan* ac_wlans_get_bssid_with_wlanid(struct ac_session_data_t* sessiondata, uint8_t radioid, uint8_t wlanid); -void ac_wlans_delete_bssid(struct ac_session_data_t* sessiondata, uint8_t radioid, const uint8_t* bssid); +struct ac_wlan* ac_wlans_create_bssid(struct ac_device* device, uint8_t wlanid, const uint8_t* bssid, struct capwap_80211_addwlan_element* addwlan); +int ac_wlans_assign_bssid(struct ac_session_t* session, struct ac_wlan* wlan); +struct ac_wlan* ac_wlans_get_bssid(struct ac_session_t* session, uint8_t radioid, const uint8_t* bssid); +struct ac_wlan* ac_wlans_get_bssid_with_wlanid(struct ac_session_t* session, uint8_t radioid, uint8_t wlanid); +void ac_wlans_delete_bssid(struct ac_session_t* session, uint8_t radioid, const uint8_t* bssid); /* Management Stations */ -struct ac_station* ac_stations_create_station(struct ac_session_data_t* sessiondata, uint8_t radioid, const uint8_t* bssid, const uint8_t* address); -struct ac_station* ac_stations_get_station(struct ac_session_data_t* sessiondata, uint8_t radioid, const uint8_t* bssid, const uint8_t* address); -void ac_stations_delete_station(struct ac_session_data_t* sessiondata, struct ac_station* station); -void ac_stations_authorize_station(struct ac_session_data_t* sessiondata, struct ac_station* station); -void ac_stations_deauthorize_station(struct ac_session_data_t* sessiondata, struct ac_station* station); +struct ac_station* ac_stations_create_station(struct ac_session_t* session, uint8_t radioid, const uint8_t* bssid, const uint8_t* address); +struct ac_station* ac_stations_get_station(struct ac_session_t* session, uint8_t radioid, const uint8_t* bssid, const uint8_t* address); +void ac_stations_delete_station(struct ac_session_t* session, struct ac_station* station); +void ac_stations_authorize_station(struct ac_session_t* session, struct ac_station* station); +void ac_stations_deauthorize_station(struct ac_session_t* session, struct ac_station* station); /* */ void ac_stations_timeout(struct capwap_timeout* timeout, unsigned long index, void* context, void* param); diff --git a/src/common/binding/ieee80211/ieee80211.h b/src/common/binding/ieee80211/ieee80211.h index 7922804..2d0df25 100644 --- a/src/common/binding/ieee80211/ieee80211.h +++ b/src/common/binding/ieee80211/ieee80211.h @@ -13,6 +13,8 @@ #define IEEE80211_MTU 7981 #define IEEE80211_SUPPORTEDRATE_MAX_COUNT 16 #define IEEE80211_MAX_STATIONS 2007 +#define IEEE80211_SSID_MAX_LENGTH 32 + /* Radio type with value same of IEEE802.11 Radio Information Message Element */ #define IEEE80211_RADIO_TYPE_80211B 0x00000001 diff --git a/src/wtp/binding/ieee80211/wifi_drivers.c b/src/wtp/binding/ieee80211/wifi_drivers.c index 1f104b0..1a693fd 100644 --- a/src/wtp/binding/ieee80211/wifi_drivers.c +++ b/src/wtp/binding/ieee80211/wifi_drivers.c @@ -180,7 +180,7 @@ static void wifi_station_clean(struct wifi_station* station) { wlan->device->instance->ops->station_deauthorize(wlan, station->address); } - if (station->aid) { + if (station->aid && (wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_LOCAL)) { ieee80211_aid_free(wlan->aidbitfield, station->aid); station->aid = 0; } @@ -429,35 +429,9 @@ static void wifi_wlan_receive_station_mgmt_probe_request(struct wifi_wlan* wlan, } /* */ -static int wifi_wlan_set_station_information(struct wifi_wlan* wlan, const struct ieee80211_header_mgmt* frame, struct ieee80211_ie_items* ieitems, struct wifi_station* station) { +static void wifi_wlan_management_legacy_station(struct wifi_wlan* wlan, struct wifi_station* station) { int updatebeacons = 0; - /* Verify SSID */ - if (ieee80211_is_valid_ssid(wlan->ssid, ieitems->ssid, NULL) != IEEE80211_VALID_SSID) { - return IEEE80211_STATUS_UNSPECIFIED_FAILURE; - } - - /* */ - station->capability = __le16_to_cpu(frame->associationrequest.capability); - station->listeninterval = __le16_to_cpu(frame->associationrequest.listeninterval); - if (ieee80211_aid_create(wlan->aidbitfield, &station->aid)) { - return IEEE80211_STATUS_AP_UNABLE_TO_HANDLE_NEW_STA; - } - - /* Get supported rates */ - if (!ieitems->supported_rates) { - return IEEE80211_STATUS_UNSPECIFIED_FAILURE; - } else if ((ieitems->supported_rates->len + (ieitems->extended_supported_rates ? ieitems->extended_supported_rates->len : 0)) > sizeof(station->supportedrates)) { - return IEEE80211_STATUS_UNSPECIFIED_FAILURE; - } - - station->supportedratescount = ieitems->supported_rates->len; - memcpy(station->supportedrates, ieitems->supported_rates->rates, ieitems->supported_rates->len); - if (ieitems->extended_supported_rates) { - station->supportedratescount += ieitems->extended_supported_rates->len; - memcpy(&station->supportedrates[ieitems->supported_rates->len], ieitems->extended_supported_rates->rates, ieitems->extended_supported_rates->len); - } - /* Check NON ERP */ if (wlan->device->currentfrequency.mode & IEEE80211_RADIO_TYPE_80211G) { int i; @@ -501,8 +475,25 @@ static int wifi_wlan_set_station_information(struct wifi_wlan* wlan, const struc if (updatebeacons) { wlan->device->instance->ops->device_updatebeacons(wlan->device); } +} - return IEEE80211_STATUS_SUCCESS; +/* */ +static int wifi_wlan_get_station_rates(struct wifi_station* station, struct ieee80211_ie_items* ieitems) { + if (!ieitems->supported_rates) { + return -1; + } else if ((ieitems->supported_rates->len + (ieitems->extended_supported_rates ? ieitems->extended_supported_rates->len : 0)) > sizeof(station->supportedrates)) { + return -1; + } + + /* */ + station->supportedratescount = ieitems->supported_rates->len; + memcpy(station->supportedrates, ieitems->supported_rates->rates, ieitems->supported_rates->len); + if (ieitems->extended_supported_rates) { + station->supportedratescount += ieitems->extended_supported_rates->len; + memcpy(&station->supportedrates[ieitems->supported_rates->len], ieitems->extended_supported_rates->rates, ieitems->extended_supported_rates->len); + } + + return 0; } /* */ @@ -627,9 +618,6 @@ static void wifi_wlan_receive_station_mgmt_association_request(struct wifi_wlan* return; } - /* */ - ; - /* Get station reference */ station = wifi_station_get(wlan, frame->sa); if (!station) { @@ -661,7 +649,24 @@ static void wifi_wlan_receive_station_mgmt_association_request(struct wifi_wlan* /* */ if (wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_LOCAL) { - resultstatuscode = wifi_wlan_set_station_information(wlan, frame, &ieitems, station); + /* Verify SSID */ + if (ieee80211_is_valid_ssid(wlan->ssid, ieitems.ssid, NULL) == IEEE80211_VALID_SSID) { + station->capability = __le16_to_cpu(frame->associationrequest.capability); + station->listeninterval = __le16_to_cpu(frame->associationrequest.listeninterval); + if (!ieee80211_aid_create(wlan->aidbitfield, &station->aid)) { + /* Get supported rates */ + if (!wifi_wlan_get_station_rates(station, &ieitems)) { + wifi_wlan_management_legacy_station(wlan, station); + resultstatuscode = IEEE80211_STATUS_SUCCESS; + } else { + resultstatuscode = IEEE80211_STATUS_UNSPECIFIED_FAILURE; + } + } else { + resultstatuscode = IEEE80211_STATUS_AP_UNABLE_TO_HANDLE_NEW_STA; + } + } else { + resultstatuscode = IEEE80211_STATUS_UNSPECIFIED_FAILURE; + } /* Create association response packet */ memset(&ieee80211_params, 0, sizeof(struct ieee80211_authentication_params)); @@ -693,6 +698,10 @@ static void wifi_wlan_receive_station_mgmt_association_request(struct wifi_wlan* } } else if (wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_SPLIT) { wlan->send_frame(wlan->send_frame_to_ac_cbparam, frame, length); + + /* Station information */ + station->capability = __le16_to_cpu(frame->associationresponse.capability); + station->listeninterval = __le16_to_cpu(frame->associationrequest.listeninterval); } } @@ -700,8 +709,6 @@ static void wifi_wlan_receive_station_mgmt_association_request(struct wifi_wlan* static void wifi_wlan_receive_station_mgmt_reassociation_request(struct wifi_wlan* wlan, const struct ieee80211_header_mgmt* frame, int length, uint8_t rssi, uint8_t snr, uint16_t rate) { int ielength; - /* TODO */ - /* Information Elements packet length */ ielength = length - (sizeof(struct ieee80211_header) + sizeof(frame->reassociationrequest)); if (ielength < 0) { @@ -715,8 +722,6 @@ static void wifi_wlan_receive_station_mgmt_reassociation_request(struct wifi_wla static void wifi_wlan_receive_station_mgmt_disassociation(struct wifi_wlan* wlan, const struct ieee80211_header_mgmt* frame, int length, uint8_t rssi, uint8_t snr, uint16_t rate) { int ielength; - /* TODO */ - /* Information Elements packet length */ ielength = length - (sizeof(struct ieee80211_header) + sizeof(frame->disassociation)); if (ielength < 0) { @@ -734,8 +739,6 @@ static void wifi_wlan_receive_station_mgmt_deauthentication(struct wifi_wlan* wl int ielength; struct wifi_station* station; - /* TODO */ - /* Information Elements packet length */ ielength = length - (sizeof(struct ieee80211_header) + sizeof(frame->deauthetication)); if (ielength < 0) { @@ -831,6 +834,7 @@ static void wifi_wlan_receive_station_mgmt_authentication_ack(struct wifi_wlan* /* Check if authenticate */ if ((algorithm == IEEE80211_AUTHENTICATION_ALGORITHM_OPEN) && (transactionseqnumber == 2)) { + capwap_logging_info("IEEE802.11 Authentication complete to %s station", station->addrtext); station->flags |= WIFI_STATION_FLAGS_AUTHENTICATED; } else if ((algorithm == IEEE80211_AUTHENTICATION_ALGORITHM_SHARED_KEY) && (transactionseqnumber == 4)) { /* TODO */ @@ -857,11 +861,15 @@ static void wifi_wlan_receive_station_mgmt_association_response_ack(struct wifi_ /* */ statuscode = __le16_to_cpu(frame->associationresponse.statuscode); if (statuscode == IEEE80211_STATUS_SUCCESS) { - station->flags |= WIFI_STATION_FLAGS_ASSOCIATE; + capwap_logging_info("IEEE802.11 Association complete to %s station", station->addrtext); - /* Apply authorization if Station already authorized */ + /* */ + station->flags |= WIFI_STATION_FLAGS_ASSOCIATE; if (station->flags & WIFI_STATION_FLAGS_AUTHORIZED) { - wlan->device->instance->ops->station_authorize(wlan, station); + /* Apply authorization if Station already authorized */ + if (wlan->device->instance->ops->station_authorize(wlan, station)) { + wifi_wlan_deauthentication_station(wlan, station, IEEE80211_REASON_PREV_AUTH_NOT_VALID, 0); + } } } } @@ -893,7 +901,7 @@ static void wifi_wlan_receive_station_mgmt_ackframe(struct wifi_wlan* wlan, cons } /* */ -static int wifi_wlan_receive_ac_mgmt_authentication(struct wifi_wlan* wlan, const struct ieee80211_header_mgmt* frame, int length) { +static int wifi_wlan_receive_ac_mgmt_authentication(struct wifi_wlan* wlan, struct ieee80211_header_mgmt* frame, int length) { int ielength; struct wifi_station* station; int forwardframe = 0; @@ -904,7 +912,22 @@ static int wifi_wlan_receive_ac_mgmt_authentication(struct wifi_wlan* wlan, cons if (wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_SPLIT) { station = wifi_station_get(wlan, frame->da); if (station) { - /* TODO */ + uint16_t statuscode = __le16_to_cpu(frame->authetication.statuscode); + + if (statuscode == IEEE80211_STATUS_SUCCESS) { + uint16_t algorithm = __le16_to_cpu(frame->authetication.algorithm); + uint16_t transactionseqnumber = __le16_to_cpu(frame->authetication.transactionseqnumber); + + /* Get authentication algorithm */ + if ((algorithm == IEEE80211_AUTHENTICATION_ALGORITHM_OPEN) && (transactionseqnumber == 2)) { + station->authalgorithm = IEEE80211_AUTHENTICATION_ALGORITHM_OPEN; + } else if ((algorithm == IEEE80211_AUTHENTICATION_ALGORITHM_SHARED_KEY) && (transactionseqnumber == 4)) { + station->authalgorithm = IEEE80211_AUTHENTICATION_ALGORITHM_SHARED_KEY; + } + } + + /* */ + forwardframe = 1; } } } @@ -913,8 +936,9 @@ static int wifi_wlan_receive_ac_mgmt_authentication(struct wifi_wlan* wlan, cons } /* */ -static int wifi_wlan_receive_ac_mgmt_association_response(struct wifi_wlan* wlan, const struct ieee80211_header_mgmt* frame, int length) { +static int wifi_wlan_receive_ac_mgmt_association_response(struct wifi_wlan* wlan, struct ieee80211_header_mgmt* frame, int length) { int ielength; + struct ieee80211_ie_items ieitems; struct wifi_station* station; int forwardframe = 0; @@ -929,7 +953,24 @@ static int wifi_wlan_receive_ac_mgmt_association_response(struct wifi_wlan* wlan wifi_wlan_deauthentication_station(wlan, station, IEEE80211_REASON_PREV_AUTH_NOT_VALID, 0); } } else if (wlan->macmode == CAPWAP_ADD_WLAN_MACMODE_SPLIT) { - /* TODO */ + uint16_t statuscode = __le16_to_cpu(frame->associationresponse.statuscode); + + if ((statuscode == IEEE80211_STATUS_SUCCESS) && !ieee80211_retrieve_information_elements_position(&ieitems, &frame->associationresponse.ie[0], ielength)) { + /* Station information */ + station->aid = (__le16_to_cpu(frame->associationresponse.aid) & ~IEEE80211_AID_FIELD); + + /* Get supported rates */ + wifi_wlan_get_station_rates(station, &ieitems); + + /* */ + wifi_wlan_management_legacy_station(wlan, station); + + /* Assign valid WLAN capability */ + frame->associationresponse.capability = __cpu_to_le16(wifi_wlan_check_capability(wlan, wlan->capability)); + } + + /* */ + forwardframe = 1; } } } @@ -938,7 +979,7 @@ static int wifi_wlan_receive_ac_mgmt_association_response(struct wifi_wlan* wlan } /* */ -static int wifi_wlan_receive_ac_mgmt_reassociation_response(struct wifi_wlan* wlan, const struct ieee80211_header_mgmt* frame, int length) { +static int wifi_wlan_receive_ac_mgmt_reassociation_response(struct wifi_wlan* wlan, struct ieee80211_header_mgmt* frame, int length) { int ielength; struct wifi_station* station; int forwardframe = 0; @@ -958,7 +999,7 @@ static int wifi_wlan_receive_ac_mgmt_reassociation_response(struct wifi_wlan* wl } /* */ -static int wifi_wlan_receive_ac_mgmt_disassociation(struct wifi_wlan* wlan, const struct ieee80211_header_mgmt* frame, int length) { +static int wifi_wlan_receive_ac_mgmt_disassociation(struct wifi_wlan* wlan, struct ieee80211_header_mgmt* frame, int length) { int ielength; struct wifi_station* station; @@ -985,7 +1026,7 @@ static int wifi_wlan_receive_ac_mgmt_disassociation(struct wifi_wlan* wlan, cons } /* */ -static int wifi_wlan_receive_ac_mgmt_deauthentication(struct wifi_wlan* wlan, const struct ieee80211_header_mgmt* frame, int length) { +static int wifi_wlan_receive_ac_mgmt_deauthentication(struct wifi_wlan* wlan, struct ieee80211_header_mgmt* frame, int length) { int ielength; struct wifi_station* station; @@ -1005,7 +1046,7 @@ static int wifi_wlan_receive_ac_mgmt_deauthentication(struct wifi_wlan* wlan, co } /* */ -static int wifi_wlan_receive_ac_mgmt_frame(struct wifi_wlan* wlan, const struct ieee80211_header_mgmt* frame, int length, uint16_t framecontrol_subtype) { +static int wifi_wlan_receive_ac_mgmt_frame(struct wifi_wlan* wlan, struct ieee80211_header_mgmt* frame, int length, uint16_t framecontrol_subtype) { int forwardframe = 0; switch (framecontrol_subtype) { @@ -1578,7 +1619,7 @@ void wifi_wlan_receive_station_ackframe(struct wifi_wlan* wlan, const struct iee } /* */ -void wifi_wlan_receive_ac_frame(struct wifi_wlan* wlan, const struct ieee80211_header* frame, int length) { +void wifi_wlan_receive_ac_frame(struct wifi_wlan* wlan, struct ieee80211_header* frame, int length) { int forwardframe = 1; uint16_t framecontrol; uint16_t framecontrol_type; @@ -1596,7 +1637,7 @@ void wifi_wlan_receive_ac_frame(struct wifi_wlan* wlan, const struct ieee80211_h /* Parsing frame */ if (framecontrol_type == IEEE80211_FRAMECONTROL_TYPE_MGMT) { - forwardframe = wifi_wlan_receive_ac_mgmt_frame(wlan, (const struct ieee80211_header_mgmt*)frame, length, framecontrol_subtype); + forwardframe = wifi_wlan_receive_ac_mgmt_frame(wlan, (struct ieee80211_header_mgmt*)frame, length, framecontrol_subtype); } /* Forward frame */ @@ -1608,6 +1649,7 @@ void wifi_wlan_receive_ac_frame(struct wifi_wlan* wlan, const struct ieee80211_h /* */ int wifi_station_authorize(struct wifi_wlan* wlan, struct station_add_params* params) { + int result; struct wifi_station* station; ASSERT(wlan != NULL); @@ -1622,9 +1664,6 @@ int wifi_station_authorize(struct wifi_wlan* wlan, struct station_add_params* pa return 0; } - /* */ - capwap_logging_info("Authorized station: %s", station->addrtext); - /* */ capwap_timeout_deletetimer(g_wifiglobal.timeout, station->idtimeout); station->idtimeout = CAPWAP_TIMEOUT_INDEX_NO_SET; @@ -1636,7 +1675,12 @@ int wifi_station_authorize(struct wifi_wlan* wlan, struct station_add_params* pa } /* Station authorized */ - return wlan->device->instance->ops->station_authorize(wlan, station); + result = wlan->device->instance->ops->station_authorize(wlan, station); + if (result) { + wifi_wlan_deauthentication_station(wlan, station, IEEE80211_REASON_PREV_AUTH_NOT_VALID, 0); + } + + return result; } /* */ diff --git a/src/wtp/binding/ieee80211/wifi_drivers.h b/src/wtp/binding/ieee80211/wifi_drivers.h index 2a8311a..75c4064 100644 --- a/src/wtp/binding/ieee80211/wifi_drivers.h +++ b/src/wtp/binding/ieee80211/wifi_drivers.h @@ -7,7 +7,6 @@ /* */ #define WIFI_DRIVER_NAME_SIZE 16 -#define WIFI_SSID_MAX_LENGTH 32 /* */ #define WIFI_BAND_UNKNOWN 0 @@ -294,7 +293,7 @@ struct wifi_wlan { void* send_frame_to_ac_cbparam; /* WLAN information */ - char ssid[WIFI_SSID_MAX_LENGTH + 1]; + char ssid[IEEE80211_SSID_MAX_LENGTH + 1]; uint8_t ssid_hidden; uint16_t capability; @@ -415,7 +414,7 @@ void wifi_wlan_destroy(struct wifi_wlan* wlan); /* WLAN packet management */ void wifi_wlan_receive_station_frame(struct wifi_wlan* wlan, const struct ieee80211_header* frame, int length, uint32_t frequency, uint8_t rssi, uint8_t snr, uint16_t rate); void wifi_wlan_receive_station_ackframe(struct wifi_wlan* wlan, const struct ieee80211_header* frame, int length, int ack); -void wifi_wlan_receive_ac_frame(struct wifi_wlan* wlan, const struct ieee80211_header* frame, int length); +void wifi_wlan_receive_ac_frame(struct wifi_wlan* wlan, struct ieee80211_header* frame, int length); /* Station management */ int wifi_station_authorize(struct wifi_wlan* wlan, struct station_add_params* params); diff --git a/src/wtp/binding/ieee80211/wifi_nl80211.c b/src/wtp/binding/ieee80211/wifi_nl80211.c index 78276f3..6f4796b 100644 --- a/src/wtp/binding/ieee80211/wifi_nl80211.c +++ b/src/wtp/binding/ieee80211/wifi_nl80211.c @@ -1003,10 +1003,15 @@ int nl80211_station_authorize(struct wifi_wlan* wlan, struct wifi_station* stati if (result == -EEXIST) { result = 0; } else { - capwap_logging_error("Unable add station into wireless driver, error code: %d", result); + capwap_logging_error("Unable to authorized station, error code: %d", result); } } + /* */ + if (!result) { + capwap_logging_info("Authorized station: %s", station->addrtext); + } + /* */ nlmsg_free(msg); return result; diff --git a/src/wtp/wtp_radio.c b/src/wtp/wtp_radio.c index 58df1b5..b9f1c58 100644 --- a/src/wtp/wtp_radio.c +++ b/src/wtp/wtp_radio.c @@ -612,7 +612,7 @@ void wtp_radio_receive_data_packet(uint8_t radioid, unsigned short binding, cons } if ((binding == CAPWAP_WIRELESS_BINDING_IEEE80211) && (length >= sizeof(struct ieee80211_header))) { - const struct ieee80211_header* header = (const struct ieee80211_header*)frame; + struct ieee80211_header* header = (struct ieee80211_header*)frame; const uint8_t* bssid = ieee80211_get_bssid_addr(header); if (bssid) {