Currently, in NO_VIRTUAL_MONITOR mode, when creating an AP/STA + monitor, there is a restriction: if the AP/STA is running, setting the channel for the monitor is not allowed. For example, in a scenario with three supported radios where the AP uses only the 2 GHz and 5 GHz bands, the 6 GHz band remains available. However, due to the restriction that rdev->num_running_ifaces must equal rdev->num_running_monitor_ifaces in cfg80211_has_monitors_only(), we are unable to create the monitor interface. cfg80211_set_monitor_channel -> cfg80211_has_monitors_only() static inline bool cfg80211_has_monitors_only() { ... return rdev->num_running_ifaces == rdev->num_running_monitor_ifaces && rdev->num_running_ifaces > 0; } To address this, introduce the new WIPHY_FLAG_SUPPORTS_CONCUR_MONITOR_N_OTHER_VIF flag to advertise concurrent support for monitor mode alongside AP/STA interfaces in cfg80211. This flag will enable the creation of a monitor interface by bypassing the cfg80211_has_monitors_only() function. In the mac80211 layer, no additional changes are required. It follows the same sequence as standalone monitor creation in NO_VIRTUAL_MONITOR mode. Signed-off-by: Nithyanantham Paramasivam <quic_nithp@xxxxxxxxxxx> --- include/net/cfg80211.h | 55 ++++++++++++++++++++++-------------------- net/wireless/chan.c | 4 ++- 2 files changed, 32 insertions(+), 27 deletions(-) diff --git a/include/net/cfg80211.h b/include/net/cfg80211.h index 6b170a8d086c..b85020ad329a 100644 --- a/include/net/cfg80211.h +++ b/include/net/cfg80211.h @@ -5037,34 +5037,37 @@ struct cfg80211_ops { * @WIPHY_FLAG_SUPPORTS_NSTR_NONPRIMARY: support connection to non-primary link * of an NSTR mobile AP MLD. * @WIPHY_FLAG_DISABLE_WEXT: disable wireless extensions for this device + * @WIPHY_FLAG_SUPPORTS_CONCUR_MONITOR_N_OTHER_VIF: Flag to advertise concurrent + * support for monitor mode alongside AP/STA */ enum wiphy_flags { - WIPHY_FLAG_SUPPORTS_EXT_KEK_KCK = BIT(0), - WIPHY_FLAG_SUPPORTS_MLO = BIT(1), - WIPHY_FLAG_SPLIT_SCAN_6GHZ = BIT(2), - WIPHY_FLAG_NETNS_OK = BIT(3), - WIPHY_FLAG_PS_ON_BY_DEFAULT = BIT(4), - WIPHY_FLAG_4ADDR_AP = BIT(5), - WIPHY_FLAG_4ADDR_STATION = BIT(6), - WIPHY_FLAG_CONTROL_PORT_PROTOCOL = BIT(7), - WIPHY_FLAG_IBSS_RSN = BIT(8), - WIPHY_FLAG_DISABLE_WEXT = BIT(9), - WIPHY_FLAG_MESH_AUTH = BIT(10), - WIPHY_FLAG_SUPPORTS_EXT_KCK_32 = BIT(11), - WIPHY_FLAG_SUPPORTS_NSTR_NONPRIMARY = BIT(12), - WIPHY_FLAG_SUPPORTS_FW_ROAM = BIT(13), - WIPHY_FLAG_AP_UAPSD = BIT(14), - WIPHY_FLAG_SUPPORTS_TDLS = BIT(15), - WIPHY_FLAG_TDLS_EXTERNAL_SETUP = BIT(16), - WIPHY_FLAG_HAVE_AP_SME = BIT(17), - WIPHY_FLAG_REPORTS_OBSS = BIT(18), - WIPHY_FLAG_AP_PROBE_RESP_OFFLOAD = BIT(19), - WIPHY_FLAG_OFFCHAN_TX = BIT(20), - WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL = BIT(21), - WIPHY_FLAG_SUPPORTS_5_10_MHZ = BIT(22), - WIPHY_FLAG_HAS_CHANNEL_SWITCH = BIT(23), - WIPHY_FLAG_NOTIFY_REGDOM_BY_DRIVER = BIT(24), - WIPHY_FLAG_CHANNEL_CHANGE_ON_BEACON = BIT(25), + WIPHY_FLAG_SUPPORTS_EXT_KEK_KCK = BIT(0), + WIPHY_FLAG_SUPPORTS_MLO = BIT(1), + WIPHY_FLAG_SPLIT_SCAN_6GHZ = BIT(2), + WIPHY_FLAG_NETNS_OK = BIT(3), + WIPHY_FLAG_PS_ON_BY_DEFAULT = BIT(4), + WIPHY_FLAG_4ADDR_AP = BIT(5), + WIPHY_FLAG_4ADDR_STATION = BIT(6), + WIPHY_FLAG_CONTROL_PORT_PROTOCOL = BIT(7), + WIPHY_FLAG_IBSS_RSN = BIT(8), + WIPHY_FLAG_DISABLE_WEXT = BIT(9), + WIPHY_FLAG_MESH_AUTH = BIT(10), + WIPHY_FLAG_SUPPORTS_EXT_KCK_32 = BIT(11), + WIPHY_FLAG_SUPPORTS_NSTR_NONPRIMARY = BIT(12), + WIPHY_FLAG_SUPPORTS_FW_ROAM = BIT(13), + WIPHY_FLAG_AP_UAPSD = BIT(14), + WIPHY_FLAG_SUPPORTS_TDLS = BIT(15), + WIPHY_FLAG_TDLS_EXTERNAL_SETUP = BIT(16), + WIPHY_FLAG_HAVE_AP_SME = BIT(17), + WIPHY_FLAG_REPORTS_OBSS = BIT(18), + WIPHY_FLAG_AP_PROBE_RESP_OFFLOAD = BIT(19), + WIPHY_FLAG_OFFCHAN_TX = BIT(20), + WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL = BIT(21), + WIPHY_FLAG_SUPPORTS_5_10_MHZ = BIT(22), + WIPHY_FLAG_HAS_CHANNEL_SWITCH = BIT(23), + WIPHY_FLAG_NOTIFY_REGDOM_BY_DRIVER = BIT(24), + WIPHY_FLAG_CHANNEL_CHANGE_ON_BEACON = BIT(25), + WIPHY_FLAG_SUPPORTS_CONCUR_MONITOR_N_OTHER_VIF = BIT(26), }; /** diff --git a/net/wireless/chan.c b/net/wireless/chan.c index 9f918b77b40e..29715d492944 100644 --- a/net/wireless/chan.c +++ b/net/wireless/chan.c @@ -1509,7 +1509,9 @@ int cfg80211_set_monitor_channel(struct cfg80211_registered_device *rdev, { if (!rdev->ops->set_monitor_channel) return -EOPNOTSUPP; - if (!cfg80211_has_monitors_only(rdev)) + if (!(rdev->wiphy.flags & + WIPHY_FLAG_SUPPORTS_CONCUR_MONITOR_N_OTHER_VIF) && + !cfg80211_has_monitors_only(rdev)) return -EBUSY; return rdev_set_monitor_channel(rdev, dev, chandef); -- 2.17.1