Commit 286e6967 authored by Alexander Wetzel's avatar Alexander Wetzel Committed by Johannes Berg
Browse files

wifi: mac80211: Drop cooked monitor support



Hostapd switched from cooked monitor interfaces to nl80211 Dec 2011.
Drop support for the outdated cooked monitor interfaces and fix
creating the virtual monitor interfaces in the following cases:

 1) We have one non-monitor and one monitor interface with
    %MONITOR_FLAG_ACTIVE enabled and then delete the non-monitor
    interface.

 2) We only have monitor interfaces enabled on resume while at least one
    has %MONITOR_FLAG_ACTIVE set.

Signed-off-by: default avatarAlexander Wetzel <Alexander@wetzel-home.de>
Link: https://patch.msgid.link/20250204111352.7004-2-Alexander@wetzel-home.de


Signed-off-by: default avatarJohannes Berg <johannes.berg@intel.com>
parent be22179c
Loading
Loading
Loading
Loading
+0 −6
Original line number Diff line number Diff line
@@ -17,12 +17,6 @@ enum skb_drop_reason_subsys {
	 */
	SKB_DROP_REASON_SUBSYS_MAC80211_UNUSABLE,

	/**
	 * @SKB_DROP_REASON_SUBSYS_MAC80211_MONITOR: mac80211 drop reasons
	 * for frames still going to monitor, see net/mac80211/drop.h
	 */
	SKB_DROP_REASON_SUBSYS_MAC80211_MONITOR,

	/**
	 * @SKB_DROP_REASON_SUBSYS_OPENVSWITCH: openvswitch drop reasons,
	 * see net/openvswitch/drop.h
+4 −5
Original line number Diff line number Diff line
@@ -89,15 +89,14 @@ static int ieee80211_set_mon_options(struct ieee80211_sub_if_data *sdata,

	/* check flags first */
	if (params->flags && ieee80211_sdata_running(sdata)) {
		u32 mask = MONITOR_FLAG_COOK_FRAMES | MONITOR_FLAG_ACTIVE;
		u32 mask = MONITOR_FLAG_ACTIVE;

		/*
		 * Prohibit MONITOR_FLAG_COOK_FRAMES and
		 * MONITOR_FLAG_ACTIVE to be changed while the
		 * interface is up.
		 * Prohibit MONITOR_FLAG_ACTIVE to be changed
		 * while the interface is up.
		 * Else we would need to add a lot of cruft
		 * to update everything:
		 *	cooked_mntrs, monitor and all fif_* counters
		 *	monitor and all fif_* counters
		 *	reconfigure hardware
		 */
		if ((params->flags & mask) != (sdata->u.mntr.flags & mask))
+7 −14
Original line number Diff line number Diff line
@@ -11,12 +11,6 @@

typedef unsigned int __bitwise ieee80211_rx_result;

#define MAC80211_DROP_REASONS_MONITOR(R)	\
	R(RX_DROP_M_UNEXPECTED_4ADDR_FRAME)	\
	R(RX_DROP_M_BAD_BCN_KEYIDX)		\
	R(RX_DROP_M_BAD_MGMT_KEYIDX)		\
/* this line for the trailing \ - add before this */

#define MAC80211_DROP_REASONS_UNUSABLE(R)	\
	/* 0x00 == ___RX_DROP_UNUSABLE */	\
	R(RX_DROP_U_MIC_FAIL)			\
@@ -66,6 +60,10 @@ typedef unsigned int __bitwise ieee80211_rx_result;
	R(RX_DROP_U_UNEXPECTED_STA_4ADDR)	\
	R(RX_DROP_U_UNEXPECTED_VLAN_MCAST)	\
	R(RX_DROP_U_NOT_PORT_CONTROL)		\
	R(RX_DROP_U_UNEXPECTED_4ADDR_FRAME)	\
	R(RX_DROP_U_BAD_BCN_KEYIDX)		\
	/* 0x30 */				\
	R(RX_DROP_U_BAD_MGMT_KEYIDX)		\
	R(RX_DROP_U_UNKNOWN_ACTION_REJECTED)	\
/* this line for the trailing \ - add before this */

@@ -78,10 +76,6 @@ enum ___mac80211_drop_reason {
	___RX_QUEUED	= SKB_NOT_DROPPED_YET,

#define ENUM(x) ___ ## x,
	___RX_DROP_MONITOR = SKB_DROP_REASON_SUBSYS_MAC80211_MONITOR <<
		SKB_DROP_REASON_SUBSYS_SHIFT,
	MAC80211_DROP_REASONS_MONITOR(ENUM)

	___RX_DROP_UNUSABLE = SKB_DROP_REASON_SUBSYS_MAC80211_UNUSABLE <<
		SKB_DROP_REASON_SUBSYS_SHIFT,
	MAC80211_DROP_REASONS_UNUSABLE(ENUM)
@@ -91,9 +85,8 @@ enum ___mac80211_drop_reason {
enum mac80211_drop_reason {
	RX_CONTINUE	= (__force ieee80211_rx_result)___RX_CONTINUE,
	RX_QUEUED	= (__force ieee80211_rx_result)___RX_QUEUED,
	RX_DROP_MONITOR	 = (__force ieee80211_rx_result)___RX_DROP_MONITOR,
	RX_DROP		= (__force ieee80211_rx_result)___RX_DROP_UNUSABLE,
#define DEF(x) x = (__force ieee80211_rx_result)___ ## x,
	MAC80211_DROP_REASONS_MONITOR(DEF)
	MAC80211_DROP_REASONS_UNUSABLE(DEF)
#undef DEF
};
+4 −7
Original line number Diff line number Diff line
@@ -200,7 +200,6 @@ enum ieee80211_packet_rx_flags {
/**
 * enum ieee80211_rx_flags - RX data flags
 *
 * @IEEE80211_RX_CMNTR: received on cooked monitor already
 * @IEEE80211_RX_BEACON_REPORTED: This frame was already reported
 *	to cfg80211_report_obss_beacon().
 *
@@ -208,8 +207,7 @@ enum ieee80211_packet_rx_flags {
 * for a single frame.
 */
enum ieee80211_rx_flags {
	IEEE80211_RX_CMNTR		= BIT(0),
	IEEE80211_RX_BEACON_REPORTED	= BIT(1),
	IEEE80211_RX_BEACON_REPORTED	= BIT(0),
};

struct ieee80211_rx_data {
@@ -1380,7 +1378,7 @@ struct ieee80211_local {
	spinlock_t queue_stop_reason_lock;

	int open_count;
	int monitors, cooked_mntrs, tx_mntrs;
	int monitors, tx_mntrs;
	/* number of interfaces with corresponding FIF_ flags */
	int fif_fcsfail, fif_plcpfail, fif_control, fif_other_bss, fif_pspoll,
	    fif_probe_req;
@@ -1492,7 +1490,7 @@ struct ieee80211_local {

	/* see iface.c */
	struct list_head interfaces;
	struct list_head mon_list; /* only that are IFF_UP && !cooked */
	struct list_head mon_list; /* only that are IFF_UP */
	struct mutex iflist_mtx;

	/* Scanning and BSS list */
@@ -2090,8 +2088,7 @@ struct sk_buff *
ieee80211_build_data_template(struct ieee80211_sub_if_data *sdata,
			      struct sk_buff *skb, u32 info_flags);
void ieee80211_tx_monitor(struct ieee80211_local *local, struct sk_buff *skb,
			  int retry_count, bool send_to_cooked,
			  struct ieee80211_tx_status *status);
			  int retry_count, struct ieee80211_tx_status *status);

void ieee80211_check_fast_xmit(struct sta_info *sta);
void ieee80211_check_fast_xmit_all(struct ieee80211_local *local);
+21 −29
Original line number Diff line number Diff line
@@ -483,8 +483,6 @@ static void ieee80211_do_stop(struct ieee80211_sub_if_data *sdata, bool going_do
		ieee80211_ibss_stop(sdata);
		break;
	case NL80211_IFTYPE_MONITOR:
		if (sdata->u.mntr.flags & MONITOR_FLAG_COOK_FRAMES)
			break;
		list_del_rcu(&sdata->u.mntr.list);
		break;
	default:
@@ -584,10 +582,8 @@ static void ieee80211_do_stop(struct ieee80211_sub_if_data *sdata, bool going_do
		/* no need to tell driver */
		break;
	case NL80211_IFTYPE_MONITOR:
		if (sdata->u.mntr.flags & MONITOR_FLAG_COOK_FRAMES) {
			local->cooked_mntrs--;
			break;
		}
		if (!(sdata->u.mntr.flags & MONITOR_FLAG_ACTIVE) &&
		    !ieee80211_hw_check(&local->hw, NO_VIRTUAL_MONITOR)) {

			local->monitors--;
			if (local->monitors == 0) {
@@ -596,6 +592,7 @@ static void ieee80211_do_stop(struct ieee80211_sub_if_data *sdata, bool going_do
			}

			ieee80211_adjust_monitor_flags(sdata, -1);
		}
		break;
	case NL80211_IFTYPE_NAN:
		/* clean all the functions */
@@ -1326,28 +1323,25 @@ int ieee80211_do_open(struct wireless_dev *wdev, bool coming_up)
		}
		break;
	case NL80211_IFTYPE_MONITOR:
		if (sdata->u.mntr.flags & MONITOR_FLAG_COOK_FRAMES) {
			local->cooked_mntrs++;
			break;
		}

		if ((sdata->u.mntr.flags & MONITOR_FLAG_ACTIVE) ||
		    ieee80211_hw_check(&local->hw, NO_VIRTUAL_MONITOR)) {
			res = drv_add_interface(local, sdata);
			if (res)
				goto err_stop;
		} else if (local->monitors == 0 && local->open_count == 0) {
		} else {
			if (local->monitors == 0 && local->open_count == 0) {
				res = ieee80211_add_virtual_monitor(local);
				if (res)
					goto err_stop;
			}
			local->monitors++;

			/* must be before the call to ieee80211_configure_filter */
		local->monitors++;
			if (local->monitors == 1) {
				local->hw.conf.flags |= IEEE80211_CONF_MONITOR;
				hw_reconf_flags |= IEEE80211_CONF_CHANGE_MONITOR;
			}
		}

		ieee80211_adjust_monitor_flags(sdata, 1);
		ieee80211_configure_filter(local);
@@ -1423,8 +1417,6 @@ int ieee80211_do_open(struct wireless_dev *wdev, bool coming_up)
		rcu_assign_pointer(local->p2p_sdata, sdata);
		break;
	case NL80211_IFTYPE_MONITOR:
		if (sdata->u.mntr.flags & MONITOR_FLAG_COOK_FRAMES)
			break;
		list_add_tail_rcu(&sdata->u.mntr.list, &local->mon_list);
		break;
	default:
Loading