mirror of
https://github.com/shenmintao/aic8800d80.git
synced 2026-09-26 17:44:16 +00:00
Compare commits
3
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
bef3cc252f | ||
|
|
d9688590c2 | ||
|
|
4902793c01 |
@@ -4420,13 +4420,29 @@ cfg80211_chandef_identical(const struct cfg80211_chan_def *chandef1,
|
||||
}
|
||||
#endif
|
||||
|
||||
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(6, 13, 0))
|
||||
static int rwnx_cfg80211_set_monitor_channel(struct wiphy *wiphy, struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef)
|
||||
#else
|
||||
static int rwnx_cfg80211_set_monitor_channel(struct wiphy *wiphy,
|
||||
struct cfg80211_chan_def *chandef)
|
||||
#endif
|
||||
#define RWNX_CFG80211_OP_TYPE(_member) \
|
||||
typeof(((struct cfg80211_ops *)0)->_member)
|
||||
#define RWNX_CFG80211_OP_MATCH(_member, _type) \
|
||||
__builtin_types_compatible_p(RWNX_CFG80211_OP_TYPE(_member), _type)
|
||||
#define RWNX_CFG80211_OP_ASSERT(_member, _callback) \
|
||||
typedef char rwnx_cfg80211_##_member##_signature_must_match[ \
|
||||
__builtin_types_compatible_p(RWNX_CFG80211_OP_TYPE(_member), \
|
||||
typeof(&(_callback))) ? 1 : -1]
|
||||
|
||||
typedef int (*rwnx_set_monitor_channel_legacy_t)(
|
||||
struct wiphy *wiphy, struct cfg80211_chan_def *chandef);
|
||||
typedef int (*rwnx_set_monitor_channel_dev_t)(
|
||||
struct wiphy *wiphy, struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef);
|
||||
|
||||
typedef char rwnx_set_monitor_channel_signature_must_be_supported[
|
||||
(RWNX_CFG80211_OP_MATCH(set_monitor_channel,
|
||||
rwnx_set_monitor_channel_legacy_t) ||
|
||||
RWNX_CFG80211_OP_MATCH(set_monitor_channel,
|
||||
rwnx_set_monitor_channel_dev_t)) ? 1 : -1];
|
||||
|
||||
static int rwnx_cfg80211_set_monitor_channel_common(
|
||||
struct wiphy *wiphy, struct cfg80211_chan_def *chandef)
|
||||
{
|
||||
struct rwnx_hw *rwnx_hw = wiphy_priv(wiphy);
|
||||
struct rwnx_vif *rwnx_vif;
|
||||
@@ -4479,19 +4495,40 @@ static int rwnx_cfg80211_set_monitor_channel(struct wiphy *wiphy,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_set_monitor_channel_legacy(
|
||||
struct wiphy *wiphy, struct cfg80211_chan_def *chandef)
|
||||
{
|
||||
return rwnx_cfg80211_set_monitor_channel_common(wiphy, chandef);
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_set_monitor_channel_dev(
|
||||
struct wiphy *wiphy, struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef)
|
||||
{
|
||||
(void)dev;
|
||||
return rwnx_cfg80211_set_monitor_channel_common(wiphy, chandef);
|
||||
}
|
||||
|
||||
#define RWNX_CFG80211_SET_MONITOR_CHANNEL_CB \
|
||||
__builtin_choose_expr( \
|
||||
RWNX_CFG80211_OP_MATCH(set_monitor_channel, \
|
||||
rwnx_set_monitor_channel_dev_t), \
|
||||
rwnx_cfg80211_set_monitor_channel_dev, \
|
||||
rwnx_cfg80211_set_monitor_channel_legacy)
|
||||
|
||||
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(6, 13, 0))
|
||||
int rwnx_cfg80211_set_monitor_channel_(struct wiphy *wiphy,
|
||||
struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef)
|
||||
{
|
||||
return rwnx_cfg80211_set_monitor_channel(wiphy, dev, chandef);
|
||||
(void)dev;
|
||||
return rwnx_cfg80211_set_monitor_channel_common(wiphy, chandef);
|
||||
}
|
||||
#else
|
||||
int rwnx_cfg80211_set_monitor_channel_(struct wiphy *wiphy,
|
||||
struct cfg80211_chan_def *chandef)
|
||||
{
|
||||
return rwnx_cfg80211_set_monitor_channel(wiphy, chandef);
|
||||
return rwnx_cfg80211_set_monitor_channel_common(wiphy, chandef);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -4553,15 +4590,45 @@ void rwnx_cfg80211_mgmt_frame_register(struct wiphy *wiphy,
|
||||
* have changed. The actual parameter values are available in
|
||||
* struct wiphy. If returning an error, no value should be changed.
|
||||
*/
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(6, 17, 0)
|
||||
static int rwnx_cfg80211_set_wiphy_params(struct wiphy *wiphy, int radio_idx, u32 changed)
|
||||
#else
|
||||
static int rwnx_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
|
||||
#endif
|
||||
typedef int (*rwnx_set_wiphy_params_legacy_t)(struct wiphy *wiphy,
|
||||
u32 changed);
|
||||
typedef int (*rwnx_set_wiphy_params_radio_t)(struct wiphy *wiphy,
|
||||
int radio_idx, u32 changed);
|
||||
|
||||
typedef char rwnx_set_wiphy_params_signature_must_be_supported[
|
||||
(RWNX_CFG80211_OP_MATCH(set_wiphy_params,
|
||||
rwnx_set_wiphy_params_legacy_t) ||
|
||||
RWNX_CFG80211_OP_MATCH(set_wiphy_params,
|
||||
rwnx_set_wiphy_params_radio_t)) ? 1 : -1];
|
||||
|
||||
static int rwnx_cfg80211_set_wiphy_params_common(struct wiphy *wiphy,
|
||||
u32 changed)
|
||||
{
|
||||
(void)wiphy;
|
||||
(void)changed;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_set_wiphy_params_legacy(struct wiphy *wiphy,
|
||||
u32 changed)
|
||||
{
|
||||
return rwnx_cfg80211_set_wiphy_params_common(wiphy, changed);
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_set_wiphy_params_radio(struct wiphy *wiphy,
|
||||
int radio_idx, u32 changed)
|
||||
{
|
||||
(void)radio_idx;
|
||||
return rwnx_cfg80211_set_wiphy_params_common(wiphy, changed);
|
||||
}
|
||||
|
||||
#define RWNX_CFG80211_SET_WIPHY_PARAMS_CB \
|
||||
__builtin_choose_expr( \
|
||||
RWNX_CFG80211_OP_MATCH(set_wiphy_params, \
|
||||
rwnx_set_wiphy_params_radio_t), \
|
||||
rwnx_cfg80211_set_wiphy_params_radio, \
|
||||
rwnx_cfg80211_set_wiphy_params_legacy)
|
||||
|
||||
|
||||
/**
|
||||
* @set_tx_power: set the transmit power according to the parameters,
|
||||
@@ -4570,18 +4637,25 @@ static int rwnx_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
|
||||
* always be %NULL unless the driver supports per-vif TX power
|
||||
* (as advertised by the nl80211 feature flag.)
|
||||
*/
|
||||
static int rwnx_cfg80211_set_tx_power(struct wiphy *wiphy,
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 8, 0)
|
||||
struct wireless_dev *wdev,
|
||||
#endif
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(6, 17, 0)
|
||||
int radio_idx,
|
||||
#endif
|
||||
enum nl80211_tx_power_setting type, int mbm)
|
||||
typedef int (*rwnx_set_tx_power_no_wdev_t)(
|
||||
struct wiphy *wiphy, enum nl80211_tx_power_setting type, int mbm);
|
||||
typedef int (*rwnx_set_tx_power_wdev_t)(
|
||||
struct wiphy *wiphy, struct wireless_dev *wdev,
|
||||
enum nl80211_tx_power_setting type, int mbm);
|
||||
typedef int (*rwnx_set_tx_power_radio_t)(
|
||||
struct wiphy *wiphy, struct wireless_dev *wdev, int radio_idx,
|
||||
enum nl80211_tx_power_setting type, int mbm);
|
||||
|
||||
typedef char rwnx_set_tx_power_signature_must_be_supported[
|
||||
(RWNX_CFG80211_OP_MATCH(set_tx_power, rwnx_set_tx_power_no_wdev_t) ||
|
||||
RWNX_CFG80211_OP_MATCH(set_tx_power, rwnx_set_tx_power_wdev_t) ||
|
||||
RWNX_CFG80211_OP_MATCH(set_tx_power,
|
||||
rwnx_set_tx_power_radio_t)) ? 1 : -1];
|
||||
|
||||
static int rwnx_cfg80211_set_tx_power_common(
|
||||
struct wiphy *wiphy, struct wireless_dev *wdev,
|
||||
enum nl80211_tx_power_setting type, int mbm)
|
||||
{
|
||||
#if LINUX_VERSION_CODE < KERNEL_VERSION(3, 8, 0)
|
||||
struct wireless_dev *wdev = NULL;
|
||||
#endif
|
||||
struct rwnx_hw *rwnx_hw = wiphy_priv(wiphy);
|
||||
struct rwnx_vif *vif;
|
||||
s8 pwr;
|
||||
@@ -4607,31 +4681,112 @@ int radio_idx,
|
||||
return res;
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_get_tx_power(struct wiphy *wiphy,
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 8, 0)
|
||||
struct wireless_dev *wdev,
|
||||
#endif
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(6, 17, 0)
|
||||
int radio_idx,
|
||||
#endif
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(6, 14, 0)
|
||||
unsigned int link_id,
|
||||
#endif
|
||||
int *mbm)
|
||||
static int rwnx_cfg80211_set_tx_power_no_wdev(
|
||||
struct wiphy *wiphy, enum nl80211_tx_power_setting type, int mbm)
|
||||
{
|
||||
#if LINUX_VERSION_CODE < KERNEL_VERSION(3, 8, 0)
|
||||
struct wireless_dev *wdev = NULL;
|
||||
#endif
|
||||
//struct rwnx_hw *rwnx_hw = wiphy_priv(wiphy);
|
||||
//struct rwnx_vif *vif;
|
||||
s8 pwr = 0;
|
||||
int res = 0;
|
||||
|
||||
*mbm = get_txpwr_max(pwr);
|
||||
|
||||
return res;
|
||||
return rwnx_cfg80211_set_tx_power_common(wiphy, NULL, type, mbm);
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_set_tx_power_wdev(
|
||||
struct wiphy *wiphy, struct wireless_dev *wdev,
|
||||
enum nl80211_tx_power_setting type, int mbm)
|
||||
{
|
||||
return rwnx_cfg80211_set_tx_power_common(wiphy, wdev, type, mbm);
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_set_tx_power_radio(
|
||||
struct wiphy *wiphy, struct wireless_dev *wdev, int radio_idx,
|
||||
enum nl80211_tx_power_setting type, int mbm)
|
||||
{
|
||||
(void)radio_idx;
|
||||
return rwnx_cfg80211_set_tx_power_common(wiphy, wdev, type, mbm);
|
||||
}
|
||||
|
||||
#define RWNX_CFG80211_SET_TX_POWER_CB \
|
||||
__builtin_choose_expr( \
|
||||
RWNX_CFG80211_OP_MATCH(set_tx_power, rwnx_set_tx_power_radio_t), \
|
||||
rwnx_cfg80211_set_tx_power_radio, \
|
||||
__builtin_choose_expr( \
|
||||
RWNX_CFG80211_OP_MATCH(set_tx_power, rwnx_set_tx_power_wdev_t), \
|
||||
rwnx_cfg80211_set_tx_power_wdev, \
|
||||
rwnx_cfg80211_set_tx_power_no_wdev))
|
||||
|
||||
typedef int (*rwnx_get_tx_power_no_wdev_t)(struct wiphy *wiphy, int *dbm);
|
||||
typedef int (*rwnx_get_tx_power_wdev_t)(struct wiphy *wiphy,
|
||||
struct wireless_dev *wdev, int *dbm);
|
||||
typedef int (*rwnx_get_tx_power_link_t)(struct wiphy *wiphy,
|
||||
struct wireless_dev *wdev,
|
||||
unsigned int link_id, int *dbm);
|
||||
typedef int (*rwnx_get_tx_power_radio_link_t)(
|
||||
struct wiphy *wiphy, struct wireless_dev *wdev, int radio_idx,
|
||||
unsigned int link_id, int *dbm);
|
||||
|
||||
typedef char rwnx_get_tx_power_signature_must_be_supported[
|
||||
(RWNX_CFG80211_OP_MATCH(get_tx_power, rwnx_get_tx_power_no_wdev_t) ||
|
||||
RWNX_CFG80211_OP_MATCH(get_tx_power, rwnx_get_tx_power_wdev_t) ||
|
||||
RWNX_CFG80211_OP_MATCH(get_tx_power, rwnx_get_tx_power_link_t) ||
|
||||
RWNX_CFG80211_OP_MATCH(get_tx_power,
|
||||
rwnx_get_tx_power_radio_link_t)) ? 1 : -1];
|
||||
|
||||
static int rwnx_cfg80211_get_tx_power_common(struct wiphy *wiphy,
|
||||
struct wireless_dev *wdev,
|
||||
int *dbm)
|
||||
{
|
||||
s8 pwr = 0;
|
||||
|
||||
(void)wiphy;
|
||||
(void)wdev;
|
||||
if (!dbm)
|
||||
return -EINVAL;
|
||||
|
||||
*dbm = get_txpwr_max(pwr);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_get_tx_power_no_wdev(struct wiphy *wiphy, int *dbm)
|
||||
{
|
||||
return rwnx_cfg80211_get_tx_power_common(wiphy, NULL, dbm);
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_get_tx_power_wdev(struct wiphy *wiphy,
|
||||
struct wireless_dev *wdev,
|
||||
int *dbm)
|
||||
{
|
||||
return rwnx_cfg80211_get_tx_power_common(wiphy, wdev, dbm);
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_get_tx_power_link(struct wiphy *wiphy,
|
||||
struct wireless_dev *wdev,
|
||||
unsigned int link_id, int *dbm)
|
||||
{
|
||||
(void)link_id;
|
||||
return rwnx_cfg80211_get_tx_power_common(wiphy, wdev, dbm);
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_get_tx_power_radio_link(
|
||||
struct wiphy *wiphy, struct wireless_dev *wdev, int radio_idx,
|
||||
unsigned int link_id, int *dbm)
|
||||
{
|
||||
(void)radio_idx;
|
||||
(void)link_id;
|
||||
return rwnx_cfg80211_get_tx_power_common(wiphy, wdev, dbm);
|
||||
}
|
||||
|
||||
#define RWNX_CFG80211_GET_TX_POWER_CB \
|
||||
__builtin_choose_expr( \
|
||||
RWNX_CFG80211_OP_MATCH(get_tx_power, \
|
||||
rwnx_get_tx_power_radio_link_t), \
|
||||
rwnx_cfg80211_get_tx_power_radio_link, \
|
||||
__builtin_choose_expr( \
|
||||
RWNX_CFG80211_OP_MATCH(get_tx_power, \
|
||||
rwnx_get_tx_power_link_t), \
|
||||
rwnx_cfg80211_get_tx_power_link, \
|
||||
__builtin_choose_expr( \
|
||||
RWNX_CFG80211_OP_MATCH(get_tx_power, \
|
||||
rwnx_get_tx_power_wdev_t), \
|
||||
rwnx_cfg80211_get_tx_power_wdev, \
|
||||
rwnx_cfg80211_get_tx_power_no_wdev)))
|
||||
|
||||
/**
|
||||
* @set_power_mgmt: set the power save to one of those two modes:
|
||||
* Power-save off
|
||||
@@ -4999,11 +5154,7 @@ static int rwnx_cfg80211_get_channel(struct wiphy *wiphy,
|
||||
if (rwnx_vif->vif_index == rwnx_hw->monitor_vif)
|
||||
{
|
||||
//retrieve channel from firmware
|
||||
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(6, 13, 0))
|
||||
rwnx_cfg80211_set_monitor_channel(wiphy, wdev->netdev, NULL);
|
||||
#else
|
||||
rwnx_cfg80211_set_monitor_channel(wiphy, NULL);
|
||||
#endif
|
||||
rwnx_cfg80211_set_monitor_channel_common(wiphy, NULL);
|
||||
}
|
||||
|
||||
//Check if channel context is valid
|
||||
@@ -5190,17 +5341,28 @@ send_frame:
|
||||
/**
|
||||
* @start_radar_detection: Start radar detection in the driver.
|
||||
*/
|
||||
static
|
||||
int rwnx_cfg80211_start_radar_detection(struct wiphy *wiphy,
|
||||
struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef
|
||||
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 15, 0))
|
||||
, u32 cac_time_ms
|
||||
#endif
|
||||
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(6, 12, 0))
|
||||
, int link_id
|
||||
#endif
|
||||
)
|
||||
typedef int (*rwnx_start_radar_detection_legacy_t)(
|
||||
struct wiphy *wiphy, struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef);
|
||||
typedef int (*rwnx_start_radar_detection_cac_t)(
|
||||
struct wiphy *wiphy, struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef, u32 cac_time_ms);
|
||||
typedef int (*rwnx_start_radar_detection_link_t)(
|
||||
struct wiphy *wiphy, struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef, u32 cac_time_ms, int link_id);
|
||||
|
||||
typedef char rwnx_start_radar_detection_signature_must_be_supported[
|
||||
(RWNX_CFG80211_OP_MATCH(start_radar_detection,
|
||||
rwnx_start_radar_detection_legacy_t) ||
|
||||
RWNX_CFG80211_OP_MATCH(start_radar_detection,
|
||||
rwnx_start_radar_detection_cac_t) ||
|
||||
RWNX_CFG80211_OP_MATCH(start_radar_detection,
|
||||
rwnx_start_radar_detection_link_t)) ? 1 : -1];
|
||||
|
||||
static int rwnx_cfg80211_start_radar_detection_common(
|
||||
struct wiphy *wiphy, struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef, u32 cac_time_ms,
|
||||
bool start_cac_timer)
|
||||
{
|
||||
struct rwnx_hw *rwnx_hw = wiphy_priv(wiphy);
|
||||
struct rwnx_vif *rwnx_vif = netdev_priv(dev);
|
||||
@@ -5208,9 +5370,8 @@ int rwnx_cfg80211_start_radar_detection(struct wiphy *wiphy,
|
||||
|
||||
printk("%s\n", __func__);
|
||||
|
||||
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 15, 0))
|
||||
rwnx_radar_start_cac(&rwnx_hw->radar, cac_time_ms, rwnx_vif);
|
||||
#endif
|
||||
if (start_cac_timer)
|
||||
rwnx_radar_start_cac(&rwnx_hw->radar, cac_time_ms, rwnx_vif);
|
||||
rwnx_send_apm_start_cac_req(rwnx_hw, rwnx_vif, chandef, &cfm);
|
||||
|
||||
if (cfm.status == CO_OK) {
|
||||
@@ -5228,6 +5389,42 @@ int rwnx_cfg80211_start_radar_detection(struct wiphy *wiphy,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_start_radar_detection_legacy(
|
||||
struct wiphy *wiphy, struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef)
|
||||
{
|
||||
return rwnx_cfg80211_start_radar_detection_common(
|
||||
wiphy, dev, chandef, 0, false);
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_start_radar_detection_cac(
|
||||
struct wiphy *wiphy, struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef, u32 cac_time_ms)
|
||||
{
|
||||
return rwnx_cfg80211_start_radar_detection_common(
|
||||
wiphy, dev, chandef, cac_time_ms, true);
|
||||
}
|
||||
|
||||
static int rwnx_cfg80211_start_radar_detection_link(
|
||||
struct wiphy *wiphy, struct net_device *dev,
|
||||
struct cfg80211_chan_def *chandef, u32 cac_time_ms, int link_id)
|
||||
{
|
||||
(void)link_id;
|
||||
return rwnx_cfg80211_start_radar_detection_common(
|
||||
wiphy, dev, chandef, cac_time_ms, true);
|
||||
}
|
||||
|
||||
#define RWNX_CFG80211_START_RADAR_DETECTION_CB \
|
||||
__builtin_choose_expr( \
|
||||
RWNX_CFG80211_OP_MATCH(start_radar_detection, \
|
||||
rwnx_start_radar_detection_link_t), \
|
||||
rwnx_cfg80211_start_radar_detection_link, \
|
||||
__builtin_choose_expr( \
|
||||
RWNX_CFG80211_OP_MATCH(start_radar_detection, \
|
||||
rwnx_start_radar_detection_cac_t), \
|
||||
rwnx_cfg80211_start_radar_detection_cac, \
|
||||
rwnx_cfg80211_start_radar_detection_legacy))
|
||||
|
||||
/**
|
||||
* @update_ft_ies: Provide updated Fast BSS Transition information to the
|
||||
* driver. If the SME is in the driver/firmware, this information can be
|
||||
@@ -6520,6 +6717,59 @@ static int rwnx_cfg80211_leave_mesh(struct wiphy *wiphy, struct net_device *dev)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Keep every direct cfg80211_ops assignment as a hard compile-time check.
|
||||
* OpenWrt can backport cfg80211 APIs without changing LINUX_VERSION_CODE, and
|
||||
* an incompatible callback must remain a build failure even when warnings are
|
||||
* relaxed by an external package.
|
||||
*/
|
||||
RWNX_CFG80211_OP_ASSERT(add_virtual_intf, rwnx_cfg80211_add_iface);
|
||||
RWNX_CFG80211_OP_ASSERT(del_virtual_intf, rwnx_cfg80211_del_iface);
|
||||
RWNX_CFG80211_OP_ASSERT(change_virtual_intf, rwnx_cfg80211_change_iface);
|
||||
RWNX_CFG80211_OP_ASSERT(start_p2p_device, rwnx_cfgp2p_start_p2p_device);
|
||||
RWNX_CFG80211_OP_ASSERT(stop_p2p_device, rwnx_cfgp2p_stop_p2p_device);
|
||||
RWNX_CFG80211_OP_ASSERT(scan, rwnx_cfg80211_scan);
|
||||
RWNX_CFG80211_OP_ASSERT(connect, rwnx_cfg80211_connect);
|
||||
RWNX_CFG80211_OP_ASSERT(disconnect, rwnx_cfg80211_disconnect);
|
||||
RWNX_CFG80211_OP_ASSERT(add_key, rwnx_cfg80211_add_key);
|
||||
RWNX_CFG80211_OP_ASSERT(get_key, rwnx_cfg80211_get_key);
|
||||
RWNX_CFG80211_OP_ASSERT(del_key, rwnx_cfg80211_del_key);
|
||||
RWNX_CFG80211_OP_ASSERT(set_default_key, rwnx_cfg80211_set_default_key);
|
||||
RWNX_CFG80211_OP_ASSERT(set_default_mgmt_key,
|
||||
rwnx_cfg80211_set_default_mgmt_key);
|
||||
RWNX_CFG80211_OP_ASSERT(add_station, rwnx_cfg80211_add_station);
|
||||
RWNX_CFG80211_OP_ASSERT(del_station, rwnx_cfg80211_del_station_compat);
|
||||
RWNX_CFG80211_OP_ASSERT(change_station, rwnx_cfg80211_change_station);
|
||||
RWNX_CFG80211_OP_ASSERT(mgmt_tx, rwnx_cfg80211_mgmt_tx);
|
||||
RWNX_CFG80211_OP_ASSERT(start_ap, rwnx_cfg80211_start_ap);
|
||||
RWNX_CFG80211_OP_ASSERT(change_beacon, rwnx_cfg80211_change_beacon);
|
||||
RWNX_CFG80211_OP_ASSERT(stop_ap, rwnx_cfg80211_stop_ap);
|
||||
RWNX_CFG80211_OP_ASSERT(probe_client, rwnx_cfg80211_probe_client);
|
||||
RWNX_CFG80211_OP_ASSERT(set_txq_params, rwnx_cfg80211_set_txq_params);
|
||||
RWNX_CFG80211_OP_ASSERT(set_power_mgmt, rwnx_cfg80211_set_power_mgmt);
|
||||
RWNX_CFG80211_OP_ASSERT(get_station, rwnx_cfg80211_get_station);
|
||||
RWNX_CFG80211_OP_ASSERT(remain_on_channel,
|
||||
rwnx_cfg80211_remain_on_channel);
|
||||
RWNX_CFG80211_OP_ASSERT(cancel_remain_on_channel,
|
||||
rwnx_cfg80211_cancel_remain_on_channel);
|
||||
RWNX_CFG80211_OP_ASSERT(dump_survey, rwnx_cfg80211_dump_survey);
|
||||
RWNX_CFG80211_OP_ASSERT(get_channel, rwnx_cfg80211_get_channel);
|
||||
RWNX_CFG80211_OP_ASSERT(update_ft_ies, rwnx_cfg80211_update_ft_ies);
|
||||
RWNX_CFG80211_OP_ASSERT(set_cqm_rssi_config,
|
||||
rwnx_cfg80211_set_cqm_rssi_config);
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 16, 0)
|
||||
RWNX_CFG80211_OP_ASSERT(channel_switch, rwnx_cfg80211_channel_switch);
|
||||
#endif
|
||||
RWNX_CFG80211_OP_ASSERT(change_bss, rwnx_cfg80211_change_bss);
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 17, 0) || \
|
||||
defined(CONFIG_WPA3_FOR_OLD_KERNEL)
|
||||
RWNX_CFG80211_OP_ASSERT(external_auth, rwnx_cfg80211_external_auth);
|
||||
#endif
|
||||
#ifdef CONFIG_SCHED_SCAN
|
||||
RWNX_CFG80211_OP_ASSERT(sched_scan_start, rwnx_cfg80211_sched_scan_start);
|
||||
RWNX_CFG80211_OP_ASSERT(sched_scan_stop, rwnx_cfg80211_sched_scan_stop);
|
||||
#endif
|
||||
|
||||
static struct cfg80211_ops rwnx_cfg80211_ops = {
|
||||
.add_virtual_intf = rwnx_cfg80211_add_iface,
|
||||
.del_virtual_intf = rwnx_cfg80211_del_iface,
|
||||
@@ -6541,20 +6791,20 @@ static struct cfg80211_ops rwnx_cfg80211_ops = {
|
||||
.start_ap = rwnx_cfg80211_start_ap,
|
||||
.change_beacon = rwnx_cfg80211_change_beacon,
|
||||
.stop_ap = rwnx_cfg80211_stop_ap,
|
||||
.set_monitor_channel = rwnx_cfg80211_set_monitor_channel,
|
||||
.set_monitor_channel = RWNX_CFG80211_SET_MONITOR_CHANNEL_CB,
|
||||
.probe_client = rwnx_cfg80211_probe_client,
|
||||
// .mgmt_frame_register = rwnx_cfg80211_mgmt_frame_register,
|
||||
.set_wiphy_params = rwnx_cfg80211_set_wiphy_params,
|
||||
.set_wiphy_params = RWNX_CFG80211_SET_WIPHY_PARAMS_CB,
|
||||
.set_txq_params = rwnx_cfg80211_set_txq_params,
|
||||
.set_tx_power = rwnx_cfg80211_set_tx_power,
|
||||
.get_tx_power = rwnx_cfg80211_get_tx_power,
|
||||
.set_tx_power = RWNX_CFG80211_SET_TX_POWER_CB,
|
||||
.get_tx_power = RWNX_CFG80211_GET_TX_POWER_CB,
|
||||
.set_power_mgmt = rwnx_cfg80211_set_power_mgmt,
|
||||
.get_station = rwnx_cfg80211_get_station,
|
||||
.remain_on_channel = rwnx_cfg80211_remain_on_channel,
|
||||
.cancel_remain_on_channel = rwnx_cfg80211_cancel_remain_on_channel,
|
||||
.dump_survey = rwnx_cfg80211_dump_survey,
|
||||
.get_channel = rwnx_cfg80211_get_channel,
|
||||
.start_radar_detection = rwnx_cfg80211_start_radar_detection,
|
||||
.start_radar_detection = RWNX_CFG80211_START_RADAR_DETECTION_CB,
|
||||
.update_ft_ies = rwnx_cfg80211_update_ft_ies,
|
||||
.set_cqm_rssi_config = rwnx_cfg80211_set_cqm_rssi_config,
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 16, 0)
|
||||
|
||||
@@ -22,6 +22,52 @@
|
||||
#include "rwnx_events.h"
|
||||
#include "rwnx_compat.h"
|
||||
|
||||
#ifdef CONFIG_RWNX_FULLMAC
|
||||
/* OpenWrt can backport cfg80211 helpers without changing LINUX_VERSION_CODE. */
|
||||
typedef void (*rwnx_cfg80211_cac_event_no_chandef_t)(
|
||||
struct net_device *netdev, enum nl80211_radar_event event, gfp_t gfp);
|
||||
typedef void (*rwnx_cfg80211_cac_event_chandef_t)(
|
||||
struct net_device *netdev, const struct cfg80211_chan_def *chandef,
|
||||
enum nl80211_radar_event event, gfp_t gfp);
|
||||
typedef void (*rwnx_cfg80211_cac_event_link_t)(
|
||||
struct net_device *netdev, const struct cfg80211_chan_def *chandef,
|
||||
enum nl80211_radar_event event, gfp_t gfp, unsigned int link_id);
|
||||
|
||||
#define RWNX_CFG80211_CAC_EVENT_MATCH(_type) \
|
||||
__builtin_types_compatible_p(typeof(&cfg80211_cac_event), _type)
|
||||
|
||||
typedef char rwnx_cfg80211_cac_event_signature_must_be_supported[
|
||||
(RWNX_CFG80211_CAC_EVENT_MATCH(
|
||||
rwnx_cfg80211_cac_event_no_chandef_t) ||
|
||||
RWNX_CFG80211_CAC_EVENT_MATCH(rwnx_cfg80211_cac_event_chandef_t) ||
|
||||
RWNX_CFG80211_CAC_EVENT_MATCH(rwnx_cfg80211_cac_event_link_t)) ? 1 : -1];
|
||||
|
||||
static void rwnx_cfg80211_cac_event_compat(
|
||||
struct net_device *netdev, const struct cfg80211_chan_def *chandef,
|
||||
enum nl80211_radar_event event, gfp_t gfp)
|
||||
{
|
||||
union {
|
||||
typeof(&cfg80211_cac_event) actual;
|
||||
rwnx_cfg80211_cac_event_no_chandef_t no_chandef;
|
||||
rwnx_cfg80211_cac_event_chandef_t chandef;
|
||||
rwnx_cfg80211_cac_event_link_t link;
|
||||
} helper = { .actual = &cfg80211_cac_event };
|
||||
|
||||
if (RWNX_CFG80211_CAC_EVENT_MATCH(
|
||||
rwnx_cfg80211_cac_event_no_chandef_t)) {
|
||||
helper.no_chandef(netdev, event, gfp);
|
||||
return;
|
||||
}
|
||||
|
||||
if (RWNX_CFG80211_CAC_EVENT_MATCH(rwnx_cfg80211_cac_event_link_t)) {
|
||||
helper.link(netdev, chandef, event, gfp, 0);
|
||||
return;
|
||||
}
|
||||
|
||||
helper.chandef(netdev, chandef, event, gfp);
|
||||
}
|
||||
#endif
|
||||
|
||||
/*
|
||||
* tolerated deviation of radar time stamp in usecs on both sides
|
||||
* TODO: this might need to be HW-dependent
|
||||
@@ -1471,15 +1517,8 @@ static void rwnx_radar_cac_work(struct work_struct *ws)
|
||||
}
|
||||
|
||||
ctxt = &rwnx_hw->chanctx_table[radar->cac_vif->ch_index];
|
||||
cfg80211_cac_event(radar->cac_vif->ndev,
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0)
|
||||
&ctxt->chan_def,
|
||||
#endif
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(6, 12, 0)
|
||||
NL80211_RADAR_CAC_FINISHED, GFP_KERNEL, 0);
|
||||
#else
|
||||
NL80211_RADAR_CAC_FINISHED, GFP_KERNEL);
|
||||
#endif
|
||||
rwnx_cfg80211_cac_event_compat(radar->cac_vif->ndev, &ctxt->chan_def,
|
||||
NL80211_RADAR_CAC_FINISHED, GFP_KERNEL);
|
||||
rwnx_send_apm_stop_cac_req(rwnx_hw, radar->cac_vif);
|
||||
rwnx_chanctx_unlink(radar->cac_vif);
|
||||
|
||||
@@ -1613,15 +1652,9 @@ void rwnx_radar_cancel_cac(struct rwnx_radar *radar)
|
||||
struct rwnx_chanctx *ctxt;
|
||||
ctxt = &rwnx_hw->chanctx_table[radar->cac_vif->ch_index];
|
||||
rwnx_send_apm_stop_cac_req(rwnx_hw, radar->cac_vif);
|
||||
cfg80211_cac_event(radar->cac_vif->ndev,
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0)
|
||||
&ctxt->chan_def,
|
||||
#endif
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(6, 12, 0)
|
||||
NL80211_RADAR_CAC_FINISHED, GFP_KERNEL, 0);
|
||||
#else
|
||||
NL80211_RADAR_CAC_ABORTED, GFP_KERNEL);
|
||||
#endif
|
||||
rwnx_cfg80211_cac_event_compat(radar->cac_vif->ndev,
|
||||
&ctxt->chan_def,
|
||||
NL80211_RADAR_CAC_ABORTED, GFP_KERNEL);
|
||||
rwnx_chanctx_unlink(radar->cac_vif);
|
||||
}
|
||||
|
||||
|
||||
@@ -34,6 +34,60 @@
|
||||
#define IEEE80211_MAX_CHAINS 4
|
||||
#endif
|
||||
|
||||
/* OpenWrt can backport these helpers without changing LINUX_VERSION_CODE. */
|
||||
typedef bool (*rwnx_cfg80211_rx_frame_legacy_t)(struct net_device *dev,
|
||||
const u8 *addr, gfp_t gfp);
|
||||
typedef bool (*rwnx_cfg80211_rx_frame_link_t)(struct net_device *dev,
|
||||
const u8 *addr, int link_id,
|
||||
gfp_t gfp);
|
||||
|
||||
#define RWNX_CFG80211_HELPER_MATCH(_helper, _type) \
|
||||
__builtin_types_compatible_p(typeof(&(_helper)), _type)
|
||||
|
||||
typedef char rwnx_cfg80211_rx_spurious_frame_signature_must_be_supported[
|
||||
(RWNX_CFG80211_HELPER_MATCH(cfg80211_rx_spurious_frame,
|
||||
rwnx_cfg80211_rx_frame_legacy_t) ||
|
||||
RWNX_CFG80211_HELPER_MATCH(cfg80211_rx_spurious_frame,
|
||||
rwnx_cfg80211_rx_frame_link_t)) ? 1 : -1];
|
||||
|
||||
typedef char rwnx_cfg80211_rx_unexpected_4addr_frame_signature_must_be_supported[
|
||||
(RWNX_CFG80211_HELPER_MATCH(cfg80211_rx_unexpected_4addr_frame,
|
||||
rwnx_cfg80211_rx_frame_legacy_t) ||
|
||||
RWNX_CFG80211_HELPER_MATCH(cfg80211_rx_unexpected_4addr_frame,
|
||||
rwnx_cfg80211_rx_frame_link_t)) ? 1 : -1];
|
||||
|
||||
static bool rwnx_cfg80211_rx_spurious_frame_compat(struct net_device *dev,
|
||||
const u8 *addr, gfp_t gfp)
|
||||
{
|
||||
union {
|
||||
typeof(&cfg80211_rx_spurious_frame) actual;
|
||||
rwnx_cfg80211_rx_frame_legacy_t legacy;
|
||||
rwnx_cfg80211_rx_frame_link_t link;
|
||||
} helper = { .actual = &cfg80211_rx_spurious_frame };
|
||||
|
||||
if (RWNX_CFG80211_HELPER_MATCH(cfg80211_rx_spurious_frame,
|
||||
rwnx_cfg80211_rx_frame_link_t))
|
||||
return helper.link(dev, addr, -1, gfp);
|
||||
|
||||
return helper.legacy(dev, addr, gfp);
|
||||
}
|
||||
|
||||
static bool rwnx_cfg80211_rx_unexpected_4addr_frame_compat(
|
||||
struct net_device *dev, const u8 *addr, gfp_t gfp)
|
||||
{
|
||||
union {
|
||||
typeof(&cfg80211_rx_unexpected_4addr_frame) actual;
|
||||
rwnx_cfg80211_rx_frame_legacy_t legacy;
|
||||
rwnx_cfg80211_rx_frame_link_t link;
|
||||
} helper = { .actual = &cfg80211_rx_unexpected_4addr_frame };
|
||||
|
||||
if (RWNX_CFG80211_HELPER_MATCH(cfg80211_rx_unexpected_4addr_frame,
|
||||
rwnx_cfg80211_rx_frame_link_t))
|
||||
return helper.link(dev, addr, -1, gfp);
|
||||
|
||||
return helper.legacy(dev, addr, gfp);
|
||||
}
|
||||
|
||||
u8 dhcped = 0;
|
||||
|
||||
u16 tx_legrates_lut_rate[] = {
|
||||
@@ -2394,11 +2448,8 @@ check_len_update:
|
||||
hdr = (struct ieee80211_hdr *)(skb->data + msdu_offset);
|
||||
rwnx_vif = rwnx_rx_get_vif(rwnx_hw, hw_rxhdr->flags_vif_idx);
|
||||
if (rwnx_vif) {
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(6, 17, 0)
|
||||
cfg80211_rx_spurious_frame(rwnx_vif->ndev, hdr->addr2, -1, GFP_ATOMIC);
|
||||
#else
|
||||
cfg80211_rx_spurious_frame(rwnx_vif->ndev, hdr->addr2, GFP_ATOMIC);
|
||||
#endif
|
||||
rwnx_cfg80211_rx_spurious_frame_compat(rwnx_vif->ndev,
|
||||
hdr->addr2, GFP_ATOMIC);
|
||||
}
|
||||
goto end;
|
||||
}
|
||||
@@ -2741,13 +2792,8 @@ check_len_update:
|
||||
|
||||
if (hw_rxhdr->flags_is_4addr && !rwnx_vif->use_4addr) {
|
||||
printk("aicwf: 4addr flag error\n");
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(6, 17, 0)
|
||||
cfg80211_rx_unexpected_4addr_frame(rwnx_vif->ndev,
|
||||
sta->mac_addr, -1, GFP_ATOMIC);
|
||||
#else
|
||||
cfg80211_rx_unexpected_4addr_frame(rwnx_vif->ndev,
|
||||
sta->mac_addr, GFP_ATOMIC);
|
||||
#endif
|
||||
rwnx_cfg80211_rx_unexpected_4addr_frame_compat(
|
||||
rwnx_vif->ndev, sta->mac_addr, GFP_ATOMIC);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user