Commit 83bdad52 authored by Alexander Bondar's avatar Alexander Bondar Committed by Johannes Berg

iwlwifi: mvm: downgrade to old power management API

Current available FW still doesn't support new PM API.
Therefore, to enable basic power management with the
existing firmware, change the API in the driver back
to the API used in the current firmware.
Signed-off-by: default avatarAlexander Bondar <alexander.bondar@intel.com>
Reviewed-by: default avatarEmmanuel Grumbach <emmanuel.grumbach@intel.com>
Signed-off-by: default avatarJohannes Berg <johannes.berg@intel.com>
parent 9166b1ee
...@@ -68,33 +68,29 @@ ...@@ -68,33 +68,29 @@
/** /**
* enum iwl_scan_flags - masks for power table command flags * enum iwl_scan_flags - masks for power table command flags
* @POWER_FLAGS_POWER_SAVE_ENA_MSK: '1' Allow to save power by turning off
* receiver and transmitter. '0' - does not allow.
* @POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK: '0' Driver disables power management, * @POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK: '0' Driver disables power management,
* '1' Driver enables PM (use rest of parameters) * '1' Driver enables PM (use rest of parameters)
* @POWER_FLAGS_SLEEP_OVER_DTIM_MSK: '0' PM have to walk up every DTIM, * @POWER_FLAGS_SLEEP_OVER_DTIM_MSK: '0' PM have to walk up every DTIM,
* '1' PM could sleep over DTIM till listen Interval. * '1' PM could sleep over DTIM till listen Interval.
* @POWER_FLAGS_LPRX_ENA_MSK: Low Power RX enable.
* @POWER_FLAGS_SNOOZE_ENA_MSK: Enable snoozing only if uAPSD is enabled and all
* access categories are both delivery and trigger enabled.
* @POWER_FLAGS_BT_SCO_ENA: Enable BT SCO coex only if uAPSD and
* PBW Snoozing enabled
* @POWER_FLAGS_ADVANCE_PM_ENA_MSK: Advanced PM (uAPSD) enable mask * @POWER_FLAGS_ADVANCE_PM_ENA_MSK: Advanced PM (uAPSD) enable mask
* @POWER_FLAGS_LPRX_ENA_MSK: Low Power RX enable.
*/ */
enum iwl_power_flags { enum iwl_power_flags {
POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK = BIT(0), POWER_FLAGS_POWER_SAVE_ENA_MSK = BIT(0),
POWER_FLAGS_SLEEP_OVER_DTIM_MSK = BIT(1), POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK = BIT(1),
POWER_FLAGS_LPRX_ENA_MSK = BIT(2), POWER_FLAGS_SLEEP_OVER_DTIM_MSK = BIT(2),
POWER_FLAGS_SNOOZE_ENA_MSK = BIT(3), POWER_FLAGS_ADVANCE_PM_ENA_MSK = BIT(9),
POWER_FLAGS_BT_SCO_ENA = BIT(4), POWER_FLAGS_LPRX_ENA_MSK = BIT(11),
POWER_FLAGS_ADVANCE_PM_ENA_MSK = BIT(5)
}; };
#define IWL_POWER_VEC_SIZE 5
/** /**
* struct iwl_powertable_cmd - Power Table Command * struct iwl_powertable_cmd - Power Table Command
* POWER_TABLE_CMD = 0x77 (command, has simple generic response) * POWER_TABLE_CMD = 0x77 (command, has simple generic response)
* *
* @id_and_color: MAC contex identifier
* @action: Action on context - no action, add new,
* modify existent, remove
* @flags: Power table command flags from POWER_FLAGS_* * @flags: Power table command flags from POWER_FLAGS_*
* @keep_alive_seconds: Keep alive period in seconds. Default - 25 sec. * @keep_alive_seconds: Keep alive period in seconds. Default - 25 sec.
* Minimum allowed:- 3 * DTIM * Minimum allowed:- 3 * DTIM
...@@ -102,39 +98,21 @@ enum iwl_power_flags { ...@@ -102,39 +98,21 @@ enum iwl_power_flags {
* PSM transition - legacy PM * PSM transition - legacy PM
* @tx_data_timeout: Minimum time (usec) from last Tx packet for AM to * @tx_data_timeout: Minimum time (usec) from last Tx packet for AM to
* PSM transition - legacy PM * PSM transition - legacy PM
* @rx_data_timeout_uapsd: Minimum time (usec) from last Rx packet for AM to * @sleep_interval: not in use
* PSM transition - uAPSD * @keep_alive_beacons: not in use
* @tx_data_timeout_uapsd: Minimum time (usec) from last Tx packet for AM to
* PSM transition - uAPSD
* @lprx_rssi_threshold: Signal strength up to which LP RX can be enabled. * @lprx_rssi_threshold: Signal strength up to which LP RX can be enabled.
* Default: 80dbm * Default: 80dbm
* @num_skip_dtim: Number of DTIMs to skip if Skip over DTIM flag is set
* @snooze_interval: TBD
* @snooze_window: TBD
* @snooze_step: TBD
* @qndp_tid: TBD
* @uapsd_ac_flags: TBD
* @uapsd_max_sp: TBD
*/ */
struct iwl_powertable_cmd { struct iwl_powertable_cmd {
/* COMMON_INDEX_HDR_API_S_VER_1 */ /* PM_POWER_TABLE_CMD_API_S_VER_5 */
__le32 id_and_color;
__le32 action;
__le16 flags; __le16 flags;
u8 reserved; u8 keep_alive_seconds;
__le16 keep_alive_seconds; u8 debug_flags;
__le32 rx_data_timeout; __le32 rx_data_timeout;
__le32 tx_data_timeout; __le32 tx_data_timeout;
__le32 rx_data_timeout_uapsd; __le32 sleep_interval[IWL_POWER_VEC_SIZE];
__le32 tx_data_timeout_uapsd; __le32 keep_alive_beacons;
u8 lprx_rssi_threshold; __le32 lprx_rssi_threshold;
u8 num_skip_dtim;
__le16 snooze_interval;
__le16 snooze_window;
u8 snooze_step;
u8 qndp_tid;
u8 uapsd_ac_flags;
u8 uapsd_max_sp;
} __packed; } __packed;
#endif #endif
...@@ -79,22 +79,18 @@ static void iwl_power_build_cmd(struct iwl_mvm *mvm, struct ieee80211_vif *vif, ...@@ -79,22 +79,18 @@ static void iwl_power_build_cmd(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
struct iwl_powertable_cmd *cmd) struct iwl_powertable_cmd *cmd)
{ {
struct ieee80211_hw *hw = mvm->hw; struct ieee80211_hw *hw = mvm->hw;
struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
struct ieee80211_chanctx_conf *chanctx_conf; struct ieee80211_chanctx_conf *chanctx_conf;
struct ieee80211_channel *chan; struct ieee80211_channel *chan;
int dtimper, dtimper_msec; int dtimper, dtimper_msec;
int keep_alive; int keep_alive;
bool radar_detect = false; bool radar_detect = false;
cmd->id_and_color = cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->id,
mvmvif->color));
cmd->action = cpu_to_le32(FW_CTXT_ACTION_MODIFY);
if ((!vif->bss_conf.ps) || if ((!vif->bss_conf.ps) ||
(iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM)) (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM))
return; return;
cmd->flags |= cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK); cmd->flags |= cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK |
POWER_FLAGS_POWER_SAVE_ENA_MSK);
dtimper = hw->conf.ps_dtim_period ?: 1; dtimper = hw->conf.ps_dtim_period ?: 1;
...@@ -110,10 +106,8 @@ static void iwl_power_build_cmd(struct iwl_mvm *mvm, struct ieee80211_vif *vif, ...@@ -110,10 +106,8 @@ static void iwl_power_build_cmd(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
/* Check skip over DTIM conditions */ /* Check skip over DTIM conditions */
if (!radar_detect && (dtimper <= 10) && if (!radar_detect && (dtimper <= 10) &&
(iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_LP)) { (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_LP))
cmd->flags |= cpu_to_le16(POWER_FLAGS_SLEEP_OVER_DTIM_MSK); cmd->flags |= cpu_to_le16(POWER_FLAGS_SLEEP_OVER_DTIM_MSK);
cmd->num_skip_dtim = 2;
}
/* Check that keep alive period is at least 3 * DTIM */ /* Check that keep alive period is at least 3 * DTIM */
dtimper_msec = dtimper * vif->bss_conf.beacon_int; dtimper_msec = dtimper * vif->bss_conf.beacon_int;
...@@ -121,7 +115,7 @@ static void iwl_power_build_cmd(struct iwl_mvm *mvm, struct ieee80211_vif *vif, ...@@ -121,7 +115,7 @@ static void iwl_power_build_cmd(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
MSEC_PER_SEC * POWER_KEEP_ALIVE_PERIOD_SEC); MSEC_PER_SEC * POWER_KEEP_ALIVE_PERIOD_SEC);
keep_alive = DIV_ROUND_UP(keep_alive, MSEC_PER_SEC); keep_alive = DIV_ROUND_UP(keep_alive, MSEC_PER_SEC);
cmd->keep_alive_seconds = cpu_to_le16(keep_alive); cmd->keep_alive_seconds = keep_alive;
if (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_LP) { if (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_LP) {
/* TODO: Also for D3 (device sleep / WoWLAN) */ /* TODO: Also for D3 (device sleep / WoWLAN) */
...@@ -148,24 +142,18 @@ int iwl_mvm_power_update_mode(struct iwl_mvm *mvm, struct ieee80211_vif *vif) ...@@ -148,24 +142,18 @@ int iwl_mvm_power_update_mode(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
iwl_power_build_cmd(mvm, vif, &cmd); iwl_power_build_cmd(mvm, vif, &cmd);
IWL_DEBUG_POWER(mvm, IWL_DEBUG_POWER(mvm,
"Sending power table command on mac id 0x%X for power level %d, flags = 0x%X\n", "Sending power table command for power level %d, flags = 0x%X\n",
cmd.id_and_color, iwlmvm_mod_params.power_scheme, iwlmvm_mod_params.power_scheme, le16_to_cpu(cmd.flags));
le16_to_cpu(cmd.flags));
if (cmd.flags & cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK)) { if (cmd.flags & cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK)) {
IWL_DEBUG_POWER(mvm, "Keep alive = %u sec\n", IWL_DEBUG_POWER(mvm, "Keep alive = %u sec\n",
le16_to_cpu(cmd.keep_alive_seconds)); cmd.keep_alive_seconds);
IWL_DEBUG_POWER(mvm, "Rx timeout = %u usec\n", IWL_DEBUG_POWER(mvm, "Rx timeout = %u usec\n",
le32_to_cpu(cmd.rx_data_timeout)); le32_to_cpu(cmd.rx_data_timeout));
IWL_DEBUG_POWER(mvm, "Tx timeout = %u usec\n", IWL_DEBUG_POWER(mvm, "Tx timeout = %u usec\n",
le32_to_cpu(cmd.tx_data_timeout)); le32_to_cpu(cmd.tx_data_timeout));
IWL_DEBUG_POWER(mvm, "Rx timeout (uAPSD) = %u usec\n",
le32_to_cpu(cmd.rx_data_timeout_uapsd));
IWL_DEBUG_POWER(mvm, "Tx timeout = %u usec\n",
le32_to_cpu(cmd.tx_data_timeout_uapsd));
IWL_DEBUG_POWER(mvm, "LP RX RSSI threshold = %u\n", IWL_DEBUG_POWER(mvm, "LP RX RSSI threshold = %u\n",
cmd.lprx_rssi_threshold); cmd.lprx_rssi_threshold);
IWL_DEBUG_POWER(mvm, "DTIMs to skip = %u\n", cmd.num_skip_dtim);
} }
return iwl_mvm_send_cmd_pdu(mvm, POWER_TABLE_CMD, CMD_SYNC, return iwl_mvm_send_cmd_pdu(mvm, POWER_TABLE_CMD, CMD_SYNC,
...@@ -175,7 +163,6 @@ int iwl_mvm_power_update_mode(struct iwl_mvm *mvm, struct ieee80211_vif *vif) ...@@ -175,7 +163,6 @@ int iwl_mvm_power_update_mode(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
int iwl_mvm_power_disable(struct iwl_mvm *mvm, struct ieee80211_vif *vif) int iwl_mvm_power_disable(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
{ {
struct iwl_powertable_cmd cmd = {}; struct iwl_powertable_cmd cmd = {};
struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
if (!iwlwifi_mod_params.power_save) { if (!iwlwifi_mod_params.power_save) {
IWL_DEBUG_POWER(mvm, "Power management is not allowed\n"); IWL_DEBUG_POWER(mvm, "Power management is not allowed\n");
...@@ -185,14 +172,9 @@ int iwl_mvm_power_disable(struct iwl_mvm *mvm, struct ieee80211_vif *vif) ...@@ -185,14 +172,9 @@ int iwl_mvm_power_disable(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
if (vif->type != NL80211_IFTYPE_STATION || vif->p2p) if (vif->type != NL80211_IFTYPE_STATION || vif->p2p)
return 0; return 0;
cmd.id_and_color = cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->id,
mvmvif->color));
cmd.action = cpu_to_le32(FW_CTXT_ACTION_MODIFY);
IWL_DEBUG_POWER(mvm, IWL_DEBUG_POWER(mvm,
"Sending power table command on mac id 0x%X for power level %d, flags = 0x%X\n", "Sending power table command power level %d, flags = 0x%X\n",
cmd.id_and_color, iwlmvm_mod_params.power_scheme, iwlmvm_mod_params.power_scheme, le16_to_cpu(cmd.flags));
le16_to_cpu(cmd.flags));
return iwl_mvm_send_cmd_pdu(mvm, POWER_TABLE_CMD, CMD_ASYNC, return iwl_mvm_send_cmd_pdu(mvm, POWER_TABLE_CMD, CMD_ASYNC,
sizeof(cmd), &cmd); sizeof(cmd), &cmd);
......
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