cfg80211: Specify frame and reason code for NL80211_CMD_DEL_STATION
authorJouni Malinen <jouni@qca.qualcomm.com>
Mon, 20 Oct 2014 10:20:45 +0000 (13:20 +0300)
committerJohannes Berg <johannes.berg@intel.com>
Mon, 20 Oct 2014 14:39:23 +0000 (16:39 +0200)
The optional NL80211_ATTR_MGMT_SUBTYPE and NL80211_ATTR_REASON_CODE
attributes can now be included in NL80211_CMD_DEL_STATION to indicate to
the driver which frame (Deauthentication/Disassociation) and reason code
in that frame should be used to indicate removal to the specific
station. This is used by drivers that implement AP SME and generate
those frames internally.

Signed-off-by: Jouni Malinen <jouni@qca.qualcomm.com>
Signed-off-by: Johannes Berg <johannes.berg@intel.com>
include/net/cfg80211.h
include/uapi/linux/nl80211.h
net/wireless/nl80211.c
net/wireless/trace.h

index ebb69f67197939211e462961feec859fb090e016..ed896c0b5b8bf2e9081798cc068c49354fece2a6 100644 (file)
@@ -804,9 +804,14 @@ struct station_parameters {
  * Used to delete a station entry (or all stations).
  *
  * @mac: MAC address of the station to remove or NULL to remove all stations
+ * @subtype: Management frame subtype to use for indicating removal
+ *     (10 = Disassociation, 12 = Deauthentication)
+ * @reason_code: Reason code for the Disassociation/Deauthentication frame
  */
 struct station_del_parameters {
        const u8 *mac;
+       u8 subtype;
+       u16 reason_code;
 };
 
 /**
index 846071b0cde936e1a3f92e9d1194033040537b71..b553c48404d3ff7a60c41e62ff6d3535f244aab6 100644 (file)
  *     the interface identified by %NL80211_ATTR_IFINDEX.
  * @NL80211_CMD_DEL_STATION: Remove a station identified by %NL80211_ATTR_MAC
  *     or, if no MAC address given, all stations, on the interface identified
- *     by %NL80211_ATTR_IFINDEX.
+ *     by %NL80211_ATTR_IFINDEX. %NL80211_ATTR_MGMT_SUBTYPE and
+ *     %NL80211_ATTR_REASON_CODE can optionally be used to specify which type
+ *     of disconnection indication should be sent to the station
+ *     (Deauthentication or Disassociation frame and reason code for that
+ *     frame).
  *
  * @NL80211_CMD_GET_MPATH: Get mesh path attributes for mesh path to
  *     destination %NL80211_ATTR_MAC on the interface identified by
index 40cf7b937926a9b978727d456f2dd99e6167ab84..0c0f2045e1f871be674bf591165158152581185f 100644 (file)
@@ -4414,6 +4414,27 @@ static int nl80211_del_station(struct sk_buff *skb, struct genl_info *info)
        if (!rdev->ops->del_station)
                return -EOPNOTSUPP;
 
+       if (info->attrs[NL80211_ATTR_MGMT_SUBTYPE]) {
+               params.subtype =
+                       nla_get_u8(info->attrs[NL80211_ATTR_MGMT_SUBTYPE]);
+               if (params.subtype != IEEE80211_STYPE_DISASSOC >> 4 &&
+                   params.subtype != IEEE80211_STYPE_DEAUTH >> 4)
+                       return -EINVAL;
+       } else {
+               /* Default to Deauthentication frame */
+               params.subtype = IEEE80211_STYPE_DEAUTH >> 4;
+       }
+
+       if (info->attrs[NL80211_ATTR_REASON_CODE]) {
+               params.reason_code =
+                       nla_get_u16(info->attrs[NL80211_ATTR_REASON_CODE]);
+               if (params.reason_code == 0)
+                       return -EINVAL; /* 0 is reserved */
+       } else {
+               /* Default to reason code 2 */
+               params.reason_code = WLAN_REASON_PREV_AUTH_NOT_VALID;
+       }
+
        return rdev_del_station(rdev, dev, &params);
 }
 
index b1339400631d96f46a1d3c68dec5fe2f4b94ea14..cdb2c2ef1ae19c243608cc3672f75a522b170f10 100644 (file)
@@ -688,14 +688,20 @@ DECLARE_EVENT_CLASS(station_del,
                WIPHY_ENTRY
                NETDEV_ENTRY
                MAC_ENTRY(sta_mac)
+               __field(u8, subtype)
+               __field(u16, reason_code)
        ),
        TP_fast_assign(
                WIPHY_ASSIGN;
                NETDEV_ASSIGN;
                MAC_ASSIGN(sta_mac, params->mac);
+               __entry->subtype = params->subtype;
+               __entry->reason_code = params->reason_code;
        ),
-       TP_printk(WIPHY_PR_FMT ", " NETDEV_PR_FMT ", station mac: " MAC_PR_FMT,
-                 WIPHY_PR_ARG, NETDEV_PR_ARG, MAC_PR_ARG(sta_mac))
+       TP_printk(WIPHY_PR_FMT ", " NETDEV_PR_FMT ", station mac: " MAC_PR_FMT
+                 ", subtype: %u, reason_code: %u",
+                 WIPHY_PR_ARG, NETDEV_PR_ARG, MAC_PR_ARG(sta_mac),
+                 __entry->subtype, __entry->reason_code)
 );
 
 DEFINE_EVENT(station_del, rdev_del_station,