| Author | Tokens | Token Proportion | Commits | Commit Proportion |
|---|---|---|---|---|
| Miri Korenblit | 663 | 36.63% | 15 | 23.08% |
| Matt Chen | 369 | 20.39% | 2 | 3.08% |
| Anjaneyulu | 243 | 13.43% | 7 | 10.77% |
| Emmanuel Grumbach | 143 | 7.90% | 4 | 6.15% |
| Johannes Berg | 76 | 4.20% | 6 | 9.23% |
| Luciano Coelho | 70 | 3.87% | 13 | 20.00% |
| Ariel Malamud | 56 | 3.09% | 1 | 1.54% |
| Somashekhar(Som) | 45 | 2.49% | 2 | 3.08% |
| Alon Giladi | 32 | 1.77% | 2 | 3.08% |
| Ron Rindjunsky | 24 | 1.33% | 1 | 1.54% |
| Gregory Greenman | 22 | 1.22% | 1 | 1.54% |
| Ihab Zhaika | 18 | 0.99% | 1 | 1.54% |
| Golan Ben-Ami | 17 | 0.94% | 2 | 3.08% |
| Nidhish A N | 9 | 0.50% | 1 | 1.54% |
| Haim Dreyfuss | 9 | 0.50% | 2 | 3.08% |
| Gil Adam | 9 | 0.50% | 2 | 3.08% |
| Ayala Barazani | 3 | 0.17% | 1 | 1.54% |
| striebit | 1 | 0.06% | 1 | 1.54% |
| Wei Yongjun | 1 | 0.06% | 1 | 1.54% |
| Total | 1810 | 65 |
// SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause /* * Copyright (C) 2023, 2025 Intel Corporation */ #include <linux/dmi.h> #include "iwl-drv.h" #include "iwl-debug.h" #include "regulatory.h" #include "fw/runtime.h" #include "fw/uefi.h" #define GET_BIOS_TABLE(__name, ...) \ do { \ int ret = -ENOENT; \ if (fwrt->uefi_tables_lock_status > UEFI_WIFI_GUID_UNLOCKED) \ ret = iwl_uefi_get_ ## __name(__VA_ARGS__); \ if (ret < 0) \ ret = iwl_acpi_get_ ## __name(__VA_ARGS__); \ return ret; \ } while (0) #define IWL_BIOS_TABLE_LOADER(__name) \ int iwl_bios_get_ ## __name(struct iwl_fw_runtime *fwrt) \ {GET_BIOS_TABLE(__name, fwrt); } \ IWL_EXPORT_SYMBOL(iwl_bios_get_ ## __name) #define IWL_BIOS_TABLE_LOADER_DATA(__name, data_type) \ int iwl_bios_get_ ## __name(struct iwl_fw_runtime *fwrt, \ data_type * data) \ {GET_BIOS_TABLE(__name, fwrt, data); } \ IWL_EXPORT_SYMBOL(iwl_bios_get_ ## __name) IWL_BIOS_TABLE_LOADER(wrds_table); IWL_BIOS_TABLE_LOADER(ewrd_table); IWL_BIOS_TABLE_LOADER(wgds_table); IWL_BIOS_TABLE_LOADER(ppag_table); IWL_BIOS_TABLE_LOADER(phy_filters); IWL_BIOS_TABLE_LOADER_DATA(tas_table, struct iwl_tas_data); IWL_BIOS_TABLE_LOADER_DATA(pwr_limit, u64); IWL_BIOS_TABLE_LOADER_DATA(mcc, char); IWL_BIOS_TABLE_LOADER_DATA(eckv, u32); IWL_BIOS_TABLE_LOADER_DATA(wbem, u32); IWL_BIOS_TABLE_LOADER_DATA(dsbr, u32); static const struct dmi_system_id dmi_ppag_approved_list[] = { { .ident = "HP", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "HP"), }, }, { .ident = "SAMSUNG", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "SAMSUNG ELECTRONICS CO., LTD"), }, }, { .ident = "MSFT", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"), }, }, { .ident = "ASUSTEK", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "ASUSTeK COMPUTER INC."), }, }, { .ident = "ASUS", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "ASUS"), }, }, { .ident = "GOOGLE-HP", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Google"), DMI_MATCH(DMI_BOARD_VENDOR, "HP"), }, }, { .ident = "GOOGLE-ASUS", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Google"), DMI_MATCH(DMI_BOARD_VENDOR, "ASUSTek COMPUTER INC."), }, }, { .ident = "GOOGLE-SAMSUNG", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Google"), DMI_MATCH(DMI_BOARD_VENDOR, "SAMSUNG ELECTRONICS CO., LTD"), }, }, { .ident = "DELL", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Dell Inc."), }, }, { .ident = "DELL", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Alienware"), }, }, { .ident = "RAZER", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Razer"), }, }, { .ident = "Honor", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "HONOR"), }, }, { .ident = "WIKO", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "WIKO"), }, }, {} }; static const struct dmi_system_id dmi_tas_approved_list[] = { { .ident = "HP", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "HP"), }, }, { .ident = "SAMSUNG", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "SAMSUNG ELECTRONICS CO., LTD"), }, }, { .ident = "LENOVO", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "LENOVO"), }, }, { .ident = "DELL", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Dell Inc."), }, }, { .ident = "MSFT", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"), }, }, { .ident = "Acer", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Acer"), }, }, { .ident = "ASUSTEK", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "ASUSTeK COMPUTER INC."), }, }, { .ident = "ASUS", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "ASUS"), }, }, { .ident = "GOOGLE-HP", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Google"), DMI_MATCH(DMI_BOARD_VENDOR, "HP"), }, }, { .ident = "MSI", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Micro-Star International Co., Ltd."), }, }, { .ident = "Honor", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "HONOR"), }, }, /* keep last */ {} }; bool iwl_sar_geo_support(struct iwl_fw_runtime *fwrt) { /* * The PER_CHAIN_LIMIT_OFFSET_CMD command is not supported on * earlier firmware versions. Unfortunately, we don't have a * TLV API flag to rely on, so rely on the major version which * is in the first byte of ucode_ver. This was implemented * initially on version 38 and then backported to 17. It was * also backported to 29, but only for 7265D devices. The * intention was to have it in 36 as well, but not all 8000 * family got this feature enabled. The 8000 family is the * only one using version 36, so skip this version entirely. */ return IWL_UCODE_SERIAL(fwrt->fw->ucode_ver) >= 38 || (IWL_UCODE_SERIAL(fwrt->fw->ucode_ver) == 17 && fwrt->trans->info.hw_rev != CSR_HW_REV_TYPE_3160) || (IWL_UCODE_SERIAL(fwrt->fw->ucode_ver) == 29 && ((fwrt->trans->info.hw_rev & CSR_HW_REV_TYPE_MSK) == CSR_HW_REV_TYPE_7265D)); } IWL_EXPORT_SYMBOL(iwl_sar_geo_support); int iwl_sar_geo_fill_table(struct iwl_fw_runtime *fwrt, struct iwl_per_chain_offset *table, u32 n_bands, u32 n_profiles) { int i, j; if (!fwrt->geo_enabled) return -ENODATA; if (!iwl_sar_geo_support(fwrt)) return -EOPNOTSUPP; for (i = 0; i < n_profiles; i++) { for (j = 0; j < n_bands; j++) { struct iwl_per_chain_offset *chain = &table[i * n_bands + j]; chain->max_tx_power = cpu_to_le16(fwrt->geo_profiles[i].bands[j].max); chain->chain_a = fwrt->geo_profiles[i].bands[j].chains[0]; chain->chain_b = fwrt->geo_profiles[i].bands[j].chains[1]; IWL_DEBUG_RADIO(fwrt, "SAR geographic profile[%d] Band[%d]: chain A = %d chain B = %d max_tx_power = %d\n", i, j, fwrt->geo_profiles[i].bands[j].chains[0], fwrt->geo_profiles[i].bands[j].chains[1], fwrt->geo_profiles[i].bands[j].max); } } return 0; } IWL_EXPORT_SYMBOL(iwl_sar_geo_fill_table); static int iwl_sar_fill_table(struct iwl_fw_runtime *fwrt, __le16 *per_chain, u32 n_subbands, int prof_a, int prof_b) { int profs[BIOS_SAR_NUM_CHAINS] = { prof_a, prof_b }; int i, j; if (WARN_ON_ONCE(n_subbands > ARRAY_SIZE(fwrt->sar_profiles[0].chains[0].subbands))) return -EINVAL; for (i = 0; i < BIOS_SAR_NUM_CHAINS; i++) { struct iwl_sar_profile *prof; /* don't allow SAR to be disabled (profile 0 means disable) */ if (profs[i] == 0) return -EPERM; /* we are off by one, so allow up to BIOS_SAR_MAX_PROFILE_NUM */ if (profs[i] > BIOS_SAR_MAX_PROFILE_NUM) return -EINVAL; /* profiles go from 1 to 4, so decrement to access the array */ prof = &fwrt->sar_profiles[profs[i] - 1]; /* if the profile is disabled, do nothing */ if (!prof->enabled) { IWL_DEBUG_RADIO(fwrt, "SAR profile %d is disabled.\n", profs[i]); /* * if one of the profiles is disabled, we * ignore all of them and return 1 to * differentiate disabled from other failures. */ return 1; } IWL_DEBUG_INFO(fwrt, "SAR EWRD: chain %d profile index %d\n", i, profs[i]); IWL_DEBUG_RADIO(fwrt, " Chain[%d]:\n", i); for (j = 0; j < n_subbands; j++) { per_chain[i * n_subbands + j] = cpu_to_le16(prof->chains[i].subbands[j]); IWL_DEBUG_RADIO(fwrt, " Band[%d] = %d * .125dBm\n", j, prof->chains[i].subbands[j]); } } return 0; } int iwl_sar_fill_profile(struct iwl_fw_runtime *fwrt, __le16 *per_chain, u32 n_tables, u32 n_subbands, int prof_a, int prof_b) { int i, ret = 0; for (i = 0; i < n_tables; i++) { ret = iwl_sar_fill_table(fwrt, &per_chain[i * n_subbands * BIOS_SAR_NUM_CHAINS], n_subbands, prof_a, prof_b); if (ret) break; } return ret; } IWL_EXPORT_SYMBOL(iwl_sar_fill_profile); bool iwl_is_ppag_approved(struct iwl_fw_runtime *fwrt) { if (!dmi_check_system(dmi_ppag_approved_list)) { IWL_DEBUG_RADIO(fwrt, "System vendor '%s' is not in the approved list, disabling PPAG.\n", dmi_get_system_info(DMI_SYS_VENDOR) ?: "<unknown>"); fwrt->ppag_flags = 0; return false; } return true; } IWL_EXPORT_SYMBOL(iwl_is_ppag_approved); /* Print the PPAG table as read from BIOS */ void iwl_bios_print_ppag(struct iwl_fw_runtime *fwrt, int n_subbands) { int i, j; IWL_DEBUG_RADIO(fwrt, "PPAG table as read from BIOS:\n"); IWL_DEBUG_RADIO(fwrt, "PPAG revision = %d\n", fwrt->ppag_bios_rev); IWL_DEBUG_RADIO(fwrt, "PPAG flags = 0x%x\n", fwrt->ppag_flags); if (WARN_ON_ONCE(n_subbands > ARRAY_SIZE(fwrt->ppag_chains[0].subbands))) return; for (i = 0; i < ARRAY_SIZE(fwrt->ppag_chains); i++) for (j = 0; j < n_subbands; j++) IWL_DEBUG_RADIO(fwrt, "ppag_chains[%d].subbands[%d] = %d\n", i, j, fwrt->ppag_chains[i].subbands[j]); } bool iwl_is_tas_approved(void) { return dmi_check_system(dmi_tas_approved_list); } IWL_EXPORT_SYMBOL(iwl_is_tas_approved); struct iwl_tas_selection_data iwl_parse_tas_selection(const u32 tas_selection_in, const u8 tbl_rev) { struct iwl_tas_selection_data tas_selection_out = {}; u8 override_iec = u32_get_bits(tas_selection_in, IWL_WTAS_OVERRIDE_IEC_MSK); u8 canada_tas_uhb = u32_get_bits(tas_selection_in, IWL_WTAS_CANADA_UHB_MSK); u8 enabled_iec = u32_get_bits(tas_selection_in, IWL_WTAS_ENABLE_IEC_MSK); u8 usa_tas_uhb = u32_get_bits(tas_selection_in, IWL_WTAS_USA_UHB_MSK); if (tbl_rev > 0) { tas_selection_out.usa_tas_uhb_allowed = usa_tas_uhb; tas_selection_out.override_tas_iec = override_iec; tas_selection_out.enable_tas_iec = enabled_iec; } if (tbl_rev > 1) tas_selection_out.canada_tas_uhb_allowed = canada_tas_uhb; return tas_selection_out; } IWL_EXPORT_SYMBOL(iwl_parse_tas_selection); bool iwl_add_mcc_to_tas_block_list(u16 *list, u8 *size, u16 mcc) { for (int i = 0; i < *size; i++) { if (list[i] == mcc) return true; } /* Verify that there is room for another country * If *size == IWL_WTAS_BLACK_LIST_MAX, then the table is full. */ if (*size >= IWL_WTAS_BLACK_LIST_MAX) return false; list[*size++] = mcc; return true; } IWL_EXPORT_SYMBOL(iwl_add_mcc_to_tas_block_list); int iwl_bios_get_dsm(struct iwl_fw_runtime *fwrt, enum iwl_dsm_funcs func, u32 *value) { GET_BIOS_TABLE(dsm, fwrt, func, value); } IWL_EXPORT_SYMBOL(iwl_bios_get_dsm); bool iwl_puncturing_is_allowed_in_bios(u32 puncturing, u16 mcc) { /* Some kind of regulatory mess means we need to currently disallow * puncturing in the US and Canada unless enabled in BIOS. */ switch (mcc) { case IWL_MCC_US: return puncturing & IWL_UEFI_CNV_PUNCTURING_USA_EN_MSK; case IWL_MCC_CANADA: return puncturing & IWL_UEFI_CNV_PUNCTURING_CANADA_EN_MSK; default: return true; } } IWL_EXPORT_SYMBOL(iwl_puncturing_is_allowed_in_bios); bool iwl_rfi_is_enabled_in_bios(struct iwl_fw_runtime *fwrt) { /* default behaviour is disabled */ u32 value = 0; int ret = iwl_bios_get_dsm(fwrt, DSM_FUNC_RFI_CONFIG, &value); if (ret < 0) { IWL_DEBUG_RADIO(fwrt, "Failed to get DSM RFI, ret=%d\n", ret); return false; } value &= DSM_VALUE_RFI_DISABLE; /* RFI BIOS CONFIG value can be 0 or 3 only. * i.e 0 means DDR and DLVR enabled. 3 means DDR and DLVR disabled. * 1 and 2 are invalid BIOS configurations, So, it's not possible to * disable ddr/dlvr separately. */ if (!value) { IWL_DEBUG_RADIO(fwrt, "DSM RFI is evaluated to enable\n"); return true; } else if (value == DSM_VALUE_RFI_DISABLE) { IWL_DEBUG_RADIO(fwrt, "DSM RFI is evaluated to disable\n"); } else { IWL_DEBUG_RADIO(fwrt, "DSM RFI got invalid value, value=%d\n", value); } return false; } IWL_EXPORT_SYMBOL(iwl_rfi_is_enabled_in_bios);
Information contained on this website is for historical information purposes only and does not indicate or represent copyright ownership.
Created with Cregit http://github.com/cregit/cregit
Version 2.0-RC1