1 /*- 2 * Copyright (c) 2018 Mellanox Technologies. All rights reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 13 * THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS `AS IS' AND 14 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 16 * ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE 17 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 18 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 19 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 20 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 21 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 22 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 23 * SUCH DAMAGE. 24 * 25 * $FreeBSD$ 26 */ 27 28 #include "opt_rss.h" 29 #include "opt_ratelimit.h" 30 31 #include <dev/mlx5/mlx5_en/en.h> 32 33 void 34 mlx5e_dim_build_cq_param(struct mlx5e_priv *priv, 35 struct mlx5e_cq_param *param) 36 { 37 struct net_dim_cq_moder prof; 38 void *cqc = param->cqc; 39 40 if (priv->params.rx_cq_moderation_mode < 2) 41 return; 42 43 switch (MLX5_GET(cqc, cqc, cq_period_mode)) { 44 case MLX5_CQ_PERIOD_MODE_START_FROM_CQE: 45 prof = net_dim_profile[NET_DIM_CQ_PERIOD_MODE_START_FROM_CQE] 46 [NET_DIM_DEF_PROFILE_CQE]; 47 MLX5_SET(cqc, cqc, cq_period, prof.usec); 48 MLX5_SET(cqc, cqc, cq_max_count, prof.pkts); 49 break; 50 51 case MLX5_CQ_PERIOD_MODE_START_FROM_EQE: 52 prof = net_dim_profile[NET_DIM_CQ_PERIOD_MODE_START_FROM_EQE] 53 [NET_DIM_DEF_PROFILE_EQE]; 54 MLX5_SET(cqc, cqc, cq_period, prof.usec); 55 MLX5_SET(cqc, cqc, cq_max_count, prof.pkts); 56 break; 57 default: 58 break; 59 } 60 } 61 62 void 63 mlx5e_dim_work(struct work_struct *work) 64 { 65 struct net_dim *dim = container_of(work, struct net_dim, work); 66 struct mlx5e_rq *rq = container_of(dim, struct mlx5e_rq, dim); 67 struct mlx5e_channel *c = container_of(rq, struct mlx5e_channel, rq); 68 struct net_dim_cq_moder cur_profile; 69 u8 profile_ix; 70 u8 mode; 71 72 /* copy current auto moderation settings and set new state */ 73 mtx_lock(&rq->mtx); 74 profile_ix = dim->profile_ix; 75 mode = dim->mode; 76 dim->state = NET_DIM_START_MEASURE; 77 mtx_unlock(&rq->mtx); 78 79 /* check for invalid mode */ 80 if (mode == 255) 81 return; 82 83 /* get current profile */ 84 cur_profile = net_dim_profile[mode][profile_ix]; 85 86 /* apply LRO restrictions */ 87 if (c->priv->params.hw_lro_en && 88 cur_profile.pkts > MLX5E_DIM_MAX_RX_CQ_MODERATION_PKTS_WITH_LRO) { 89 cur_profile.pkts = MLX5E_DIM_MAX_RX_CQ_MODERATION_PKTS_WITH_LRO; 90 } 91 92 /* modify CQ */ 93 mlx5_core_modify_cq_moderation(c->priv->mdev, &rq->cq.mcq, 94 cur_profile.usec, cur_profile.pkts); 95 } 96