Commit bc8d0a45 authored by Miri Korenblit's avatar Miri Korenblit Committed by Johannes Berg

wifi: iwlwifi: read PPAG table from UEFI

Try to read the PPAG table from UEFI first,
and if the WIFI UEFI tables are unlocked or the
table doesn't exist - try to read it from ACPI
Signed-off-by: default avatarMiri Korenblit <miriam.rachel.korenblit@intel.com>
Reviewed-by: default avatarGregory Greenman <gregory.greenman@intel.com>
Link: https://msgid.link/20240131091413.6516da09aec1.I0dcaf0b6d8857417ba1318467a28da5d0d7d7f27@changeidSigned-off-by: default avatarJohannes Berg <johannes.berg@intel.com>
parent 8408e83e
...@@ -968,7 +968,6 @@ int iwl_acpi_get_ppag_table(struct iwl_fw_runtime *fwrt) ...@@ -968,7 +968,6 @@ int iwl_acpi_get_ppag_table(struct iwl_fw_runtime *fwrt)
kfree(data); kfree(data);
return ret; return ret;
} }
IWL_EXPORT_SYMBOL(iwl_acpi_get_ppag_table);
void iwl_acpi_get_phy_filters(struct iwl_fw_runtime *fwrt, void iwl_acpi_get_phy_filters(struct iwl_fw_runtime *fwrt,
struct iwl_phy_specific_cfg *filters) struct iwl_phy_specific_cfg *filters)
......
...@@ -24,6 +24,7 @@ IWL_EXPORT_SYMBOL(iwl_bios_get_ ## __name ## _table) ...@@ -24,6 +24,7 @@ IWL_EXPORT_SYMBOL(iwl_bios_get_ ## __name ## _table)
IWL_BIOS_TABLE_LOADER(wrds); IWL_BIOS_TABLE_LOADER(wrds);
IWL_BIOS_TABLE_LOADER(ewrd); IWL_BIOS_TABLE_LOADER(ewrd);
IWL_BIOS_TABLE_LOADER(wgds); IWL_BIOS_TABLE_LOADER(wgds);
IWL_BIOS_TABLE_LOADER(ppag);
static const struct dmi_system_id dmi_ppag_approved_list[] = { static const struct dmi_system_id dmi_ppag_approved_list[] = {
{ .ident = "HP", { .ident = "HP",
......
...@@ -113,4 +113,5 @@ int iwl_bios_get_ewrd_table(struct iwl_fw_runtime *fwrt); ...@@ -113,4 +113,5 @@ int iwl_bios_get_ewrd_table(struct iwl_fw_runtime *fwrt);
int iwl_bios_get_wgds_table(struct iwl_fw_runtime *fwrt); int iwl_bios_get_wgds_table(struct iwl_fw_runtime *fwrt);
int iwl_bios_get_ppag_table(struct iwl_fw_runtime *fwrt);
#endif /* __fw_regulatory_h__ */ #endif /* __fw_regulatory_h__ */
...@@ -172,10 +172,10 @@ struct iwl_fw_runtime { ...@@ -172,10 +172,10 @@ struct iwl_fw_runtime {
u32 geo_rev; u32 geo_rev;
u32 geo_num_profiles; u32 geo_num_profiles;
bool geo_enabled; bool geo_enabled;
#ifdef CONFIG_ACPI
struct iwl_ppag_chain ppag_chains[IWL_NUM_CHAIN_LIMITS]; struct iwl_ppag_chain ppag_chains[IWL_NUM_CHAIN_LIMITS];
u32 ppag_flags; u32 ppag_flags;
u32 ppag_ver; u32 ppag_ver;
#ifdef CONFIG_ACPI
struct iwl_sar_offset_mapping_cmd sgom_table; struct iwl_sar_offset_mapping_cmd sgom_table;
bool sgom_enabled; bool sgom_enabled;
struct iwl_uats_table_cmd uats_table; struct iwl_uats_table_cmd uats_table;
......
...@@ -521,3 +521,32 @@ int iwl_uefi_get_wgds_table(struct iwl_fw_runtime *fwrt) ...@@ -521,3 +521,32 @@ int iwl_uefi_get_wgds_table(struct iwl_fw_runtime *fwrt)
kfree(data); kfree(data);
return ret; return ret;
} }
int iwl_uefi_get_ppag_table(struct iwl_fw_runtime *fwrt)
{
struct uefi_cnv_var_ppag *data;
int ret = 0;
data = iwl_uefi_get_verified_variable(fwrt->trans, IWL_UEFI_PPAG_NAME,
"PPAG", sizeof(*data), NULL);
if (IS_ERR(data))
return -EINVAL;
if (data->revision < IWL_UEFI_MIN_PPAG_REV ||
data->revision > IWL_UEFI_MAX_PPAG_REV) {
ret = -EINVAL;
IWL_DEBUG_RADIO(fwrt, "Unsupported UEFI PPAG revision:%d\n",
data->revision);
goto out;
}
fwrt->ppag_ver = data->revision;
fwrt->ppag_flags = data->ppag_modes & IWL_PPAG_ETSI_CHINA_MASK;
BUILD_BUG_ON(sizeof(fwrt->ppag_chains) != sizeof(data->ppag_chains));
memcpy(&fwrt->ppag_chains, &data->ppag_chains,
sizeof(data->ppag_chains));
out:
kfree(data);
return ret;
}
...@@ -15,6 +15,7 @@ ...@@ -15,6 +15,7 @@
#define IWL_UEFI_WRDS_NAME L"UefiCnvWlanWRDS" #define IWL_UEFI_WRDS_NAME L"UefiCnvWlanWRDS"
#define IWL_UEFI_EWRD_NAME L"UefiCnvWlanEWRD" #define IWL_UEFI_EWRD_NAME L"UefiCnvWlanEWRD"
#define IWL_UEFI_WGDS_NAME L"UefiCnvWlanWGDS" #define IWL_UEFI_WGDS_NAME L"UefiCnvWlanWGDS"
#define IWL_UEFI_PPAG_NAME L"UefiCnvWlanPPAG"
#define IWL_SGOM_MAP_SIZE 339 #define IWL_SGOM_MAP_SIZE 339
#define IWL_UATS_MAP_SIZE 339 #define IWL_UATS_MAP_SIZE 339
...@@ -22,6 +23,8 @@ ...@@ -22,6 +23,8 @@
#define IWL_UEFI_WRDS_REVISION 2 #define IWL_UEFI_WRDS_REVISION 2
#define IWL_UEFI_EWRD_REVISION 2 #define IWL_UEFI_EWRD_REVISION 2
#define IWL_UEFI_WGDS_REVISION 3 #define IWL_UEFI_WGDS_REVISION 3
#define IWL_UEFI_MIN_PPAG_REV 1
#define IWL_UEFI_MAX_PPAG_REV 3
struct pnvm_sku_package { struct pnvm_sku_package {
u8 rev; u8 rev;
...@@ -99,6 +102,19 @@ struct uefi_cnv_var_wgds { ...@@ -99,6 +102,19 @@ struct uefi_cnv_var_wgds {
struct iwl_geo_profile geo_profiles[BIOS_GEO_MAX_PROFILE_NUM]; struct iwl_geo_profile geo_profiles[BIOS_GEO_MAX_PROFILE_NUM];
} __packed; } __packed;
/*
* struct uefi_cnv_var_ppag - PPAG table as defined in UEFI
* @revision: the revision of the table
* @ppag_modes: bit 0 - PPAG is enabled/disabled in ETSI,
* bit 1 - PPAG is enabled/disabled in China
* @ppag_chains: the PPAG values per chain and band
*/
struct uefi_cnv_var_ppag {
u8 revision;
u32 ppag_modes;
struct iwl_ppag_chain ppag_chains[IWL_NUM_CHAIN_LIMITS];
} __packed;
/* /*
* This is known to be broken on v4.19 and to work on v5.4. Until we * 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 * figure out why this is the case and how to make it work, simply
...@@ -116,6 +132,7 @@ int iwl_uefi_handle_tlv_mem_desc(struct iwl_trans *trans, const u8 *data, ...@@ -116,6 +132,7 @@ int iwl_uefi_handle_tlv_mem_desc(struct iwl_trans *trans, const u8 *data,
int iwl_uefi_get_wrds_table(struct iwl_fw_runtime *fwrt); int iwl_uefi_get_wrds_table(struct iwl_fw_runtime *fwrt);
int iwl_uefi_get_ewrd_table(struct iwl_fw_runtime *fwrt); int iwl_uefi_get_ewrd_table(struct iwl_fw_runtime *fwrt);
int iwl_uefi_get_wgds_table(struct iwl_fw_runtime *fwrt); int iwl_uefi_get_wgds_table(struct iwl_fw_runtime *fwrt);
int iwl_uefi_get_ppag_table(struct iwl_fw_runtime *fwrt);
#else /* CONFIG_EFI */ #else /* CONFIG_EFI */
static inline void *iwl_uefi_get_pnvm(struct iwl_trans *trans, size_t *len) static inline void *iwl_uefi_get_pnvm(struct iwl_trans *trans, size_t *len)
{ {
...@@ -161,6 +178,11 @@ static inline int iwl_uefi_get_wgds_table(struct iwl_fw_runtime *fwrt) ...@@ -161,6 +178,11 @@ static inline int iwl_uefi_get_wgds_table(struct iwl_fw_runtime *fwrt)
{ {
return -ENOENT; return -ENOENT;
} }
static inline int iwl_uefi_get_ppag_table(struct iwl_fw_runtime *fwrt)
{
return -ENOENT;
}
#endif /* CONFIG_EFI */ #endif /* CONFIG_EFI */
#if defined(CONFIG_EFI) && defined(CONFIG_ACPI) #if defined(CONFIG_EFI) && defined(CONFIG_ACPI)
......
...@@ -1078,8 +1078,6 @@ static int iwl_mvm_sar_geo_init(struct iwl_mvm *mvm) ...@@ -1078,8 +1078,6 @@ static int iwl_mvm_sar_geo_init(struct iwl_mvm *mvm)
return iwl_mvm_send_cmd_pdu(mvm, cmd_id, 0, len, &cmd); return iwl_mvm_send_cmd_pdu(mvm, cmd_id, 0, len, &cmd);
} }
#ifdef CONFIG_ACPI
int iwl_mvm_ppag_send_cmd(struct iwl_mvm *mvm) int iwl_mvm_ppag_send_cmd(struct iwl_mvm *mvm)
{ {
union iwl_ppag_table_cmd cmd; union iwl_ppag_table_cmd cmd;
...@@ -1110,6 +1108,8 @@ static int iwl_mvm_ppag_init(struct iwl_mvm *mvm) ...@@ -1110,6 +1108,8 @@ static int iwl_mvm_ppag_init(struct iwl_mvm *mvm)
return iwl_mvm_ppag_send_cmd(mvm); return iwl_mvm_ppag_send_cmd(mvm);
} }
#ifdef CONFIG_ACPI
static const struct dmi_system_id dmi_tas_approved_list[] = { static const struct dmi_system_id dmi_tas_approved_list[] = {
{ .ident = "HP", { .ident = "HP",
.matches = { .matches = {
...@@ -1389,16 +1389,6 @@ static void iwl_mvm_lari_cfg(struct iwl_mvm *mvm) ...@@ -1389,16 +1389,6 @@ static void iwl_mvm_lari_cfg(struct iwl_mvm *mvm)
#else /* CONFIG_ACPI */ #else /* CONFIG_ACPI */
int iwl_mvm_ppag_send_cmd(struct iwl_mvm *mvm)
{
return -ENOENT;
}
static int iwl_mvm_ppag_init(struct iwl_mvm *mvm)
{
return 0;
}
static void iwl_mvm_tas_init(struct iwl_mvm *mvm) static void iwl_mvm_tas_init(struct iwl_mvm *mvm)
{ {
} }
...@@ -1426,7 +1416,7 @@ void iwl_mvm_get_bios_tables(struct iwl_mvm *mvm) ...@@ -1426,7 +1416,7 @@ void iwl_mvm_get_bios_tables(struct iwl_mvm *mvm)
iwl_acpi_get_guid_lock_status(&mvm->fwrt); iwl_acpi_get_guid_lock_status(&mvm->fwrt);
/* read PPAG table */ /* read PPAG table */
ret = iwl_acpi_get_ppag_table(&mvm->fwrt); ret = iwl_bios_get_ppag_table(&mvm->fwrt);
if (ret < 0) { if (ret < 0) {
IWL_DEBUG_RADIO(mvm, IWL_DEBUG_RADIO(mvm,
"PPAG BIOS table invalid or unavailable. (%d)\n", "PPAG BIOS table invalid or unavailable. (%d)\n",
......
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