|
@@ -89,6 +89,7 @@ MODULE_AUTHOR(DRV_COPYRIGHT " " DRV_AUTHOR);
|
|
MODULE_LICENSE("GPL");
|
|
MODULE_LICENSE("GPL");
|
|
|
|
|
|
static const struct iwl_op_mode_ops iwl_mvm_ops;
|
|
static const struct iwl_op_mode_ops iwl_mvm_ops;
|
|
|
|
+static const struct iwl_op_mode_ops iwl_mvm_ops_mq;
|
|
|
|
|
|
struct iwl_mvm_mod_params iwlmvm_mod_params = {
|
|
struct iwl_mvm_mod_params iwlmvm_mod_params = {
|
|
.power_scheme = IWL_POWER_SCHEME_BPS,
|
|
.power_scheme = IWL_POWER_SCHEME_BPS,
|
|
@@ -424,7 +425,6 @@ iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg,
|
|
hw->max_tx_aggregation_subframes = cfg->max_tx_agg_size;
|
|
hw->max_tx_aggregation_subframes = cfg->max_tx_agg_size;
|
|
|
|
|
|
op_mode = hw->priv;
|
|
op_mode = hw->priv;
|
|
- op_mode->ops = &iwl_mvm_ops;
|
|
|
|
|
|
|
|
mvm = IWL_OP_MODE_GET_MVM(op_mode);
|
|
mvm = IWL_OP_MODE_GET_MVM(op_mode);
|
|
mvm->dev = trans->dev;
|
|
mvm->dev = trans->dev;
|
|
@@ -433,6 +433,15 @@ iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg,
|
|
mvm->fw = fw;
|
|
mvm->fw = fw;
|
|
mvm->hw = hw;
|
|
mvm->hw = hw;
|
|
|
|
|
|
|
|
+ if (iwl_mvm_has_new_rx_api(mvm)) {
|
|
|
|
+ op_mode->ops = &iwl_mvm_ops_mq;
|
|
|
|
+ } else {
|
|
|
|
+ op_mode->ops = &iwl_mvm_ops;
|
|
|
|
+
|
|
|
|
+ if (WARN_ON(trans->num_rx_queues > 1))
|
|
|
|
+ goto out_free;
|
|
|
|
+ }
|
|
|
|
+
|
|
mvm->restart_fw = iwlwifi_mod_params.restart_fw ? -1 : 0;
|
|
mvm->restart_fw = iwlwifi_mod_params.restart_fw ? -1 : 0;
|
|
|
|
|
|
mvm->aux_queue = 15;
|
|
mvm->aux_queue = 15;
|
|
@@ -719,21 +728,11 @@ static inline void iwl_mvm_rx_check_trigger(struct iwl_mvm *mvm,
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
-static void iwl_mvm_rx_dispatch(struct iwl_op_mode *op_mode,
|
|
|
|
- struct napi_struct *napi,
|
|
|
|
- struct iwl_rx_cmd_buffer *rxb)
|
|
|
|
|
|
+static void iwl_mvm_rx_common(struct iwl_mvm *mvm,
|
|
|
|
+ struct iwl_rx_cmd_buffer *rxb,
|
|
|
|
+ struct iwl_rx_packet *pkt)
|
|
{
|
|
{
|
|
- struct iwl_rx_packet *pkt = rxb_addr(rxb);
|
|
|
|
- struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode);
|
|
|
|
- u8 i;
|
|
|
|
-
|
|
|
|
- if (likely(pkt->hdr.cmd == REPLY_RX_MPDU_CMD)) {
|
|
|
|
- iwl_mvm_rx_rx_mpdu(mvm, napi, rxb);
|
|
|
|
- return;
|
|
|
|
- } else if (pkt->hdr.cmd == REPLY_RX_PHY_CMD) {
|
|
|
|
- iwl_mvm_rx_rx_phy_cmd(mvm, rxb);
|
|
|
|
- return;
|
|
|
|
- }
|
|
|
|
|
|
+ int i;
|
|
|
|
|
|
iwl_mvm_rx_check_trigger(mvm, pkt);
|
|
iwl_mvm_rx_check_trigger(mvm, pkt);
|
|
|
|
|
|
@@ -773,6 +772,36 @@ static void iwl_mvm_rx_dispatch(struct iwl_op_mode *op_mode,
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+static void iwl_mvm_rx(struct iwl_op_mode *op_mode,
|
|
|
|
+ struct napi_struct *napi,
|
|
|
|
+ struct iwl_rx_cmd_buffer *rxb)
|
|
|
|
+{
|
|
|
|
+ struct iwl_rx_packet *pkt = rxb_addr(rxb);
|
|
|
|
+ struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode);
|
|
|
|
+
|
|
|
|
+ if (likely(pkt->hdr.cmd == REPLY_RX_MPDU_CMD))
|
|
|
|
+ iwl_mvm_rx_rx_mpdu(mvm, napi, rxb);
|
|
|
|
+ else if (pkt->hdr.cmd == REPLY_RX_PHY_CMD)
|
|
|
|
+ iwl_mvm_rx_rx_phy_cmd(mvm, rxb);
|
|
|
|
+ else
|
|
|
|
+ iwl_mvm_rx_common(mvm, rxb, pkt);
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+static void iwl_mvm_rx_mq(struct iwl_op_mode *op_mode,
|
|
|
|
+ struct napi_struct *napi,
|
|
|
|
+ struct iwl_rx_cmd_buffer *rxb)
|
|
|
|
+{
|
|
|
|
+ struct iwl_rx_packet *pkt = rxb_addr(rxb);
|
|
|
|
+ struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode);
|
|
|
|
+
|
|
|
|
+ if (likely(pkt->hdr.cmd == REPLY_RX_MPDU_CMD))
|
|
|
|
+ iwl_mvm_rx_rx_mpdu(mvm, napi, rxb);
|
|
|
|
+ else if (pkt->hdr.cmd == REPLY_RX_PHY_CMD)
|
|
|
|
+ iwl_mvm_rx_rx_phy_cmd(mvm, rxb);
|
|
|
|
+ else
|
|
|
|
+ iwl_mvm_rx_common(mvm, rxb, pkt);
|
|
|
|
+}
|
|
|
|
+
|
|
static void iwl_mvm_stop_sw_queue(struct iwl_op_mode *op_mode, int queue)
|
|
static void iwl_mvm_stop_sw_queue(struct iwl_op_mode *op_mode, int queue)
|
|
{
|
|
{
|
|
struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode);
|
|
struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode);
|
|
@@ -1366,17 +1395,38 @@ int iwl_mvm_exit_d0i3(struct iwl_op_mode *op_mode)
|
|
return _iwl_mvm_exit_d0i3(mvm);
|
|
return _iwl_mvm_exit_d0i3(mvm);
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+#define IWL_MVM_COMMON_OPS \
|
|
|
|
+ /* these could be differentiated */ \
|
|
|
|
+ .queue_full = iwl_mvm_stop_sw_queue, \
|
|
|
|
+ .queue_not_full = iwl_mvm_wake_sw_queue, \
|
|
|
|
+ .hw_rf_kill = iwl_mvm_set_hw_rfkill_state, \
|
|
|
|
+ .free_skb = iwl_mvm_free_skb, \
|
|
|
|
+ .nic_error = iwl_mvm_nic_error, \
|
|
|
|
+ .cmd_queue_full = iwl_mvm_cmd_queue_full, \
|
|
|
|
+ .nic_config = iwl_mvm_nic_config, \
|
|
|
|
+ .enter_d0i3 = iwl_mvm_enter_d0i3, \
|
|
|
|
+ .exit_d0i3 = iwl_mvm_exit_d0i3, \
|
|
|
|
+ /* as we only register one, these MUST be common! */ \
|
|
|
|
+ .start = iwl_op_mode_mvm_start, \
|
|
|
|
+ .stop = iwl_op_mode_mvm_stop
|
|
|
|
+
|
|
static const struct iwl_op_mode_ops iwl_mvm_ops = {
|
|
static const struct iwl_op_mode_ops iwl_mvm_ops = {
|
|
- .start = iwl_op_mode_mvm_start,
|
|
|
|
- .stop = iwl_op_mode_mvm_stop,
|
|
|
|
- .rx = iwl_mvm_rx_dispatch,
|
|
|
|
- .queue_full = iwl_mvm_stop_sw_queue,
|
|
|
|
- .queue_not_full = iwl_mvm_wake_sw_queue,
|
|
|
|
- .hw_rf_kill = iwl_mvm_set_hw_rfkill_state,
|
|
|
|
- .free_skb = iwl_mvm_free_skb,
|
|
|
|
- .nic_error = iwl_mvm_nic_error,
|
|
|
|
- .cmd_queue_full = iwl_mvm_cmd_queue_full,
|
|
|
|
- .nic_config = iwl_mvm_nic_config,
|
|
|
|
- .enter_d0i3 = iwl_mvm_enter_d0i3,
|
|
|
|
- .exit_d0i3 = iwl_mvm_exit_d0i3,
|
|
|
|
|
|
+ IWL_MVM_COMMON_OPS,
|
|
|
|
+ .rx = iwl_mvm_rx,
|
|
|
|
+};
|
|
|
|
+
|
|
|
|
+static void iwl_mvm_rx_mq_rss(struct iwl_op_mode *op_mode,
|
|
|
|
+ struct napi_struct *napi,
|
|
|
|
+ struct iwl_rx_cmd_buffer *rxb,
|
|
|
|
+ unsigned int queue)
|
|
|
|
+{
|
|
|
|
+ struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode);
|
|
|
|
+
|
|
|
|
+ iwl_mvm_rx_rx_mpdu(mvm, napi, rxb);
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+static const struct iwl_op_mode_ops iwl_mvm_ops_mq = {
|
|
|
|
+ IWL_MVM_COMMON_OPS,
|
|
|
|
+ .rx = iwl_mvm_rx_mq,
|
|
|
|
+ .rx_rss = iwl_mvm_rx_mq_rss,
|
|
};
|
|
};
|