handle WTP QoS IE

This commit is contained in:
Andreas Schultz
2016-03-04 17:02:33 +01:00
parent d93cd1044d
commit 5f98005414
6 changed files with 217 additions and 1 deletions

View File

@ -1438,6 +1438,37 @@ int wifi_device_setfrequency(struct wifi_device* device, uint32_t band, uint32_t
return result;
}
int wifi_device_settxqueue(struct wifi_device *device, struct capwap_80211_wtpqos_element *qos)
{
int i, txop;
for (i = 0; i < CAPWAP_UPDATE_STATION_QOS_SUBELEMENTS; i++) {
switch (i) {
case 0: /* Best Effort */
txop = 0;
break;
case 1: /* Background */
txop = 0;
break;
case 2: /* Video */
txop = 94;
break;
case 3: /* Voice */
txop = 47;
break;
default:
return -1;
}
if (device->instance->ops->device_settxqueue(device, i,
qos->qos[i].aifs,
qos->qos[i].cwmin,
qos->qos[i].cwmax, txop) < 0)
return -1;
}
return 0;
}
/* */
int wifi_device_updaterates(struct wifi_device* device, uint8_t* rates, int ratescount) {
struct device_setrates_params buildrate;

View File

@ -67,6 +67,8 @@ DECLARE_OPAQUE_TYPE(wifi_global_handle);
DECLARE_OPAQUE_TYPE(wifi_device_handle);
DECLARE_OPAQUE_TYPE(wifi_wlan_handle);
struct capwap_80211_wtpqos_element;
/* */
struct device_setrates_params {
int supportedratescount;
@ -380,6 +382,8 @@ struct wifi_driver_ops {
int (*device_getcapability)(struct wifi_device* device, struct wifi_capability* capability);
void (*device_updatebeacons)(struct wifi_device* device);
int (*device_setfrequency)(struct wifi_device* device);
int (*device_settxqueue)(struct wifi_device* device, int queue, int aifs,
int cw_min, int cw_max, int txop);
void (*device_deinit)(struct wifi_device* device);
/* WLAN functions */
@ -410,6 +414,7 @@ struct wifi_device* wifi_device_connect(const char* ifname, const char* driver);
const struct wifi_capability* wifi_device_getcapability(struct wifi_device* device);
int wifi_device_setconfiguration(struct wifi_device* device, struct device_setconfiguration_params* params);
int wifi_device_setfrequency(struct wifi_device* device, uint32_t band, uint32_t mode, uint8_t channel);
int wifi_device_settxqueue(struct wifi_device *device, struct capwap_80211_wtpqos_element *qos);
int wifi_device_updaterates(struct wifi_device* device, uint8_t* rates, int ratescount);
/* WLAN management */

View File

@ -1553,6 +1553,80 @@ static void nl80211_device_updatebeacons(struct wifi_device* device) {
}
}
/* */
static int nl80211_device_settxqueue(struct wifi_device* device, int queue, int aifs,
int cw_min, int cw_max, int txop)
{
int result;
struct nl_msg* msg;
struct capwap_list_item* wlansearch;
struct nl80211_device_handle* devicehandle;
struct wifi_wlan* wlan = NULL;
struct nlattr *txq, *params;
ASSERT(device != NULL);
ASSERT(device->handle != NULL);
/* Search a valid interface */
for (wlansearch = device->wlans->first; wlansearch; wlansearch = wlansearch->next) {
struct wifi_wlan* element = (struct wifi_wlan*)wlansearch->item;
if (element->flags & WIFI_WLAN_RUNNING) {
wlan = element;
break;
}
}
if (!wlan)
return -1;
msg = nlmsg_alloc();
if (!msg)
return -1;
/* Set TX Queue using device index of first BSS */
devicehandle = (struct nl80211_device_handle*)device->handle;
genlmsg_put(msg, 0, 0, devicehandle->globalhandle->nl80211_id, 0, 0, NL80211_CMD_SET_WIPHY, 0);
nla_put_u32(msg, NL80211_ATTR_IFINDEX, wlan->virtindex);
txq = nla_nest_start(msg, NL80211_ATTR_WIPHY_TXQ_PARAMS);
/* We are only sending parameters for a single TXQ at a time */
params = nla_nest_start(msg, 1);
switch (queue) {
case 0:
nla_put_u8(msg, NL80211_TXQ_ATTR_QUEUE, NL80211_TXQ_Q_VO);
break;
case 1:
nla_put_u8(msg, NL80211_TXQ_ATTR_QUEUE, NL80211_TXQ_Q_VI);
break;
case 2:
nla_put_u8(msg, NL80211_TXQ_ATTR_QUEUE, NL80211_TXQ_Q_BE);
break;
case 3:
nla_put_u8(msg, NL80211_TXQ_ATTR_QUEUE, NL80211_TXQ_Q_BK);
break;
default:
nlmsg_free(msg);
return -1;
}
nla_put_u16(msg, NL80211_TXQ_ATTR_TXOP, txop);
nla_put_u16(msg, NL80211_TXQ_ATTR_CWMIN, cw_min);
nla_put_u16(msg, NL80211_TXQ_ATTR_CWMAX, cw_max);
nla_put_u8(msg, NL80211_TXQ_ATTR_AIFS, aifs);
nla_nest_end(msg, params);
nla_nest_end(msg, txq);
result = nl80211_send_and_recv_msg(devicehandle->globalhandle, msg, NULL, NULL);
if (result)
capwap_logging_error("Unable set TX Queue, error code: %d", result);
nlmsg_free(msg);
return result;
}
/* */
static int nl80211_device_setfrequency(struct wifi_device* device) {
ASSERT(device != NULL);
@ -1793,6 +1867,7 @@ const struct wifi_driver_ops wifi_driver_nl80211_ops = {
.device_getfdevent = nl80211_device_getfdevent,
.device_getcapability = nl80211_device_getcapability,
.device_updatebeacons = nl80211_device_updatebeacons,
.device_settxqueue = nl80211_device_settxqueue,
.device_setfrequency = nl80211_device_setfrequency,
.device_deinit = nl80211_device_deinit,