Commit b187c70b authored by Kalle Valo's avatar Kalle Valo

Merge tag 'iwlwifi-next-for-kalle-2023-01-30' of...

Merge tag 'iwlwifi-next-for-kalle-2023-01-30' of http://git.kernel.org/pub/scm/linux/kernel/git/iwlwifi/iwlwifi-next

iwlwifi updates towards v6.3, this patch-set contains:

* EHT rate reporting
* Sniffer support for EHT and a few fixes in the related code
* A few general cleanups and small bugfixes
* Bump FW API to 74 for AX devices
* Fix a compilation error in mei (it still depends on BROKEN)
* STEP equalizer support - transfer some Phy related parameters from
  the BIOS to the firmware
parents 75da437a 9cbd5a8a
......@@ -10,7 +10,7 @@
#include "fw/api/txq.h"
/* Highest firmware API version supported */
#define IWL_22000_UCODE_API_MAX 72
#define IWL_22000_UCODE_API_MAX 74
/* Lowest firmware API version supported */
#define IWL_22000_UCODE_API_MIN 39
......
......@@ -153,6 +153,7 @@ enum iwl_legacy_cmds {
/**
* @TXPATH_FLUSH: &struct iwl_tx_path_flush_cmd
* response in &struct iwl_tx_path_flush_cmd_rsp
*/
TXPATH_FLUSH = 0x1e,
......
......@@ -83,7 +83,7 @@ enum iwl_data_path_subcmd_ids {
MONITOR_NOTIF = 0xF4,
/**
* @RX_NO_DATA_NOTIF: &struct iwl_rx_no_data
* @RX_NO_DATA_NOTIF: &struct iwl_rx_no_data or &struct iwl_rx_no_data_ver_3
*/
RX_NO_DATA_NOTIF = 0xF5,
......
......@@ -273,7 +273,7 @@ enum iwl_rx_mpdu_mac_info {
};
/* TSF overload low dword */
enum iwl_rx_phy_data0 {
enum iwl_rx_phy_he_data0 {
/* info type: HE any */
IWL_RX_PHY_DATA0_HE_BEAM_CHNG = 0x00000001,
IWL_RX_PHY_DATA0_HE_UPLINK = 0x00000002,
......@@ -289,6 +289,25 @@ enum iwl_rx_phy_data0 {
IWL_RX_PHY_DATA0_HE_DELIM_EOF = 0x80000000,
};
/* TSF overload low dword */
enum iwl_rx_phy_eht_data0 {
/* info type: EHT any */
/* 1 bits reserved */
IWL_RX_PHY_DATA0_EHT_UPLINK = BIT(1),
IWL_RX_PHY_DATA0_EHT_BSS_COLOR_MASK = 0x000000fc,
IWL_RX_PHY_DATA0_ETH_SPATIAL_REUSE_MASK = 0x00000f00,
IWL_RX_PHY_DATA0_EHT_PS160 = BIT(12),
IWL_RX_PHY_DATA0_EHT_TXOP_DUR_MASK = 0x000fe000,
IWL_RX_PHY_DATA0_EHT_LDPC_EXT_SYM = BIT(20),
IWL_RX_PHY_DATA0_EHT_PRE_FEC_PAD_MASK = 0x00600000,
IWL_RX_PHY_DATA0_EHT_PE_DISAMBIG = BIT(23),
IWL_RX_PHY_DATA0_EHT_BW320_SLOT = BIT(24),
IWL_RX_PHY_DATA0_EHT_SIGA_CRC_OK = BIT(25),
IWL_RX_PHY_DATA0_EHT_PHY_VER = 0x1c000000,
/* 2 bits reserved */
IWL_RX_PHY_DATA0_EHT_DELIM_EOF = BIT(31),
};
enum iwl_rx_phy_info_type {
IWL_RX_PHY_INFO_TYPE_NONE = 0,
IWL_RX_PHY_INFO_TYPE_CCK = 1,
......@@ -301,19 +320,26 @@ enum iwl_rx_phy_info_type {
IWL_RX_PHY_INFO_TYPE_HE_TB = 8,
IWL_RX_PHY_INFO_TYPE_HE_MU_EXT = 9,
IWL_RX_PHY_INFO_TYPE_HE_TB_EXT = 10,
IWL_RX_PHY_INFO_TYPE_EHT_MU = 11,
IWL_RX_PHY_INFO_TYPE_EHT_TB = 12,
IWL_RX_PHY_INFO_TYPE_EHT_MU_EXT = 13,
IWL_RX_PHY_INFO_TYPE_EHT_TB_EXT = 14,
};
/* TSF overload high dword */
enum iwl_rx_phy_data1 {
enum iwl_rx_phy_common_data1 {
/*
* check this first - if TSF overload is set,
* see &enum iwl_rx_phy_info_type
*/
IWL_RX_PHY_DATA1_INFO_TYPE_MASK = 0xf0000000,
/* info type: HT/VHT/HE any */
/* info type: HT/VHT/HE/EHT any */
IWL_RX_PHY_DATA1_LSIG_LEN_MASK = 0x0fff0000,
};
/* TSF overload high dword For HE rates*/
enum iwl_rx_phy_he_data1 {
/* info type: HE MU/MU-EXT */
IWL_RX_PHY_DATA1_HE_MU_SIGB_COMPRESSION = 0x00000001,
IWL_RX_PHY_DATA1_HE_MU_SIBG_SYM_OR_USER_NUM_MASK = 0x0000001e,
......@@ -329,8 +355,23 @@ enum iwl_rx_phy_data1 {
IWL_RX_PHY_DATA1_HE_TB_LOW_SS_MASK = 0x0000000e,
};
/* TSF overload high dword For EHT-MU/TB rates*/
enum iwl_rx_phy_eht_data1 {
/* info type: EHT-MU */
IWL_RX_PHY_DATA1_EHT_MU_NUM_SIG_SYM_USIGA2 = 0x0000001f,
/* info type: EHT-TB */
IWL_RX_PHY_DATA1_EHT_TB_PILOT_TYPE = BIT(0),
IWL_RX_PHY_DATA1_EHT_TB_LOW_SS = 0x0000001e,
/* info type: EHT any */
/* number of EHT-LTF symbols 0 - 1 EHT-LTF, 1 - 2 EHT-LTFs, 2 - 4 EHT-LTFs,
* 3 - 6 EHT-LTFs, 4 - 8 EHT-LTFs */
IWL_RX_PHY_DATA1_EHT_SIG_LTF_NUM = 0x000000e0,
IWL_RX_PHY_DATA1_EHT_RU_ALLOC = 0x0000ff00,
};
/* goes into Metadata DW 7 */
enum iwl_rx_phy_data2 {
enum iwl_rx_phy_he_data2 {
/* info type: HE MU-EXT */
/* the a1/a2/... is what the PHY/firmware calls the values */
IWL_RX_PHY_DATA2_HE_MU_EXT_CH1_RU0 = 0x000000ff, /* a1 */
......@@ -346,7 +387,7 @@ enum iwl_rx_phy_data2 {
};
/* goes into Metadata DW 8 */
enum iwl_rx_phy_data3 {
enum iwl_rx_phy_he_data3 {
/* info type: HE MU-EXT */
IWL_RX_PHY_DATA3_HE_MU_EXT_CH1_RU1 = 0x000000ff, /* c1 */
IWL_RX_PHY_DATA3_HE_MU_EXT_CH1_RU3 = 0x0000ff00, /* c2 */
......@@ -355,7 +396,7 @@ enum iwl_rx_phy_data3 {
};
/* goes into Metadata DW 4 high 16 bits */
enum iwl_rx_phy_data4 {
enum iwl_rx_phy_he_he_data4 {
/* info type: HE MU-EXT */
IWL_RX_PHY_DATA4_HE_MU_EXT_CH1_CTR_RU = 0x0001,
IWL_RX_PHY_DATA4_HE_MU_EXT_CH2_CTR_RU = 0x0002,
......@@ -366,6 +407,51 @@ enum iwl_rx_phy_data4 {
IWL_RX_PHY_DATA4_HE_MU_EXT_PREAMBLE_PUNC_TYPE_MASK = 0x0600,
};
/* goes into Metadata DW 7 */
enum iwl_rx_phy_eht_data2 {
/* info type: EHT-MU-EXT */
/* OFDM_RX_VECTOR_COMMON_RU_ALLOC_0_OUT */
IWL_RX_PHY_DATA2_EHT_MU_EXT_RU_ALLOC_A1 = 0x000001ff,
IWL_RX_PHY_DATA2_EHT_MU_EXT_RU_ALLOC_A2 = 0x0003fe00,
IWL_RX_PHY_DATA2_EHT_MU_EXT_RU_ALLOC_A3 = 0x01fc0000,
/* info type: EHT-TB-EXT */
IWL_RX_PHY_DATA2_EHT_TB_EXT_TRIG_SIGA1 = 0xffffffff,
};
/* goes into Metadata DW 8 */
enum iwl_rx_phy_eht_data3 {
/* info type: EHT-MU-EXT */
/* OFDM_RX_VECTOR_COMMON_RU_ALLOC_1_OUT */
IWL_RX_PHY_DATA3_EHT_MU_EXT_RU_ALLOC_B1 = 0x000001ff,
IWL_RX_PHY_DATA3_EHT_MU_EXT_RU_ALLOC_B2 = 0x0003fe00,
IWL_RX_PHY_DATA3_EHT_MU_EXT_RU_ALLOC_B3 = 0x01fc0000,
};
/* goes into Metadata DW 4 */
enum iwl_rx_phy_eht_data4 {
/* info type: EHT-MU-EXT */
/* OFDM_RX_VECTOR_COMMON_RU_ALLOC_2_OUT */
IWL_RX_PHY_DATA4_EHT_MU_EXT_RU_ALLOC_C1 = 0x000001ff,
IWL_RX_PHY_DATA4_EHT_MU_EXT_RU_ALLOC_C2 = 0x0003fe00,
IWL_RX_PHY_DATA4_EHT_MU_EXT_RU_ALLOC_C3 = 0x01fc0000,
IWL_RX_PHY_DATA4_EHT_MU_EXT_SIGB_MCS = 0x18000000,
};
/* goes into Metadata DW 16 */
enum iwl_rx_phy_data5 {
/* info type: EHT any */
IWL_RX_PHY_DATA5_EHT_TYPE_AND_COMP = 0x00000003,
/* info type: EHT-TB */
IWL_RX_PHY_DATA5_EHT_TB_SPATIAL_REUSE1 = 0x0000003c,
IWL_RX_PHY_DATA5_EHT_TB_SPATIAL_REUSE2 = 0x000003c0,
/* info type: EHT-MU */
IWL_RX_PHY_DATA5_EHT_MU_PUNC_CH_CODE = 0x0000007c,
IWL_RX_PHY_DATA5_EHT_MU_STA_ID_USR = 0x0003ff80,
IWL_RX_PHY_DATA5_EHT_MU_NUM_USR_NON_OFDMA = 0x001c0000,
IWL_RX_PHY_DATA5_EHT_MU_SPATIAL_CONF_USR_FIELD = 0x0fe00000,
};
/**
* struct iwl_rx_mpdu_desc_v1 - RX MPDU descriptor
*/
......@@ -440,7 +526,9 @@ struct iwl_rx_mpdu_desc_v1 {
/**
* @phy_data1: valid only if
* %IWL_RX_MPDU_PHY_TSF_OVERLOAD is set,
* see &enum iwl_rx_phy_data1.
* see &enum iwl_rx_phy_common_data1 or
* &enum iwl_rx_phy_he_data1 or
* &enum iwl_rx_phy_eht_data1.
*/
__le32 phy_data1;
};
......@@ -540,11 +628,18 @@ struct iwl_rx_mpdu_desc_v3 {
__le32 phy_data1;
};
};
/* DW16 & DW17 */
/* DW16 */
/**
* @phy_data5: valid only if
* %IWL_RX_MPDU_PHY_TSF_OVERLOAD is set,
* see &enum iwl_rx_phy_data5.
*/
__le32 phy_data5;
/* DW17 */
/**
* @reserved: reserved
*/
__le32 reserved[2];
__le32 reserved[1];
} __packed; /* RX_MPDU_RES_START_API_S_VER_3,
RX_MPDU_RES_START_API_S_VER_5 */
......@@ -639,12 +734,14 @@ struct iwl_rx_mpdu_desc {
#define RX_NO_DATA_INFO_ERR_UNSUPPORTED_RATE 2
#define RX_NO_DATA_INFO_ERR_NO_DELIM 3
#define RX_NO_DATA_INFO_ERR_BAD_MAC_HDR 4
#define RX_NO_DATA_INFO_LOW_ENERGY 5
#define RX_NO_DATA_FRAME_TIME_POS 0
#define RX_NO_DATA_FRAME_TIME_MSK (0xfffff << RX_NO_DATA_FRAME_TIME_POS)
#define RX_NO_DATA_RX_VEC0_HE_NSTS_MSK 0x03800000
#define RX_NO_DATA_RX_VEC0_VHT_NSTS_MSK 0x38000000
#define RX_NO_DATA_RX_VEC2_EHT_NSTS_MSK 0x00f00000
/**
* struct iwl_rx_no_data - RX no data descriptor
......@@ -654,7 +751,8 @@ struct iwl_rx_mpdu_desc {
* @on_air_rise_time: GP2 during on air rise
* @fr_time: frame time
* @rate: rate/mcs of frame
* @phy_info: &enum iwl_rx_phy_data0 and &enum iwl_rx_phy_info_type
* @phy_info: &enum iwl_rx_phy_he_data0 or &enum iwl_rx_phy_eht_data0
* based on &enum iwl_rx_phy_info_type
* @rx_vec: DW-12:9 raw RX vectors from DSP according to modulation type.
* for VHT: OFDM_RX_VECTOR_SIGA1_OUT, OFDM_RX_VECTOR_SIGA2_OUT
* for HE: OFDM_RX_VECTOR_HE_SIGA1_OUT, OFDM_RX_VECTOR_HE_SIGA2_OUT
......@@ -670,6 +768,33 @@ struct iwl_rx_no_data {
} __packed; /* RX_NO_DATA_NTFY_API_S_VER_1,
RX_NO_DATA_NTFY_API_S_VER_2 */
/**
* struct iwl_rx_no_data_ver_3 - RX no data descriptor
* @info: 7:0 frame type, 15:8 RX error type
* @rssi: 7:0 energy chain-A,
* 15:8 chain-B, measured at FINA time (FINA_ENERGY), 16:23 channel
* @on_air_rise_time: GP2 during on air rise
* @fr_time: frame time
* @rate: rate/mcs of frame
* @phy_info: &enum iwl_rx_phy_eht_data0 and &enum iwl_rx_phy_info_type
* @rx_vec: DW-12:9 raw RX vectors from DSP according to modulation type.
* for VHT: OFDM_RX_VECTOR_SIGA1_OUT, OFDM_RX_VECTOR_SIGA2_OUT
* for HE: OFDM_RX_VECTOR_HE_SIGA1_OUT, OFDM_RX_VECTOR_HE_SIGA2_OUT
* for EHT: OFDM_RX_VECTOR_USIG_A1_OUT, OFDM_RX_VECTOR_USIG_A2_OUT,
* OFDM_RX_VECTOR_EHT_OUT, OFDM_RX_VECTOR_EHT_USER_FIELD_OUT
*/
struct iwl_rx_no_data_ver_3 {
__le32 info;
__le32 rssi;
__le32 on_air_rise_time;
__le32 fr_time;
__le32 rate;
__le32 phy_info[2];
__le32 rx_vec[4];
} __packed; /* RX_NO_DATA_NTFY_API_S_VER_1,
RX_NO_DATA_NTFY_API_S_VER_2
RX_NO_DATA_NTFY_API_S_VER_3 */
struct iwl_frame_release {
u8 baid;
u8 reserved;
......
// SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause
/*
* Copyright(c) 2021 Intel Corporation
* Copyright(c) 2021-2022 Intel Corporation
*/
#include "iwl-drv.h"
......@@ -246,6 +246,63 @@ void *iwl_uefi_get_reduced_power(struct iwl_trans *trans, size_t *len)
return data;
}
static int iwl_uefi_step_parse(struct uefi_cnv_common_step_data *common_step_data,
struct iwl_trans *trans)
{
if (common_step_data->revision != 1)
return -EINVAL;
trans->mbx_addr_0_step = (u32)common_step_data->revision |
(u32)common_step_data->cnvi_eq_channel << 8 |
(u32)common_step_data->cnvr_eq_channel << 16 |
(u32)common_step_data->radio1 << 24;
trans->mbx_addr_1_step = (u32)common_step_data->radio2;
return 0;
}
void iwl_uefi_get_step_table(struct iwl_trans *trans)
{
struct uefi_cnv_common_step_data *data;
unsigned long package_size;
efi_status_t status;
int ret;
if (trans->trans_cfg->device_family < IWL_DEVICE_FAMILY_AX210)
return;
if (!efi_rt_services_supported(EFI_RT_SUPPORTED_GET_VARIABLE))
return;
/* TODO: we hardcode a maximum length here, because reading
* from the UEFI is not working. To implement this properly,
* we have to call efivar_entry_size().
*/
package_size = IWL_HARDCODED_STEP_SIZE;
data = kmalloc(package_size, GFP_KERNEL);
if (!data)
return;
status = efi.get_variable(IWL_UEFI_STEP_NAME, &IWL_EFI_VAR_GUID,
NULL, &package_size, data);
if (status != EFI_SUCCESS) {
IWL_DEBUG_FW(trans,
"STEP UEFI variable not found 0x%lx\n", status);
goto out_free;
}
IWL_DEBUG_FW(trans, "Read STEP from UEFI with size %lu\n",
package_size);
ret = iwl_uefi_step_parse(data, trans);
if (ret < 0)
IWL_DEBUG_FW(trans, "Cannot read STEP tables. rev is invalid\n");
out_free:
kfree(data);
}
IWL_EXPORT_SYMBOL(iwl_uefi_get_step_table);
#ifdef CONFIG_ACPI
static int iwl_uefi_sgom_parse(struct uefi_cnv_wlan_sgom_data *sgom_data,
struct iwl_fw_runtime *fwrt)
......
/* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */
/*
* Copyright(c) 2021 Intel Corporation
* Copyright(c) 2021-2022 Intel Corporation
*/
#ifndef __iwl_fw_uefi__
#define __iwl_fw_uefi__
......@@ -8,6 +8,7 @@
#define IWL_UEFI_OEM_PNVM_NAME L"UefiCnvWlanOemSignedPnvm"
#define IWL_UEFI_REDUCED_POWER_NAME L"UefiCnvWlanReducedPower"
#define IWL_UEFI_SGOM_NAME L"UefiCnvWlanSarGeoOffsetMapping"
#define IWL_UEFI_STEP_NAME L"UefiCnvCommonSTEP"
/*
* TODO: we have these hardcoded values that the caller must pass,
......@@ -18,6 +19,7 @@
#define IWL_HARDCODED_PNVM_SIZE 4096
#define IWL_HARDCODED_REDUCE_POWER_SIZE 32768
#define IWL_HARDCODED_SGOM_SIZE 339
#define IWL_HARDCODED_STEP_SIZE 6
struct pnvm_sku_package {
u8 rev;
......@@ -32,6 +34,15 @@ struct uefi_cnv_wlan_sgom_data {
u8 offset_map[IWL_HARDCODED_SGOM_SIZE - 1];
} __packed;
struct uefi_cnv_common_step_data {
u8 revision;
u8 step_mode;
u8 cnvi_eq_channel;
u8 cnvr_eq_channel;
u8 radio1;
u8 radio2;
} __packed;
/*
* This is known to be broken on v4.19 and to work on v5.4. Until we
* figure out why this is the case and how to make it work, simply
......@@ -40,6 +51,7 @@ struct uefi_cnv_wlan_sgom_data {
#ifdef CONFIG_EFI
void *iwl_uefi_get_pnvm(struct iwl_trans *trans, size_t *len);
void *iwl_uefi_get_reduced_power(struct iwl_trans *trans, size_t *len);
void iwl_uefi_get_step_table(struct iwl_trans *trans);
#else /* CONFIG_EFI */
static inline
void *iwl_uefi_get_pnvm(struct iwl_trans *trans, size_t *len)
......@@ -52,6 +64,11 @@ void *iwl_uefi_get_reduced_power(struct iwl_trans *trans, size_t *len)
{
return ERR_PTR(-EOPNOTSUPP);
}
static inline
void iwl_uefi_get_step_table(struct iwl_trans *trans)
{
}
#endif /* CONFIG_EFI */
#if defined(CONFIG_EFI) && defined(CONFIG_ACPI)
......
......@@ -140,6 +140,20 @@ struct iwl_prph_scratch_uefi_cfg {
__le32 reserved;
} __packed; /* PERIPH_SCRATCH_UEFI_CFG_S */
/*
* struct iwl_prph_scratch_step_cfg - prph scratch step configuration
* @mbx_addr_0: [0:7] revision,
* [8:15] cnvi_to_cnvr length,
* [16:23] cnvr_to_cnvi channel length,
* [24:31] radio1 reserved
* @mbx_addr_1: [0:7] radio2 reserved
*/
struct iwl_prph_scratch_step_cfg {
__le32 mbx_addr_0;
__le32 mbx_addr_1;
} __packed;
/*
* struct iwl_prph_scratch_ctrl_cfg - prph scratch ctrl and config
* @version: version information of context info and HW
......@@ -147,6 +161,7 @@ struct iwl_prph_scratch_uefi_cfg {
* @pnvm_cfg: ror configuration
* @hwm_cfg: hwm configuration
* @rbd_cfg: default RX queue configuration
* @step_cfg: step configuration
*/
struct iwl_prph_scratch_ctrl_cfg {
struct iwl_prph_scratch_version version;
......@@ -155,6 +170,7 @@ struct iwl_prph_scratch_ctrl_cfg {
struct iwl_prph_scratch_hwm_cfg hwm_cfg;
struct iwl_prph_scratch_rbd_cfg rbd_cfg;
struct iwl_prph_scratch_uefi_cfg reduce_power_cfg;
struct iwl_prph_scratch_step_cfg step_cfg;
} __packed; /* PERIPH_SCRATCH_CTRL_CFG_S */
/*
......@@ -165,7 +181,7 @@ struct iwl_prph_scratch_ctrl_cfg {
*/
struct iwl_prph_scratch {
struct iwl_prph_scratch_ctrl_cfg ctrl_cfg;
__le32 reserved[12];
__le32 reserved[10];
struct iwl_context_info_dram dram;
} __packed; /* PERIPH_SCRATCH_S */
......@@ -265,5 +281,6 @@ int iwl_trans_pcie_ctx_info_gen3_set_pnvm(struct iwl_trans *trans,
const void *data, u32 len);
int iwl_trans_pcie_ctx_info_gen3_set_reduce_power(struct iwl_trans *trans,
const void *data, u32 len);
int iwl_trans_pcie_ctx_info_gen3_set_step(struct iwl_trans *trans,
u32 mbx_addr_0_step, u32 mbx_addr_1_step);
#endif /* __iwl_context_info_file_gen3_h__ */
......@@ -163,7 +163,6 @@ static void iwl_req_fw_callback(const struct firmware *ucode_raw,
static int iwl_request_firmware(struct iwl_drv *drv, bool first)
{
const struct iwl_cfg *cfg = drv->trans->cfg;
char tag[8];
if (drv->trans->trans_cfg->device_family == IWL_DEVICE_FAMILY_9000 &&
(drv->trans->hw_rev_step != SILICON_B_STEP &&
......@@ -174,13 +173,10 @@ static int iwl_request_firmware(struct iwl_drv *drv, bool first)
return -EINVAL;
}
if (first) {
if (first)
drv->fw_index = cfg->ucode_api_max;
sprintf(tag, "%d", drv->fw_index);
} else {
else
drv->fw_index--;
sprintf(tag, "%d", drv->fw_index);
}
if (drv->fw_index < cfg->ucode_api_min) {
IWL_ERR(drv, "no suitable firmware found!\n");
......@@ -200,8 +196,8 @@ static int iwl_request_firmware(struct iwl_drv *drv, bool first)
return -ENOENT;
}
snprintf(drv->firmware_name, sizeof(drv->firmware_name), "%s%s.ucode",
cfg->fw_name_pre, tag);
snprintf(drv->firmware_name, sizeof(drv->firmware_name), "%s%d.ucode",
cfg->fw_name_pre, drv->fw_index);
IWL_DEBUG_FW_INFO(drv, "attempting to load firmware '%s'\n",
drv->firmware_name);
......
......@@ -1001,6 +1001,8 @@ struct iwl_trans_txqs {
* This mode is set dynamically, depending on the WoWLAN values
* configured from the userspace at runtime.
* @iwl_trans_txqs: transport tx queues data.
* @mbx_addr_0_step: step address data 0
* @mbx_addr_1_step: step address data 1
*/
struct iwl_trans {
bool csme_own;
......@@ -1057,6 +1059,8 @@ struct iwl_trans {
const char *name;
struct iwl_trans_txqs txqs;
u32 mbx_addr_0_step;
u32 mbx_addr_1_step;
/* pointer to trans specific struct */
/*Ensure that this pointer will always be aligned to sizeof pointer */
......
......@@ -788,7 +788,7 @@ static void iwl_mei_handle_amt_state(struct mei_cl_device *cldev,
if (mei->amt_enabled)
iwl_mei_set_init_conf(mei);
else if (iwl_mei_cache.ops)
iwl_mei_cache.ops->rfkill(iwl_mei_cache.priv, false, false);
iwl_mei_cache.ops->rfkill(iwl_mei_cache.priv, false);
schedule_work(&mei->netdev_work);
......@@ -829,7 +829,7 @@ static void iwl_mei_handle_csme_taking_ownership(struct mei_cl_device *cldev,
*/
mei->csme_taking_ownership = true;
iwl_mei_cache.ops->rfkill(iwl_mei_cache.priv, true, true);
iwl_mei_cache.ops->rfkill(iwl_mei_cache.priv, true);
} else {
iwl_mei_send_sap_msg(cldev,
SAP_MSG_NOTIF_CSME_OWNERSHIP_CONFIRMED);
......@@ -1774,7 +1774,7 @@ int iwl_mei_register(void *priv, const struct iwl_mei_ops *ops)
if (mei->amt_enabled)
iwl_mei_send_sap_msg(mei->cldev,
SAP_MSG_NOTIF_WIFIDR_UP);
ops->rfkill(priv, mei->link_prot_state, false);
ops->rfkill(priv, mei->link_prot_state);
}
}
ret = 0;
......
......@@ -324,12 +324,12 @@ static ssize_t iwl_dbgfs_sar_geo_profile_read(struct file *file,
pos += scnprintf(buf + pos, bufsz - pos,
"Use geographic profile %d\n", tbl_idx);
pos += scnprintf(buf + pos, bufsz - pos,
"2.4GHz:\n\tChain A offset: %hhu dBm\n\tChain B offset: %hhu dBm\n\tmax tx power: %hhu dBm\n",
"2.4GHz:\n\tChain A offset: %u dBm\n\tChain B offset: %u dBm\n\tmax tx power: %u dBm\n",
mvm->fwrt.geo_profiles[tbl_idx - 1].bands[0].chains[0],
mvm->fwrt.geo_profiles[tbl_idx - 1].bands[0].chains[1],
mvm->fwrt.geo_profiles[tbl_idx - 1].bands[0].max);
pos += scnprintf(buf + pos, bufsz - pos,
"5.2GHz:\n\tChain A offset: %hhu dBm\n\tChain B offset: %hhu dBm\n\tmax tx power: %hhu dBm\n",
"5.2GHz:\n\tChain A offset: %u dBm\n\tChain B offset: %u dBm\n\tmax tx power: %u dBm\n",
mvm->fwrt.geo_profiles[tbl_idx - 1].bands[1].chains[0],
mvm->fwrt.geo_profiles[tbl_idx - 1].bands[1].chains[1],
mvm->fwrt.geo_profiles[tbl_idx - 1].bands[1].max);
......@@ -1069,7 +1069,7 @@ iwl_dbgfs_scan_ant_rxchain_read(struct file *file,
pos += scnprintf(buf + pos, bufsz - pos, "A");
if (mvm->scan_rx_ant & ANT_B)
pos += scnprintf(buf + pos, bufsz - pos, "B");
pos += scnprintf(buf + pos, bufsz - pos, " (%hhx)\n", mvm->scan_rx_ant);
pos += scnprintf(buf + pos, bufsz - pos, " (%x)\n", mvm->scan_rx_ant);
return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
}
......
......@@ -1206,7 +1206,7 @@ void iwl_mvm_ftm_range_resp(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb)
}
IWL_DEBUG_INFO(mvm, "Range response received\n");
IWL_DEBUG_INFO(mvm, "request id: %lld, num of entries: %hhu\n",
IWL_DEBUG_INFO(mvm, "request id: %lld, num of entries: %u\n",
mvm->ftm_initiator.req->cookie, num_of_aps);
for (i = 0; i < num_of_aps && i < IWL_MVM_TOF_MAX_APS; i++) {
......@@ -1298,7 +1298,7 @@ void iwl_mvm_ftm_range_resp(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb)
if (fw_has_api(&mvm->fw->ucode_capa,
IWL_UCODE_TLV_API_FTM_RTT_ACCURACY))
IWL_DEBUG_INFO(mvm, "RTT confidence: %hhu\n",
IWL_DEBUG_INFO(mvm, "RTT confidence: %u\n",
fw_ap->rttConfidence);
iwl_mvm_debug_range_resp(mvm, i, &result);
......
......@@ -5116,6 +5116,9 @@ static void iwl_mvm_set_sta_rate(u32 rate_n_flags, struct rate_info *rinfo)
case RATE_MCS_CHAN_WIDTH_160:
rinfo->bw = RATE_INFO_BW_160;
break;
case RATE_MCS_CHAN_WIDTH_320:
rinfo->bw = RATE_INFO_BW_320;
break;
}
if (format == RATE_MCS_CCK_MSK ||
......@@ -5176,6 +5179,10 @@ static void iwl_mvm_set_sta_rate(u32 rate_n_flags, struct rate_info *rinfo)
rinfo->flags |= RATE_INFO_FLAGS_SHORT_GI;
switch (format) {
case RATE_MCS_EHT_MSK:
/* TODO: GI/LTF/RU. How does the firmware encode them? */
rinfo->flags |= RATE_INFO_FLAGS_EHT_MCS;
break;
case RATE_MCS_HE_MSK:
gi_ltf = u32_get_bits(rate_n_flags, RATE_MCS_HE_GI_LTF_MSK);
......
......@@ -1128,6 +1128,7 @@ iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg,
iwl_mvm_get_acpi_tables(mvm);
iwl_uefi_get_sgom_table(trans, &mvm->fwrt);
iwl_uefi_get_step_table(trans);
mvm->init_status = 0;
......
......@@ -10,37 +10,11 @@
#include "mvm.h"
#include "fw-api.h"
static void *iwl_mvm_skb_get_hdr(struct sk_buff *skb)
{
struct ieee80211_rx_status *rx_status = IEEE80211_SKB_RXCB(skb);
u8 *data = skb->data;
/* Alignment concerns */
BUILD_BUG_ON(sizeof(struct ieee80211_radiotap_he) % 4);
BUILD_BUG_ON(sizeof(struct ieee80211_radiotap_he_mu) % 4);
BUILD_BUG_ON(sizeof(struct ieee80211_radiotap_lsig) % 4);
BUILD_BUG_ON(sizeof(struct ieee80211_vendor_radiotap) % 4);
if (rx_status->flag & RX_FLAG_RADIOTAP_HE)
data += sizeof(struct ieee80211_radiotap_he);
if (rx_status->flag & RX_FLAG_RADIOTAP_HE_MU)
data += sizeof(struct ieee80211_radiotap_he_mu);
if (rx_status->flag & RX_FLAG_RADIOTAP_LSIG)
data += sizeof(struct ieee80211_radiotap_lsig);
if (rx_status->flag & RX_FLAG_RADIOTAP_VENDOR_DATA) {
struct ieee80211_vendor_radiotap *radiotap = (void *)data;
data += sizeof(*radiotap) + radiotap->len + radiotap->pad;
}
return data;
}
static inline int iwl_mvm_check_pn(struct iwl_mvm *mvm, struct sk_buff *skb,
int queue, struct ieee80211_sta *sta)
{
struct iwl_mvm_sta *mvmsta;
struct ieee80211_hdr *hdr = iwl_mvm_skb_get_hdr(skb);
struct ieee80211_hdr *hdr = (void *)skb_mac_header(skb);
struct ieee80211_rx_status *stats = IEEE80211_SKB_RXCB(skb);
struct iwl_mvm_key_pn *ptk_pn;
int res;
......@@ -179,6 +153,10 @@ static int iwl_mvm_create_skb(struct iwl_mvm *mvm, struct sk_buff *skb,
if (unlikely(headlen < hdrlen))
return -EINVAL;
/* Since data doesn't move data while putting data on skb and that is
* the only way we use, data + len is the next place that hdr would be put
*/
skb_set_mac_header(skb, skb->len);
skb_put_data(skb, hdr, hdrlen);
skb_put_data(skb, (u8 *)hdr + hdrlen + pad_len, headlen - hdrlen);
......@@ -936,7 +914,7 @@ static bool iwl_mvm_reorder(struct iwl_mvm *mvm,
struct iwl_rx_mpdu_desc *desc)
{
struct ieee80211_rx_status *rx_status = IEEE80211_SKB_RXCB(skb);
struct ieee80211_hdr *hdr = iwl_mvm_skb_get_hdr(skb);
struct ieee80211_hdr *hdr = (void *)skb_mac_header(skb);
struct iwl_mvm_sta *mvm_sta;
struct iwl_mvm_baid_data *baid_data;
struct iwl_mvm_reorder_buffer *buffer;
......@@ -1346,6 +1324,10 @@ static void iwl_mvm_decode_he_phy_data(struct iwl_mvm *mvm,
case IWL_RX_PHY_INFO_TYPE_HT:
case IWL_RX_PHY_INFO_TYPE_VHT_SU:
case IWL_RX_PHY_INFO_TYPE_VHT_MU:
case IWL_RX_PHY_INFO_TYPE_EHT_MU:
case IWL_RX_PHY_INFO_TYPE_EHT_TB:
case IWL_RX_PHY_INFO_TYPE_EHT_MU_EXT:
case IWL_RX_PHY_INFO_TYPE_EHT_TB_EXT:
return;
case IWL_RX_PHY_INFO_TYPE_HE_TB_EXT:
he->data1 |= cpu_to_le16(IEEE80211_RADIOTAP_HE_DATA1_SPTL_REUSE_KNOWN |
......@@ -1690,6 +1672,9 @@ static void iwl_mvm_rx_fill_status(struct iwl_mvm *mvm,
case RATE_MCS_CHAN_WIDTH_160:
rx_status->bw = RATE_INFO_BW_160;
break;
case RATE_MCS_CHAN_WIDTH_320:
rx_status->bw = RATE_INFO_BW_320;
break;
}
/* must be before L-SIG data */
......@@ -1726,6 +1711,9 @@ static void iwl_mvm_rx_fill_status(struct iwl_mvm *mvm,
rx_status->he_dcm =
!!(rate_n_flags & RATE_HE_DUAL_CARRIER_MODE_MSK);
break;
case RATE_MCS_EHT_MSK:
rx_status->encoding = RX_ENC_EHT;
break;
}
switch (format) {
......@@ -1736,6 +1724,7 @@ static void iwl_mvm_rx_fill_status(struct iwl_mvm *mvm,
break;
case RATE_MCS_VHT_MSK:
case RATE_MCS_HE_MSK:
case RATE_MCS_EHT_MSK:
rx_status->nss =
u32_get_bits(rate_n_flags, RATE_MCS_NSS_MSK) + 1;
rx_status->rate_idx = rate_n_flags & RATE_MCS_CODE_MSK;
......@@ -1747,10 +1736,11 @@ static void iwl_mvm_rx_fill_status(struct iwl_mvm *mvm,
rx_status->rate_idx = rate;
if ((rate < 0 || rate > 0xFF) && net_ratelimit()) {
IWL_ERR(mvm, "Invalid rate flags 0x%x, band %d,\n",
rate_n_flags, rx_status->band);
if ((rate < 0 || rate > 0xFF)) {
rx_status->rate_idx = 0;
if (net_ratelimit())
IWL_ERR(mvm, "Invalid rate flags 0x%x, band %d,\n",
rate_n_flags, rx_status->band);
}
break;
......@@ -2065,7 +2055,7 @@ void iwl_mvm_rx_monitor_no_data(struct iwl_mvm *mvm, struct napi_struct *napi,
{
struct ieee80211_rx_status *rx_status;
struct iwl_rx_packet *pkt = rxb_addr(rxb);
struct iwl_rx_no_data *desc = (void *)pkt->data;
struct iwl_rx_no_data_ver_3 *desc = (void *)pkt->data;
u32 rssi;
u32 info_type;
struct ieee80211_sta *sta = NULL;
......@@ -2101,6 +2091,18 @@ void iwl_mvm_rx_monitor_no_data(struct iwl_mvm *mvm, struct napi_struct *napi,
format = phy_data.rate_n_flags & RATE_MCS_MOD_TYPE_MSK;
if (iwl_fw_lookup_notif_ver(mvm->fw, DATA_PATH_GROUP,
RX_NO_DATA_NOTIF, 0) >= 3) {
if (unlikely(iwl_rx_packet_payload_len(pkt) <
sizeof(struct iwl_rx_no_data_ver_3)))
/* invalid len for ver 3 */
return;
} else {
if (format == RATE_MCS_EHT_MSK)
/* no support for EHT before version 3 API */
return;
}
/* Dont use dev_alloc_skb(), we'll have enough headroom once
* ieee80211_hdr pulled.
*/
......@@ -2136,6 +2138,16 @@ void iwl_mvm_rx_monitor_no_data(struct iwl_mvm *mvm, struct napi_struct *napi,
iwl_mvm_rx_fill_status(mvm, skb, &phy_data, queue);
/* no more radio tap info should be put after this point.
*
* We mark it as mac header, for upper layers to know where
* all radio tap header ends.
*
* Since data doesn't move data while putting data on skb and that is
* the only way we use, data + len is the next place that hdr would be put
*/
skb_set_mac_header(skb, skb->len);
/*
* Override the nss from the rx_vec since the rate_n_flags has
* only 2 bits for the nss which gives a max of 4 ss but there
......@@ -2152,6 +2164,10 @@ void iwl_mvm_rx_monitor_no_data(struct iwl_mvm *mvm, struct napi_struct *napi,
le32_get_bits(desc->rx_vec[0],
RX_NO_DATA_RX_VEC0_HE_NSTS_MSK) + 1;
break;
case RATE_MCS_EHT_MSK:
rx_status->nss =
le32_get_bits(desc->rx_vec[2],
RX_NO_DATA_RX_VEC2_EHT_NSTS_MSK) + 1;
}
rcu_read_lock();
......
......@@ -1107,8 +1107,8 @@ static int iwl_mvm_tx_mpdu(struct iwl_mvm *mvm, struct sk_buff *skb,
spin_lock(&mvmsta->lock);
/* nullfunc frames should go to the MGMT queue regardless of QOS,
* the condition of !ieee80211_is_qos_nullfunc(fc) keeps the default
* assignment of MGMT TID
* the conditions of !ieee80211_is_qos_nullfunc(fc) and
* !ieee80211_is_data_qos(fc) keep the default assignment of MGMT TID
*/
if (ieee80211_is_data_qos(fc) && !ieee80211_is_qos_nullfunc(fc)) {
tid = ieee80211_get_tid(hdr);
......@@ -1133,7 +1133,8 @@ static int iwl_mvm_tx_mpdu(struct iwl_mvm *mvm, struct sk_buff *skb,
/* update the tx_cmd hdr as it was already copied */
tx_cmd->hdr->seq_ctrl = hdr->seq_ctrl;
}
} else if (ieee80211_is_data(fc) && !ieee80211_is_data_qos(fc)) {
} else if (ieee80211_is_data(fc) && !ieee80211_is_data_qos(fc) &&
!ieee80211_is_nullfunc(fc)) {
tid = IWL_TID_NON_QOS;
}
......
......@@ -136,6 +136,10 @@ int iwl_pcie_ctxt_info_gen3_init(struct iwl_trans *trans,
&control_flags);
prph_sc_ctrl->control.control_flags = cpu_to_le32(control_flags);
/* initialize the Step equalizer data */
prph_sc_ctrl->step_cfg.mbx_addr_0 = cpu_to_le32(trans->mbx_addr_0_step);
prph_sc_ctrl->step_cfg.mbx_addr_1 = cpu_to_le32(trans->mbx_addr_1_step);
/* allocate ucode sections in dram and set addresses */
ret = iwl_pcie_init_fw_sec(trans, fw, &prph_scratch->dram);
if (ret)
......@@ -343,3 +347,4 @@ int iwl_trans_pcie_ctx_info_gen3_set_reduce_power(struct iwl_trans *trans,
return 0;
}
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment