aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBruno Randolf <br1@einfach.org>2010-12-07 23:59:24 -0500
committerJohn W. Linville <linville@tuxdriver.com>2010-12-13 15:23:27 -0500
commita7ffac9591a2a0ee74c431396ae475a8d0caa51e (patch)
tree174134b89e490592003307263e6b3964d9a1eacf
parenta08e7ade9ddf4fe79576f953cc5c1725e944d26c (diff)
cfg80211: Add antenna availability information
Add a field to wiphy for the hardware to report the availble antennas for configuration. Only if this is set to something bigger than zero, will the anntenna configuration ops be executed. Allthough this could be a simple number of antennas, I defined it as a bitmap of antennas which are available for configuration, since it's more consistent with the rest of the antenna API and there could be cases where the hardware allows only configuration of certain antennas. As it does not make much of a difference in size or normal usage, I think it's better to be able to support this, in case the need arises. The antenna configuration is now also checked against the availabe antennas and rejected if it does not match. Signed-off-by: Bruno Randolf <br1@einfach.org> -- v3: always apply available antenna mask (for "all" antennas case). v2: reject antenna configurations which don't match the available antennas Signed-off-by: John W. Linville <linville@tuxdriver.com>
-rw-r--r--include/net/cfg80211.h5
-rw-r--r--net/wireless/nl80211.c15
2 files changed, 18 insertions, 2 deletions
diff --git a/include/net/cfg80211.h b/include/net/cfg80211.h
index 0d5979924be3..4d5acb013636 100644
--- a/include/net/cfg80211.h
+++ b/include/net/cfg80211.h
@@ -1468,6 +1468,9 @@ struct ieee80211_txrx_stypes {
1468 * @mgmt_stypes: bitmasks of frame subtypes that can be subscribed to or 1468 * @mgmt_stypes: bitmasks of frame subtypes that can be subscribed to or
1469 * transmitted through nl80211, points to an array indexed by interface 1469 * transmitted through nl80211, points to an array indexed by interface
1470 * type 1470 * type
1471 *
1472 * @available_antennas: bitmap of antennas which are available to configure.
1473 * antenna configuration commands will be rejected unless this is set.
1471 */ 1474 */
1472struct wiphy { 1475struct wiphy {
1473 /* assign these fields before you register the wiphy */ 1476 /* assign these fields before you register the wiphy */
@@ -1507,6 +1510,8 @@ struct wiphy {
1507 1510
1508 u8 max_num_pmkids; 1511 u8 max_num_pmkids;
1509 1512
1513 u32 available_antennas;
1514
1510 /* If multiple wiphys are registered and you're handed e.g. 1515 /* If multiple wiphys are registered and you're handed e.g.
1511 * a regular netdev with assigned ieee80211_ptr, you won't 1516 * a regular netdev with assigned ieee80211_ptr, you won't
1512 * know whether it points to a wiphy your driver has registered 1517 * know whether it points to a wiphy your driver has registered
diff --git a/net/wireless/nl80211.c b/net/wireless/nl80211.c
index c3f80e565365..73a7f6d354c9 100644
--- a/net/wireless/nl80211.c
+++ b/net/wireless/nl80211.c
@@ -548,7 +548,7 @@ static int nl80211_send_wiphy(struct sk_buff *msg, u32 pid, u32 seq, int flags,
548 if (dev->wiphy.flags & WIPHY_FLAG_CONTROL_PORT_PROTOCOL) 548 if (dev->wiphy.flags & WIPHY_FLAG_CONTROL_PORT_PROTOCOL)
549 NLA_PUT_FLAG(msg, NL80211_ATTR_CONTROL_PORT_ETHERTYPE); 549 NLA_PUT_FLAG(msg, NL80211_ATTR_CONTROL_PORT_ETHERTYPE);
550 550
551 if (dev->ops->get_antenna) { 551 if (dev->wiphy.available_antennas && dev->ops->get_antenna) {
552 u32 tx_ant = 0, rx_ant = 0; 552 u32 tx_ant = 0, rx_ant = 0;
553 int res; 553 int res;
554 res = dev->ops->get_antenna(&dev->wiphy, &tx_ant, &rx_ant); 554 res = dev->ops->get_antenna(&dev->wiphy, &tx_ant, &rx_ant);
@@ -1046,7 +1046,7 @@ static int nl80211_set_wiphy(struct sk_buff *skb, struct genl_info *info)
1046 if (info->attrs[NL80211_ATTR_WIPHY_ANTENNA_TX] && 1046 if (info->attrs[NL80211_ATTR_WIPHY_ANTENNA_TX] &&
1047 info->attrs[NL80211_ATTR_WIPHY_ANTENNA_RX]) { 1047 info->attrs[NL80211_ATTR_WIPHY_ANTENNA_RX]) {
1048 u32 tx_ant, rx_ant; 1048 u32 tx_ant, rx_ant;
1049 if (!rdev->ops->set_antenna) { 1049 if (!rdev->wiphy.available_antennas || !rdev->ops->set_antenna) {
1050 result = -EOPNOTSUPP; 1050 result = -EOPNOTSUPP;
1051 goto bad_res; 1051 goto bad_res;
1052 } 1052 }
@@ -1054,6 +1054,17 @@ static int nl80211_set_wiphy(struct sk_buff *skb, struct genl_info *info)
1054 tx_ant = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_ANTENNA_TX]); 1054 tx_ant = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_ANTENNA_TX]);
1055 rx_ant = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_ANTENNA_RX]); 1055 rx_ant = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_ANTENNA_RX]);
1056 1056
1057 /* reject antenna configurations which don't match the
1058 * available antenna mask, except for the "all" mask */
1059 if ((~tx_ant && (tx_ant & ~rdev->wiphy.available_antennas)) ||
1060 (~rx_ant && (rx_ant & ~rdev->wiphy.available_antennas))) {
1061 result = -EINVAL;
1062 goto bad_res;
1063 }
1064
1065 tx_ant = tx_ant & rdev->wiphy.available_antennas;
1066 rx_ant = rx_ant & rdev->wiphy.available_antennas;
1067
1057 result = rdev->ops->set_antenna(&rdev->wiphy, tx_ant, rx_ant); 1068 result = rdev->ops->set_antenna(&rdev->wiphy, tx_ant, rx_ant);
1058 if (result) 1069 if (result)
1059 goto bad_res; 1070 goto bad_res;