Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 98027769 authored by Arend van Spriel's avatar Arend van Spriel Committed by Kalle Valo
Browse files

brcmfmac: enable 802.11d support in firmware



When the driver gets beacon info containing a country IE from user-space
upon .start_ap() callback, it will enable regulatory 802.11d support.

Reviewed-by: default avatarPieter-Paul Giesberts <pieterpg@broadcom.com>
Reviewed-by: default avatarHante Meuleman <meuleman@broadcom.com>
Signed-off-by: default avatarArend van Spriel <arend@broadcom.com>
Signed-off-by: default avatarKalle Valo <kvalo@codeaurora.org>
parent 6b89dcb3
Loading
Loading
Loading
Loading
+26 −0
Original line number Diff line number Diff line
@@ -3966,6 +3966,7 @@ brcmf_cfg80211_start_ap(struct wiphy *wiphy, struct net_device *ndev,
	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
	struct brcmf_if *ifp = netdev_priv(ndev);
	const struct brcmf_tlv *ssid_ie;
	const struct brcmf_tlv *country_ie;
	struct brcmf_ssid_le ssid_le;
	s32 err = -EPERM;
	const struct brcmf_tlv *rsn_ie;
@@ -3975,6 +3976,7 @@ brcmf_cfg80211_start_ap(struct wiphy *wiphy, struct net_device *ndev,
	struct brcmf_fil_bss_enable_le bss_enable;
	u16 chanspec;
	bool mbss;
	int is_11d;

	brcmf_dbg(TRACE, "ctrlchn=%d, center=%d, bw=%d, beacon_interval=%d, dtim_period=%d,\n",
		  settings->chandef.chan->hw_value,
@@ -3986,6 +3988,13 @@ brcmf_cfg80211_start_ap(struct wiphy *wiphy, struct net_device *ndev,
	dev_role = ifp->vif->wdev.iftype;
	mbss = ifp->vif->mbss;

	/* store current 11d setting */
	brcmf_fil_cmd_int_get(ifp, BRCMF_C_GET_REGULATORY, &ifp->vif->is_11d);
	country_ie = brcmf_parse_tlvs((u8 *)settings->beacon.tail,
				      settings->beacon.tail_len,
				      WLAN_EID_COUNTRY);
	is_11d = country_ie ? 1 : 0;

	memset(&ssid_le, 0, sizeof(ssid_le));
	if (settings->ssid == NULL || settings->ssid_len == 0) {
		ie_offset = DOT11_MGMT_HDR_LEN + DOT11_BCN_PRB_FIXED_LEN;
@@ -4051,6 +4060,14 @@ brcmf_cfg80211_start_ap(struct wiphy *wiphy, struct net_device *ndev,
			goto exit;
		}

		if (is_11d != ifp->vif->is_11d) {
			err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_REGULATORY,
						    is_11d);
			if (err < 0) {
				brcmf_err("Regulatory Set Error, %d\n", err);
				goto exit;
			}
		}
		if (settings->beacon_interval) {
			err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_BCNPRD,
						    settings->beacon_interval);
@@ -4083,6 +4100,10 @@ brcmf_cfg80211_start_ap(struct wiphy *wiphy, struct net_device *ndev,
			brcmf_err("SET INFRA error %d\n", err);
			goto exit;
		}
	} else if (WARN_ON(is_11d != ifp->vif->is_11d)) {
		/* Multiple-BSS should use same 11d configuration */
		err = -EINVAL;
		goto exit;
	}
	if (dev_role == NL80211_IFTYPE_AP) {
		if ((brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MBSS)) && (!mbss))
@@ -4178,6 +4199,11 @@ static int brcmf_cfg80211_stop_ap(struct wiphy *wiphy, struct net_device *ndev)
			brcmf_err("setting INFRA mode failed %d\n", err);
		if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MBSS))
			brcmf_fil_iovar_int_set(ifp, "mbss", 0);
		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_REGULATORY,
					    ifp->vif->is_11d);
		if (err < 0)
			brcmf_err("restoring REGULATORY setting failed %d\n",
				  err);
		/* Bring device back up so it can be used again */
		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_UP, 1);
		if (err < 0)
+1 −0
Original line number Diff line number Diff line
@@ -200,6 +200,7 @@ struct brcmf_cfg80211_vif {
	struct list_head list;
	u16 mgmt_rx_reg;
	bool mbss;
	int is_11d;
};

/* association inform */
+2 −0
Original line number Diff line number Diff line
@@ -43,6 +43,8 @@
#define BRCMF_C_SET_RADIO			38
#define BRCMF_C_GET_PHYTYPE			39
#define BRCMF_C_SET_KEY				45
#define BRCMF_C_GET_REGULATORY			46
#define BRCMF_C_SET_REGULATORY			47
#define BRCMF_C_SET_PASSIVE_SCAN		49
#define BRCMF_C_SCAN				50
#define BRCMF_C_SCAN_RESULTS			51