1 /*
2  * Copyright (c) 2015, Mellanox Technologies. All rights reserved.
3  *
4  * This software is available to you under a choice of one of two
5  * licenses.  You may choose to be licensed under the terms of the GNU
6  * General Public License (GPL) Version 2, available from the file
7  * COPYING in the main directory of this source tree, or the
8  * OpenIB.org BSD license below:
9  *
10  *     Redistribution and use in source and binary forms, with or
11  *     without modification, are permitted provided that the following
12  *     conditions are met:
13  *
14  *      - Redistributions of source code must retain the above
15  *        copyright notice, this list of conditions and the following
16  *        disclaimer.
17  *
18  *      - Redistributions in binary form must reproduce the above
19  *        copyright notice, this list of conditions and the following
20  *        disclaimer in the documentation and/or other materials
21  *        provided with the distribution.
22  *
23  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
24  * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
25  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
26  * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
27  * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
28  * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
29  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
30  * SOFTWARE.
31  */
32 
33 #include "en.h"
34 
35 static void mlx5e_get_drvinfo(struct net_device *dev,
36 			      struct ethtool_drvinfo *drvinfo)
37 {
38 	struct mlx5e_priv *priv = netdev_priv(dev);
39 	struct mlx5_core_dev *mdev = priv->mdev;
40 
41 	strlcpy(drvinfo->driver, DRIVER_NAME, sizeof(drvinfo->driver));
42 	strlcpy(drvinfo->version, DRIVER_VERSION " (" DRIVER_RELDATE ")",
43 		sizeof(drvinfo->version));
44 	snprintf(drvinfo->fw_version, sizeof(drvinfo->fw_version),
45 		 "%d.%d.%d",
46 		 fw_rev_maj(mdev), fw_rev_min(mdev), fw_rev_sub(mdev));
47 	strlcpy(drvinfo->bus_info, pci_name(mdev->pdev),
48 		sizeof(drvinfo->bus_info));
49 }
50 
51 struct ptys2ethtool_config {
52 	__ETHTOOL_DECLARE_LINK_MODE_MASK(supported);
53 	__ETHTOOL_DECLARE_LINK_MODE_MASK(advertised);
54 	u32 speed;
55 };
56 
57 static struct ptys2ethtool_config ptys2ethtool_table[MLX5E_LINK_MODES_NUMBER];
58 
59 #define MLX5_BUILD_PTYS2ETHTOOL_CONFIG(reg_, speed_, ...)               \
60 	({                                                              \
61 		struct ptys2ethtool_config *cfg;                        \
62 		const unsigned int modes[] = { __VA_ARGS__ };           \
63 		unsigned int i;                                         \
64 		cfg = &ptys2ethtool_table[reg_];                        \
65 		cfg->speed = speed_;                                    \
66 		bitmap_zero(cfg->supported,                             \
67 			    __ETHTOOL_LINK_MODE_MASK_NBITS);            \
68 		bitmap_zero(cfg->advertised,                            \
69 			    __ETHTOOL_LINK_MODE_MASK_NBITS);            \
70 		for (i = 0 ; i < ARRAY_SIZE(modes) ; ++i) {             \
71 			__set_bit(modes[i], cfg->supported);            \
72 			__set_bit(modes[i], cfg->advertised);           \
73 		}                                                       \
74 	})
75 
76 void mlx5e_build_ptys2ethtool_map(void)
77 {
78 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_1000BASE_CX_SGMII, SPEED_1000,
79 				       ETHTOOL_LINK_MODE_1000baseKX_Full_BIT);
80 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_1000BASE_KX, SPEED_1000,
81 				       ETHTOOL_LINK_MODE_1000baseKX_Full_BIT);
82 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_10GBASE_CX4, SPEED_10000,
83 				       ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT);
84 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_10GBASE_KX4, SPEED_10000,
85 				       ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT);
86 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_10GBASE_KR, SPEED_10000,
87 				       ETHTOOL_LINK_MODE_10000baseKR_Full_BIT);
88 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_20GBASE_KR2, SPEED_20000,
89 				       ETHTOOL_LINK_MODE_20000baseKR2_Full_BIT);
90 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_40GBASE_CR4, SPEED_40000,
91 				       ETHTOOL_LINK_MODE_40000baseCR4_Full_BIT);
92 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_40GBASE_KR4, SPEED_40000,
93 				       ETHTOOL_LINK_MODE_40000baseKR4_Full_BIT);
94 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_56GBASE_R4, SPEED_56000,
95 				       ETHTOOL_LINK_MODE_56000baseKR4_Full_BIT);
96 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_10GBASE_CR, SPEED_10000,
97 				       ETHTOOL_LINK_MODE_10000baseKR_Full_BIT);
98 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_10GBASE_SR, SPEED_10000,
99 				       ETHTOOL_LINK_MODE_10000baseKR_Full_BIT);
100 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_10GBASE_ER, SPEED_10000,
101 				       ETHTOOL_LINK_MODE_10000baseKR_Full_BIT);
102 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_40GBASE_SR4, SPEED_40000,
103 				       ETHTOOL_LINK_MODE_40000baseSR4_Full_BIT);
104 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_40GBASE_LR4, SPEED_40000,
105 				       ETHTOOL_LINK_MODE_40000baseLR4_Full_BIT);
106 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_50GBASE_SR2, SPEED_50000,
107 				       ETHTOOL_LINK_MODE_50000baseSR2_Full_BIT);
108 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_100GBASE_CR4, SPEED_100000,
109 				       ETHTOOL_LINK_MODE_100000baseCR4_Full_BIT);
110 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_100GBASE_SR4, SPEED_100000,
111 				       ETHTOOL_LINK_MODE_100000baseSR4_Full_BIT);
112 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_100GBASE_KR4, SPEED_100000,
113 				       ETHTOOL_LINK_MODE_100000baseKR4_Full_BIT);
114 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_100GBASE_LR4, SPEED_100000,
115 				       ETHTOOL_LINK_MODE_100000baseLR4_ER4_Full_BIT);
116 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_10GBASE_T, SPEED_10000,
117 				       ETHTOOL_LINK_MODE_10000baseT_Full_BIT);
118 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_25GBASE_CR, SPEED_25000,
119 				       ETHTOOL_LINK_MODE_25000baseCR_Full_BIT);
120 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_25GBASE_KR, SPEED_25000,
121 				       ETHTOOL_LINK_MODE_25000baseKR_Full_BIT);
122 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_25GBASE_SR, SPEED_25000,
123 				       ETHTOOL_LINK_MODE_25000baseSR_Full_BIT);
124 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_50GBASE_CR2, SPEED_50000,
125 				       ETHTOOL_LINK_MODE_50000baseCR2_Full_BIT);
126 	MLX5_BUILD_PTYS2ETHTOOL_CONFIG(MLX5E_50GBASE_KR2, SPEED_50000,
127 				       ETHTOOL_LINK_MODE_50000baseKR2_Full_BIT);
128 }
129 
130 static unsigned long mlx5e_query_pfc_combined(struct mlx5e_priv *priv)
131 {
132 	struct mlx5_core_dev *mdev = priv->mdev;
133 	u8 pfc_en_tx;
134 	u8 pfc_en_rx;
135 	int err;
136 
137 	err = mlx5_query_port_pfc(mdev, &pfc_en_tx, &pfc_en_rx);
138 
139 	return err ? 0 : pfc_en_tx | pfc_en_rx;
140 }
141 
142 static bool mlx5e_query_global_pause_combined(struct mlx5e_priv *priv)
143 {
144 	struct mlx5_core_dev *mdev = priv->mdev;
145 	u32 rx_pause;
146 	u32 tx_pause;
147 	int err;
148 
149 	err = mlx5_query_port_pause(mdev, &rx_pause, &tx_pause);
150 
151 	return err ? false : rx_pause | tx_pause;
152 }
153 
154 #define MLX5E_NUM_Q_CNTRS(priv) (NUM_Q_COUNTERS * (!!priv->q_counter))
155 #define MLX5E_NUM_RQ_STATS(priv) \
156 	(NUM_RQ_STATS * priv->params.num_channels * \
157 	 test_bit(MLX5E_STATE_OPENED, &priv->state))
158 #define MLX5E_NUM_SQ_STATS(priv) \
159 	(NUM_SQ_STATS * priv->params.num_channels * priv->params.num_tc * \
160 	 test_bit(MLX5E_STATE_OPENED, &priv->state))
161 #define MLX5E_NUM_PFC_COUNTERS(priv) \
162 	((mlx5e_query_global_pause_combined(priv) + hweight8(mlx5e_query_pfc_combined(priv))) * \
163 	  NUM_PPORT_PER_PRIO_PFC_COUNTERS)
164 
165 static int mlx5e_get_sset_count(struct net_device *dev, int sset)
166 {
167 	struct mlx5e_priv *priv = netdev_priv(dev);
168 
169 	switch (sset) {
170 	case ETH_SS_STATS:
171 		return NUM_SW_COUNTERS +
172 		       MLX5E_NUM_Q_CNTRS(priv) +
173 		       NUM_VPORT_COUNTERS + NUM_PPORT_COUNTERS +
174 		       MLX5E_NUM_RQ_STATS(priv) +
175 		       MLX5E_NUM_SQ_STATS(priv) +
176 		       MLX5E_NUM_PFC_COUNTERS(priv);
177 	case ETH_SS_PRIV_FLAGS:
178 		return ARRAY_SIZE(mlx5e_priv_flags);
179 	/* fallthrough */
180 	default:
181 		return -EOPNOTSUPP;
182 	}
183 }
184 
185 static void mlx5e_fill_stats_strings(struct mlx5e_priv *priv, uint8_t *data)
186 {
187 	int i, j, tc, prio, idx = 0;
188 	unsigned long pfc_combined;
189 
190 	/* SW counters */
191 	for (i = 0; i < NUM_SW_COUNTERS; i++)
192 		strcpy(data + (idx++) * ETH_GSTRING_LEN, sw_stats_desc[i].format);
193 
194 	/* Q counters */
195 	for (i = 0; i < MLX5E_NUM_Q_CNTRS(priv); i++)
196 		strcpy(data + (idx++) * ETH_GSTRING_LEN, q_stats_desc[i].format);
197 
198 	/* VPORT counters */
199 	for (i = 0; i < NUM_VPORT_COUNTERS; i++)
200 		strcpy(data + (idx++) * ETH_GSTRING_LEN,
201 		       vport_stats_desc[i].format);
202 
203 	/* PPORT counters */
204 	for (i = 0; i < NUM_PPORT_802_3_COUNTERS; i++)
205 		strcpy(data + (idx++) * ETH_GSTRING_LEN,
206 		       pport_802_3_stats_desc[i].format);
207 
208 	for (i = 0; i < NUM_PPORT_2863_COUNTERS; i++)
209 		strcpy(data + (idx++) * ETH_GSTRING_LEN,
210 		       pport_2863_stats_desc[i].format);
211 
212 	for (i = 0; i < NUM_PPORT_2819_COUNTERS; i++)
213 		strcpy(data + (idx++) * ETH_GSTRING_LEN,
214 		       pport_2819_stats_desc[i].format);
215 
216 	for (prio = 0; prio < NUM_PPORT_PRIO; prio++) {
217 		for (i = 0; i < NUM_PPORT_PER_PRIO_TRAFFIC_COUNTERS; i++)
218 			sprintf(data + (idx++) * ETH_GSTRING_LEN,
219 				pport_per_prio_traffic_stats_desc[i].format, prio);
220 	}
221 
222 	pfc_combined = mlx5e_query_pfc_combined(priv);
223 	for_each_set_bit(prio, &pfc_combined, NUM_PPORT_PRIO) {
224 		for (i = 0; i < NUM_PPORT_PER_PRIO_PFC_COUNTERS; i++) {
225 			char pfc_string[ETH_GSTRING_LEN];
226 
227 			snprintf(pfc_string, sizeof(pfc_string), "prio%d", prio);
228 			sprintf(data + (idx++) * ETH_GSTRING_LEN,
229 				pport_per_prio_pfc_stats_desc[i].format, pfc_string);
230 		}
231 	}
232 
233 	if (mlx5e_query_global_pause_combined(priv)) {
234 		for (i = 0; i < NUM_PPORT_PER_PRIO_PFC_COUNTERS; i++) {
235 			sprintf(data + (idx++) * ETH_GSTRING_LEN,
236 				pport_per_prio_pfc_stats_desc[i].format, "global");
237 		}
238 	}
239 
240 	if (!test_bit(MLX5E_STATE_OPENED, &priv->state))
241 		return;
242 
243 	/* per channel counters */
244 	for (i = 0; i < priv->params.num_channels; i++)
245 		for (j = 0; j < NUM_RQ_STATS; j++)
246 			sprintf(data + (idx++) * ETH_GSTRING_LEN,
247 				rq_stats_desc[j].format, i);
248 
249 	for (tc = 0; tc < priv->params.num_tc; tc++)
250 		for (i = 0; i < priv->params.num_channels; i++)
251 			for (j = 0; j < NUM_SQ_STATS; j++)
252 				sprintf(data + (idx++) * ETH_GSTRING_LEN,
253 					sq_stats_desc[j].format,
254 					priv->channeltc_to_txq_map[i][tc]);
255 }
256 
257 static void mlx5e_get_strings(struct net_device *dev,
258 			      uint32_t stringset, uint8_t *data)
259 {
260 	struct mlx5e_priv *priv = netdev_priv(dev);
261 	int i;
262 
263 	switch (stringset) {
264 	case ETH_SS_PRIV_FLAGS:
265 		for (i = 0; i < ARRAY_SIZE(mlx5e_priv_flags); i++)
266 			strcpy(data + i * ETH_GSTRING_LEN, mlx5e_priv_flags[i]);
267 		break;
268 
269 	case ETH_SS_TEST:
270 		break;
271 
272 	case ETH_SS_STATS:
273 		mlx5e_fill_stats_strings(priv, data);
274 		break;
275 	}
276 }
277 
278 static void mlx5e_get_ethtool_stats(struct net_device *dev,
279 				    struct ethtool_stats *stats, u64 *data)
280 {
281 	struct mlx5e_priv *priv = netdev_priv(dev);
282 	int i, j, tc, prio, idx = 0;
283 	unsigned long pfc_combined;
284 
285 	if (!data)
286 		return;
287 
288 	mutex_lock(&priv->state_lock);
289 	if (test_bit(MLX5E_STATE_OPENED, &priv->state))
290 		mlx5e_update_stats(priv);
291 	mutex_unlock(&priv->state_lock);
292 
293 	for (i = 0; i < NUM_SW_COUNTERS; i++)
294 		data[idx++] = MLX5E_READ_CTR64_CPU(&priv->stats.sw,
295 						   sw_stats_desc, i);
296 
297 	for (i = 0; i < MLX5E_NUM_Q_CNTRS(priv); i++)
298 		data[idx++] = MLX5E_READ_CTR32_CPU(&priv->stats.qcnt,
299 						   q_stats_desc, i);
300 
301 	for (i = 0; i < NUM_VPORT_COUNTERS; i++)
302 		data[idx++] = MLX5E_READ_CTR64_BE(priv->stats.vport.query_vport_out,
303 						  vport_stats_desc, i);
304 
305 	for (i = 0; i < NUM_PPORT_802_3_COUNTERS; i++)
306 		data[idx++] = MLX5E_READ_CTR64_BE(&priv->stats.pport.IEEE_802_3_counters,
307 						  pport_802_3_stats_desc, i);
308 
309 	for (i = 0; i < NUM_PPORT_2863_COUNTERS; i++)
310 		data[idx++] = MLX5E_READ_CTR64_BE(&priv->stats.pport.RFC_2863_counters,
311 						  pport_2863_stats_desc, i);
312 
313 	for (i = 0; i < NUM_PPORT_2819_COUNTERS; i++)
314 		data[idx++] = MLX5E_READ_CTR64_BE(&priv->stats.pport.RFC_2819_counters,
315 						  pport_2819_stats_desc, i);
316 
317 	for (prio = 0; prio < NUM_PPORT_PRIO; prio++) {
318 		for (i = 0; i < NUM_PPORT_PER_PRIO_TRAFFIC_COUNTERS; i++)
319 			data[idx++] = MLX5E_READ_CTR64_BE(&priv->stats.pport.per_prio_counters[prio],
320 						 pport_per_prio_traffic_stats_desc, i);
321 	}
322 
323 	pfc_combined = mlx5e_query_pfc_combined(priv);
324 	for_each_set_bit(prio, &pfc_combined, NUM_PPORT_PRIO) {
325 		for (i = 0; i < NUM_PPORT_PER_PRIO_PFC_COUNTERS; i++) {
326 			data[idx++] = MLX5E_READ_CTR64_BE(&priv->stats.pport.per_prio_counters[prio],
327 							  pport_per_prio_pfc_stats_desc, i);
328 		}
329 	}
330 
331 	if (mlx5e_query_global_pause_combined(priv)) {
332 		for (i = 0; i < NUM_PPORT_PER_PRIO_PFC_COUNTERS; i++) {
333 			data[idx++] = MLX5E_READ_CTR64_BE(&priv->stats.pport.per_prio_counters[0],
334 							  pport_per_prio_pfc_stats_desc, 0);
335 		}
336 	}
337 
338 	if (!test_bit(MLX5E_STATE_OPENED, &priv->state))
339 		return;
340 
341 	/* per channel counters */
342 	for (i = 0; i < priv->params.num_channels; i++)
343 		for (j = 0; j < NUM_RQ_STATS; j++)
344 			data[idx++] =
345 			       MLX5E_READ_CTR64_CPU(&priv->channel[i]->rq.stats,
346 						    rq_stats_desc, j);
347 
348 	for (tc = 0; tc < priv->params.num_tc; tc++)
349 		for (i = 0; i < priv->params.num_channels; i++)
350 			for (j = 0; j < NUM_SQ_STATS; j++)
351 				data[idx++] = MLX5E_READ_CTR64_CPU(&priv->channel[i]->sq[tc].stats,
352 								   sq_stats_desc, j);
353 }
354 
355 static void mlx5e_get_ringparam(struct net_device *dev,
356 				struct ethtool_ringparam *param)
357 {
358 	struct mlx5e_priv *priv = netdev_priv(dev);
359 	int rq_wq_type = priv->params.rq_wq_type;
360 
361 	param->rx_max_pending = 1 << mlx5_max_log_rq_size(rq_wq_type);
362 	param->tx_max_pending = 1 << MLX5E_PARAMS_MAXIMUM_LOG_SQ_SIZE;
363 	param->rx_pending     = 1 << priv->params.log_rq_size;
364 	param->tx_pending     = 1 << priv->params.log_sq_size;
365 }
366 
367 static int mlx5e_set_ringparam(struct net_device *dev,
368 			       struct ethtool_ringparam *param)
369 {
370 	struct mlx5e_priv *priv = netdev_priv(dev);
371 	bool was_opened;
372 	int rq_wq_type = priv->params.rq_wq_type;
373 	u16 min_rx_wqes;
374 	u8 log_rq_size;
375 	u8 log_sq_size;
376 	int err = 0;
377 
378 	if (param->rx_jumbo_pending) {
379 		netdev_info(dev, "%s: rx_jumbo_pending not supported\n",
380 			    __func__);
381 		return -EINVAL;
382 	}
383 	if (param->rx_mini_pending) {
384 		netdev_info(dev, "%s: rx_mini_pending not supported\n",
385 			    __func__);
386 		return -EINVAL;
387 	}
388 	if (param->rx_pending < (1 << mlx5_min_log_rq_size(rq_wq_type))) {
389 		netdev_info(dev, "%s: rx_pending (%d) < min (%d)\n",
390 			    __func__, param->rx_pending,
391 			    1 << mlx5_min_log_rq_size(rq_wq_type));
392 		return -EINVAL;
393 	}
394 	if (param->rx_pending > (1 << mlx5_max_log_rq_size(rq_wq_type))) {
395 		netdev_info(dev, "%s: rx_pending (%d) > max (%d)\n",
396 			    __func__, param->rx_pending,
397 			    1 << mlx5_max_log_rq_size(rq_wq_type));
398 		return -EINVAL;
399 	}
400 	if (param->tx_pending < (1 << MLX5E_PARAMS_MINIMUM_LOG_SQ_SIZE)) {
401 		netdev_info(dev, "%s: tx_pending (%d) < min (%d)\n",
402 			    __func__, param->tx_pending,
403 			    1 << MLX5E_PARAMS_MINIMUM_LOG_SQ_SIZE);
404 		return -EINVAL;
405 	}
406 	if (param->tx_pending > (1 << MLX5E_PARAMS_MAXIMUM_LOG_SQ_SIZE)) {
407 		netdev_info(dev, "%s: tx_pending (%d) > max (%d)\n",
408 			    __func__, param->tx_pending,
409 			    1 << MLX5E_PARAMS_MAXIMUM_LOG_SQ_SIZE);
410 		return -EINVAL;
411 	}
412 
413 	log_rq_size = order_base_2(param->rx_pending);
414 	log_sq_size = order_base_2(param->tx_pending);
415 	min_rx_wqes = mlx5_min_rx_wqes(rq_wq_type, param->rx_pending);
416 
417 	if (log_rq_size == priv->params.log_rq_size &&
418 	    log_sq_size == priv->params.log_sq_size &&
419 	    min_rx_wqes == priv->params.min_rx_wqes)
420 		return 0;
421 
422 	mutex_lock(&priv->state_lock);
423 
424 	was_opened = test_bit(MLX5E_STATE_OPENED, &priv->state);
425 	if (was_opened)
426 		mlx5e_close_locked(dev);
427 
428 	priv->params.log_rq_size = log_rq_size;
429 	priv->params.log_sq_size = log_sq_size;
430 	priv->params.min_rx_wqes = min_rx_wqes;
431 
432 	if (was_opened)
433 		err = mlx5e_open_locked(dev);
434 
435 	mutex_unlock(&priv->state_lock);
436 
437 	return err;
438 }
439 
440 static void mlx5e_get_channels(struct net_device *dev,
441 			       struct ethtool_channels *ch)
442 {
443 	struct mlx5e_priv *priv = netdev_priv(dev);
444 
445 	ch->max_combined   = mlx5e_get_max_num_channels(priv->mdev);
446 	ch->combined_count = priv->params.num_channels;
447 }
448 
449 static int mlx5e_set_channels(struct net_device *dev,
450 			      struct ethtool_channels *ch)
451 {
452 	struct mlx5e_priv *priv = netdev_priv(dev);
453 	int ncv = mlx5e_get_max_num_channels(priv->mdev);
454 	unsigned int count = ch->combined_count;
455 	bool arfs_enabled;
456 	bool was_opened;
457 	int err = 0;
458 
459 	if (!count) {
460 		netdev_info(dev, "%s: combined_count=0 not supported\n",
461 			    __func__);
462 		return -EINVAL;
463 	}
464 	if (ch->rx_count || ch->tx_count) {
465 		netdev_info(dev, "%s: separate rx/tx count not supported\n",
466 			    __func__);
467 		return -EINVAL;
468 	}
469 	if (count > ncv) {
470 		netdev_info(dev, "%s: count (%d) > max (%d)\n",
471 			    __func__, count, ncv);
472 		return -EINVAL;
473 	}
474 
475 	if (priv->params.num_channels == count)
476 		return 0;
477 
478 	mutex_lock(&priv->state_lock);
479 
480 	was_opened = test_bit(MLX5E_STATE_OPENED, &priv->state);
481 	if (was_opened)
482 		mlx5e_close_locked(dev);
483 
484 	arfs_enabled = dev->features & NETIF_F_NTUPLE;
485 	if (arfs_enabled)
486 		mlx5e_arfs_disable(priv);
487 
488 	priv->params.num_channels = count;
489 	mlx5e_build_default_indir_rqt(priv->mdev, priv->params.indirection_rqt,
490 				      MLX5E_INDIR_RQT_SIZE, count);
491 
492 	if (was_opened)
493 		err = mlx5e_open_locked(dev);
494 	if (err)
495 		goto out;
496 
497 	if (arfs_enabled) {
498 		err = mlx5e_arfs_enable(priv);
499 		if (err)
500 			netdev_err(dev, "%s: mlx5e_arfs_enable failed: %d\n",
501 				   __func__, err);
502 	}
503 
504 out:
505 	mutex_unlock(&priv->state_lock);
506 
507 	return err;
508 }
509 
510 static int mlx5e_get_coalesce(struct net_device *netdev,
511 			      struct ethtool_coalesce *coal)
512 {
513 	struct mlx5e_priv *priv = netdev_priv(netdev);
514 
515 	if (!MLX5_CAP_GEN(priv->mdev, cq_moderation))
516 		return -ENOTSUPP;
517 
518 	coal->rx_coalesce_usecs       = priv->params.rx_cq_moderation.usec;
519 	coal->rx_max_coalesced_frames = priv->params.rx_cq_moderation.pkts;
520 	coal->tx_coalesce_usecs       = priv->params.tx_cq_moderation.usec;
521 	coal->tx_max_coalesced_frames = priv->params.tx_cq_moderation.pkts;
522 	coal->use_adaptive_rx_coalesce = priv->params.rx_am_enabled;
523 
524 	return 0;
525 }
526 
527 static int mlx5e_set_coalesce(struct net_device *netdev,
528 			      struct ethtool_coalesce *coal)
529 {
530 	struct mlx5e_priv *priv    = netdev_priv(netdev);
531 	struct mlx5_core_dev *mdev = priv->mdev;
532 	struct mlx5e_channel *c;
533 	bool restart =
534 		!!coal->use_adaptive_rx_coalesce != priv->params.rx_am_enabled;
535 	bool was_opened;
536 	int err = 0;
537 	int tc;
538 	int i;
539 
540 	if (!MLX5_CAP_GEN(mdev, cq_moderation))
541 		return -ENOTSUPP;
542 
543 	mutex_lock(&priv->state_lock);
544 
545 	was_opened = test_bit(MLX5E_STATE_OPENED, &priv->state);
546 	if (was_opened && restart) {
547 		mlx5e_close_locked(netdev);
548 		priv->params.rx_am_enabled = !!coal->use_adaptive_rx_coalesce;
549 	}
550 
551 	priv->params.tx_cq_moderation.usec = coal->tx_coalesce_usecs;
552 	priv->params.tx_cq_moderation.pkts = coal->tx_max_coalesced_frames;
553 	priv->params.rx_cq_moderation.usec = coal->rx_coalesce_usecs;
554 	priv->params.rx_cq_moderation.pkts = coal->rx_max_coalesced_frames;
555 
556 	if (!was_opened || restart)
557 		goto out;
558 
559 	for (i = 0; i < priv->params.num_channels; ++i) {
560 		c = priv->channel[i];
561 
562 		for (tc = 0; tc < c->num_tc; tc++) {
563 			mlx5_core_modify_cq_moderation(mdev,
564 						&c->sq[tc].cq.mcq,
565 						coal->tx_coalesce_usecs,
566 						coal->tx_max_coalesced_frames);
567 		}
568 
569 		mlx5_core_modify_cq_moderation(mdev, &c->rq.cq.mcq,
570 					       coal->rx_coalesce_usecs,
571 					       coal->rx_max_coalesced_frames);
572 	}
573 
574 out:
575 	if (was_opened && restart)
576 		err = mlx5e_open_locked(netdev);
577 
578 	mutex_unlock(&priv->state_lock);
579 	return err;
580 }
581 
582 static void ptys2ethtool_supported_link(unsigned long *supported_modes,
583 					u32 eth_proto_cap)
584 {
585 	int proto;
586 
587 	for_each_set_bit(proto, (unsigned long *)&eth_proto_cap, MLX5E_LINK_MODES_NUMBER)
588 		bitmap_or(supported_modes, supported_modes,
589 			  ptys2ethtool_table[proto].supported,
590 			  __ETHTOOL_LINK_MODE_MASK_NBITS);
591 }
592 
593 static void ptys2ethtool_adver_link(unsigned long *advertising_modes,
594 				    u32 eth_proto_cap)
595 {
596 	int proto;
597 
598 	for_each_set_bit(proto, (unsigned long *)&eth_proto_cap, MLX5E_LINK_MODES_NUMBER)
599 		bitmap_or(advertising_modes, advertising_modes,
600 			  ptys2ethtool_table[proto].advertised,
601 			  __ETHTOOL_LINK_MODE_MASK_NBITS);
602 }
603 
604 static void ptys2ethtool_supported_port(struct ethtool_link_ksettings *link_ksettings,
605 					u32 eth_proto_cap)
606 {
607 	if (eth_proto_cap & (MLX5E_PROT_MASK(MLX5E_10GBASE_CR)
608 			   | MLX5E_PROT_MASK(MLX5E_10GBASE_SR)
609 			   | MLX5E_PROT_MASK(MLX5E_40GBASE_CR4)
610 			   | MLX5E_PROT_MASK(MLX5E_40GBASE_SR4)
611 			   | MLX5E_PROT_MASK(MLX5E_100GBASE_SR4)
612 			   | MLX5E_PROT_MASK(MLX5E_1000BASE_CX_SGMII))) {
613 		ethtool_link_ksettings_add_link_mode(link_ksettings, supported, FIBRE);
614 	}
615 
616 	if (eth_proto_cap & (MLX5E_PROT_MASK(MLX5E_100GBASE_KR4)
617 			   | MLX5E_PROT_MASK(MLX5E_40GBASE_KR4)
618 			   | MLX5E_PROT_MASK(MLX5E_10GBASE_KR)
619 			   | MLX5E_PROT_MASK(MLX5E_10GBASE_KX4)
620 			   | MLX5E_PROT_MASK(MLX5E_1000BASE_KX))) {
621 		ethtool_link_ksettings_add_link_mode(link_ksettings, supported, Backplane);
622 	}
623 }
624 
625 int mlx5e_get_max_linkspeed(struct mlx5_core_dev *mdev, u32 *speed)
626 {
627 	u32 max_speed = 0;
628 	u32 proto_cap;
629 	int err;
630 	int i;
631 
632 	err = mlx5_query_port_proto_cap(mdev, &proto_cap, MLX5_PTYS_EN);
633 	if (err)
634 		return err;
635 
636 	for (i = 0; i < MLX5E_LINK_MODES_NUMBER; ++i)
637 		if (proto_cap & MLX5E_PROT_MASK(i))
638 			max_speed = max(max_speed, ptys2ethtool_table[i].speed);
639 
640 	*speed = max_speed;
641 	return 0;
642 }
643 
644 static void get_speed_duplex(struct net_device *netdev,
645 			     u32 eth_proto_oper,
646 			     struct ethtool_link_ksettings *link_ksettings)
647 {
648 	int i;
649 	u32 speed = SPEED_UNKNOWN;
650 	u8 duplex = DUPLEX_UNKNOWN;
651 
652 	if (!netif_carrier_ok(netdev))
653 		goto out;
654 
655 	for (i = 0; i < MLX5E_LINK_MODES_NUMBER; ++i) {
656 		if (eth_proto_oper & MLX5E_PROT_MASK(i)) {
657 			speed = ptys2ethtool_table[i].speed;
658 			duplex = DUPLEX_FULL;
659 			break;
660 		}
661 	}
662 out:
663 	link_ksettings->base.speed = speed;
664 	link_ksettings->base.duplex = duplex;
665 }
666 
667 static void get_supported(u32 eth_proto_cap,
668 			  struct ethtool_link_ksettings *link_ksettings)
669 {
670 	unsigned long *supported = link_ksettings->link_modes.supported;
671 
672 	ptys2ethtool_supported_port(link_ksettings, eth_proto_cap);
673 	ptys2ethtool_supported_link(supported, eth_proto_cap);
674 	ethtool_link_ksettings_add_link_mode(link_ksettings, supported, Pause);
675 	ethtool_link_ksettings_add_link_mode(link_ksettings, supported, Asym_Pause);
676 }
677 
678 static void get_advertising(u32 eth_proto_cap, u8 tx_pause,
679 			    u8 rx_pause,
680 			    struct ethtool_link_ksettings *link_ksettings)
681 {
682 	unsigned long *advertising = link_ksettings->link_modes.advertising;
683 
684 	ptys2ethtool_adver_link(advertising, eth_proto_cap);
685 	if (tx_pause)
686 		ethtool_link_ksettings_add_link_mode(link_ksettings, advertising, Pause);
687 	if (tx_pause ^ rx_pause)
688 		ethtool_link_ksettings_add_link_mode(link_ksettings, advertising, Asym_Pause);
689 }
690 
691 static u8 get_connector_port(u32 eth_proto)
692 {
693 	if (eth_proto & (MLX5E_PROT_MASK(MLX5E_10GBASE_SR)
694 			 | MLX5E_PROT_MASK(MLX5E_40GBASE_SR4)
695 			 | MLX5E_PROT_MASK(MLX5E_100GBASE_SR4)
696 			 | MLX5E_PROT_MASK(MLX5E_1000BASE_CX_SGMII))) {
697 			return PORT_FIBRE;
698 	}
699 
700 	if (eth_proto & (MLX5E_PROT_MASK(MLX5E_40GBASE_CR4)
701 			 | MLX5E_PROT_MASK(MLX5E_10GBASE_CR)
702 			 | MLX5E_PROT_MASK(MLX5E_100GBASE_CR4))) {
703 			return PORT_DA;
704 	}
705 
706 	if (eth_proto & (MLX5E_PROT_MASK(MLX5E_10GBASE_KX4)
707 			 | MLX5E_PROT_MASK(MLX5E_10GBASE_KR)
708 			 | MLX5E_PROT_MASK(MLX5E_40GBASE_KR4)
709 			 | MLX5E_PROT_MASK(MLX5E_100GBASE_KR4))) {
710 			return PORT_NONE;
711 	}
712 
713 	return PORT_OTHER;
714 }
715 
716 static void get_lp_advertising(u32 eth_proto_lp,
717 			       struct ethtool_link_ksettings *link_ksettings)
718 {
719 	unsigned long *lp_advertising = link_ksettings->link_modes.lp_advertising;
720 
721 	ptys2ethtool_adver_link(lp_advertising, eth_proto_lp);
722 }
723 
724 static int mlx5e_get_link_ksettings(struct net_device *netdev,
725 				    struct ethtool_link_ksettings *link_ksettings)
726 {
727 	struct mlx5e_priv *priv    = netdev_priv(netdev);
728 	struct mlx5_core_dev *mdev = priv->mdev;
729 	u32 out[MLX5_ST_SZ_DW(ptys_reg)];
730 	u32 eth_proto_cap;
731 	u32 eth_proto_admin;
732 	u32 eth_proto_lp;
733 	u32 eth_proto_oper;
734 	u8 an_disable_admin;
735 	u8 an_status;
736 	int err;
737 
738 	err = mlx5_query_port_ptys(mdev, out, sizeof(out), MLX5_PTYS_EN, 1);
739 
740 	if (err) {
741 		netdev_err(netdev, "%s: query port ptys failed: %d\n",
742 			   __func__, err);
743 		goto err_query_ptys;
744 	}
745 
746 	eth_proto_cap    = MLX5_GET(ptys_reg, out, eth_proto_capability);
747 	eth_proto_admin  = MLX5_GET(ptys_reg, out, eth_proto_admin);
748 	eth_proto_oper   = MLX5_GET(ptys_reg, out, eth_proto_oper);
749 	eth_proto_lp     = MLX5_GET(ptys_reg, out, eth_proto_lp_advertise);
750 	an_disable_admin = MLX5_GET(ptys_reg, out, an_disable_admin);
751 	an_status        = MLX5_GET(ptys_reg, out, an_status);
752 
753 	ethtool_link_ksettings_zero_link_mode(link_ksettings, supported);
754 	ethtool_link_ksettings_zero_link_mode(link_ksettings, advertising);
755 
756 	get_supported(eth_proto_cap, link_ksettings);
757 	get_advertising(eth_proto_admin, 0, 0, link_ksettings);
758 	get_speed_duplex(netdev, eth_proto_oper, link_ksettings);
759 
760 	eth_proto_oper = eth_proto_oper ? eth_proto_oper : eth_proto_cap;
761 
762 	link_ksettings->base.port = get_connector_port(eth_proto_oper);
763 	get_lp_advertising(eth_proto_lp, link_ksettings);
764 
765 	if (an_status == MLX5_AN_COMPLETE)
766 		ethtool_link_ksettings_add_link_mode(link_ksettings,
767 						     lp_advertising, Autoneg);
768 
769 	link_ksettings->base.autoneg = an_disable_admin ? AUTONEG_DISABLE :
770 							  AUTONEG_ENABLE;
771 	ethtool_link_ksettings_add_link_mode(link_ksettings, supported,
772 					     Autoneg);
773 	if (!an_disable_admin)
774 		ethtool_link_ksettings_add_link_mode(link_ksettings,
775 						     advertising, Autoneg);
776 
777 err_query_ptys:
778 	return err;
779 }
780 
781 static u32 mlx5e_ethtool2ptys_adver_link(const unsigned long *link_modes)
782 {
783 	u32 i, ptys_modes = 0;
784 
785 	for (i = 0; i < MLX5E_LINK_MODES_NUMBER; ++i) {
786 		if (bitmap_intersects(ptys2ethtool_table[i].advertised,
787 				      link_modes,
788 				      __ETHTOOL_LINK_MODE_MASK_NBITS))
789 			ptys_modes |= MLX5E_PROT_MASK(i);
790 	}
791 
792 	return ptys_modes;
793 }
794 
795 static u32 mlx5e_ethtool2ptys_speed_link(u32 speed)
796 {
797 	u32 i, speed_links = 0;
798 
799 	for (i = 0; i < MLX5E_LINK_MODES_NUMBER; ++i) {
800 		if (ptys2ethtool_table[i].speed == speed)
801 			speed_links |= MLX5E_PROT_MASK(i);
802 	}
803 
804 	return speed_links;
805 }
806 
807 static int mlx5e_set_link_ksettings(struct net_device *netdev,
808 				    const struct ethtool_link_ksettings *link_ksettings)
809 {
810 	struct mlx5e_priv *priv    = netdev_priv(netdev);
811 	struct mlx5_core_dev *mdev = priv->mdev;
812 	u32 eth_proto_cap, eth_proto_admin;
813 	bool an_changes = false;
814 	u8 an_disable_admin;
815 	u8 an_disable_cap;
816 	bool an_disable;
817 	u32 link_modes;
818 	u8 an_status;
819 	u32 speed;
820 	int err;
821 
822 	speed = link_ksettings->base.speed;
823 
824 	link_modes = link_ksettings->base.autoneg == AUTONEG_ENABLE ?
825 		mlx5e_ethtool2ptys_adver_link(link_ksettings->link_modes.advertising) :
826 		mlx5e_ethtool2ptys_speed_link(speed);
827 
828 	err = mlx5_query_port_proto_cap(mdev, &eth_proto_cap, MLX5_PTYS_EN);
829 	if (err) {
830 		netdev_err(netdev, "%s: query port eth proto cap failed: %d\n",
831 			   __func__, err);
832 		goto out;
833 	}
834 
835 	link_modes = link_modes & eth_proto_cap;
836 	if (!link_modes) {
837 		netdev_err(netdev, "%s: Not supported link mode(s) requested",
838 			   __func__);
839 		err = -EINVAL;
840 		goto out;
841 	}
842 
843 	err = mlx5_query_port_proto_admin(mdev, &eth_proto_admin, MLX5_PTYS_EN);
844 	if (err) {
845 		netdev_err(netdev, "%s: query port eth proto admin failed: %d\n",
846 			   __func__, err);
847 		goto out;
848 	}
849 
850 	mlx5_query_port_autoneg(mdev, MLX5_PTYS_EN, &an_status,
851 				&an_disable_cap, &an_disable_admin);
852 
853 	an_disable = link_ksettings->base.autoneg == AUTONEG_DISABLE;
854 	an_changes = ((!an_disable && an_disable_admin) ||
855 		      (an_disable && !an_disable_admin));
856 
857 	if (!an_changes && link_modes == eth_proto_admin)
858 		goto out;
859 
860 	mlx5_set_port_ptys(mdev, an_disable, link_modes, MLX5_PTYS_EN);
861 	mlx5_toggle_port_link(mdev);
862 
863 out:
864 	return err;
865 }
866 
867 static u32 mlx5e_get_rxfh_key_size(struct net_device *netdev)
868 {
869 	struct mlx5e_priv *priv = netdev_priv(netdev);
870 
871 	return sizeof(priv->params.toeplitz_hash_key);
872 }
873 
874 static u32 mlx5e_get_rxfh_indir_size(struct net_device *netdev)
875 {
876 	return MLX5E_INDIR_RQT_SIZE;
877 }
878 
879 static int mlx5e_get_rxfh(struct net_device *netdev, u32 *indir, u8 *key,
880 			  u8 *hfunc)
881 {
882 	struct mlx5e_priv *priv = netdev_priv(netdev);
883 
884 	if (indir)
885 		memcpy(indir, priv->params.indirection_rqt,
886 		       sizeof(priv->params.indirection_rqt));
887 
888 	if (key)
889 		memcpy(key, priv->params.toeplitz_hash_key,
890 		       sizeof(priv->params.toeplitz_hash_key));
891 
892 	if (hfunc)
893 		*hfunc = priv->params.rss_hfunc;
894 
895 	return 0;
896 }
897 
898 static void mlx5e_modify_tirs_hash(struct mlx5e_priv *priv, void *in, int inlen)
899 {
900 	struct mlx5_core_dev *mdev = priv->mdev;
901 	void *tirc = MLX5_ADDR_OF(modify_tir_in, in, ctx);
902 	int i;
903 
904 	MLX5_SET(modify_tir_in, in, bitmask.hash, 1);
905 	mlx5e_build_tir_ctx_hash(tirc, priv);
906 
907 	for (i = 0; i < MLX5E_NUM_INDIR_TIRS; i++)
908 		mlx5_core_modify_tir(mdev, priv->indir_tir[i].tirn, in, inlen);
909 }
910 
911 static int mlx5e_set_rxfh(struct net_device *dev, const u32 *indir,
912 			  const u8 *key, const u8 hfunc)
913 {
914 	struct mlx5e_priv *priv = netdev_priv(dev);
915 	int inlen = MLX5_ST_SZ_BYTES(modify_tir_in);
916 	void *in;
917 
918 	if ((hfunc != ETH_RSS_HASH_NO_CHANGE) &&
919 	    (hfunc != ETH_RSS_HASH_XOR) &&
920 	    (hfunc != ETH_RSS_HASH_TOP))
921 		return -EINVAL;
922 
923 	in = mlx5_vzalloc(inlen);
924 	if (!in)
925 		return -ENOMEM;
926 
927 	mutex_lock(&priv->state_lock);
928 
929 	if (indir) {
930 		u32 rqtn = priv->indir_rqt.rqtn;
931 
932 		memcpy(priv->params.indirection_rqt, indir,
933 		       sizeof(priv->params.indirection_rqt));
934 		mlx5e_redirect_rqt(priv, rqtn, MLX5E_INDIR_RQT_SIZE, 0);
935 	}
936 
937 	if (key)
938 		memcpy(priv->params.toeplitz_hash_key, key,
939 		       sizeof(priv->params.toeplitz_hash_key));
940 
941 	if (hfunc != ETH_RSS_HASH_NO_CHANGE)
942 		priv->params.rss_hfunc = hfunc;
943 
944 	mlx5e_modify_tirs_hash(priv, in, inlen);
945 
946 	mutex_unlock(&priv->state_lock);
947 
948 	kvfree(in);
949 
950 	return 0;
951 }
952 
953 static int mlx5e_get_rxnfc(struct net_device *netdev,
954 			   struct ethtool_rxnfc *info, u32 *rule_locs)
955 {
956 	struct mlx5e_priv *priv = netdev_priv(netdev);
957 	int err = 0;
958 
959 	switch (info->cmd) {
960 	case ETHTOOL_GRXRINGS:
961 		info->data = priv->params.num_channels;
962 		break;
963 	case ETHTOOL_GRXCLSRLCNT:
964 		info->rule_cnt = priv->fs.ethtool.tot_num_rules;
965 		break;
966 	case ETHTOOL_GRXCLSRULE:
967 		err = mlx5e_ethtool_get_flow(priv, info, info->fs.location);
968 		break;
969 	case ETHTOOL_GRXCLSRLALL:
970 		err = mlx5e_ethtool_get_all_flows(priv, info, rule_locs);
971 		break;
972 	default:
973 		err = -EOPNOTSUPP;
974 		break;
975 	}
976 
977 	return err;
978 }
979 
980 static int mlx5e_get_tunable(struct net_device *dev,
981 			     const struct ethtool_tunable *tuna,
982 			     void *data)
983 {
984 	const struct mlx5e_priv *priv = netdev_priv(dev);
985 	int err = 0;
986 
987 	switch (tuna->id) {
988 	case ETHTOOL_TX_COPYBREAK:
989 		*(u32 *)data = priv->params.tx_max_inline;
990 		break;
991 	default:
992 		err = -EINVAL;
993 		break;
994 	}
995 
996 	return err;
997 }
998 
999 static int mlx5e_set_tunable(struct net_device *dev,
1000 			     const struct ethtool_tunable *tuna,
1001 			     const void *data)
1002 {
1003 	struct mlx5e_priv *priv = netdev_priv(dev);
1004 	struct mlx5_core_dev *mdev = priv->mdev;
1005 	bool was_opened;
1006 	u32 val;
1007 	int err = 0;
1008 
1009 	switch (tuna->id) {
1010 	case ETHTOOL_TX_COPYBREAK:
1011 		val = *(u32 *)data;
1012 		if (val > mlx5e_get_max_inline_cap(mdev)) {
1013 			err = -EINVAL;
1014 			break;
1015 		}
1016 
1017 		mutex_lock(&priv->state_lock);
1018 
1019 		was_opened = test_bit(MLX5E_STATE_OPENED, &priv->state);
1020 		if (was_opened)
1021 			mlx5e_close_locked(dev);
1022 
1023 		priv->params.tx_max_inline = val;
1024 
1025 		if (was_opened)
1026 			err = mlx5e_open_locked(dev);
1027 
1028 		mutex_unlock(&priv->state_lock);
1029 		break;
1030 	default:
1031 		err = -EINVAL;
1032 		break;
1033 	}
1034 
1035 	return err;
1036 }
1037 
1038 static void mlx5e_get_pauseparam(struct net_device *netdev,
1039 				 struct ethtool_pauseparam *pauseparam)
1040 {
1041 	struct mlx5e_priv *priv    = netdev_priv(netdev);
1042 	struct mlx5_core_dev *mdev = priv->mdev;
1043 	int err;
1044 
1045 	err = mlx5_query_port_pause(mdev, &pauseparam->rx_pause,
1046 				    &pauseparam->tx_pause);
1047 	if (err) {
1048 		netdev_err(netdev, "%s: mlx5_query_port_pause failed:0x%x\n",
1049 			   __func__, err);
1050 	}
1051 }
1052 
1053 static int mlx5e_set_pauseparam(struct net_device *netdev,
1054 				struct ethtool_pauseparam *pauseparam)
1055 {
1056 	struct mlx5e_priv *priv    = netdev_priv(netdev);
1057 	struct mlx5_core_dev *mdev = priv->mdev;
1058 	int err;
1059 
1060 	if (pauseparam->autoneg)
1061 		return -EINVAL;
1062 
1063 	err = mlx5_set_port_pause(mdev,
1064 				  pauseparam->rx_pause ? 1 : 0,
1065 				  pauseparam->tx_pause ? 1 : 0);
1066 	if (err) {
1067 		netdev_err(netdev, "%s: mlx5_set_port_pause failed:0x%x\n",
1068 			   __func__, err);
1069 	}
1070 
1071 	return err;
1072 }
1073 
1074 static int mlx5e_get_ts_info(struct net_device *dev,
1075 			     struct ethtool_ts_info *info)
1076 {
1077 	struct mlx5e_priv *priv = netdev_priv(dev);
1078 	int ret;
1079 
1080 	ret = ethtool_op_get_ts_info(dev, info);
1081 	if (ret)
1082 		return ret;
1083 
1084 	info->phc_index = priv->tstamp.ptp ?
1085 			  ptp_clock_index(priv->tstamp.ptp) : -1;
1086 
1087 	if (!MLX5_CAP_GEN(priv->mdev, device_frequency_khz))
1088 		return 0;
1089 
1090 	info->so_timestamping |= SOF_TIMESTAMPING_TX_HARDWARE |
1091 				 SOF_TIMESTAMPING_RX_HARDWARE |
1092 				 SOF_TIMESTAMPING_RAW_HARDWARE;
1093 
1094 	info->tx_types = (BIT(1) << HWTSTAMP_TX_OFF) |
1095 			 (BIT(1) << HWTSTAMP_TX_ON);
1096 
1097 	info->rx_filters = (BIT(1) << HWTSTAMP_FILTER_NONE) |
1098 			   (BIT(1) << HWTSTAMP_FILTER_ALL);
1099 
1100 	return 0;
1101 }
1102 
1103 static __u32 mlx5e_get_wol_supported(struct mlx5_core_dev *mdev)
1104 {
1105 	__u32 ret = 0;
1106 
1107 	if (MLX5_CAP_GEN(mdev, wol_g))
1108 		ret |= WAKE_MAGIC;
1109 
1110 	if (MLX5_CAP_GEN(mdev, wol_s))
1111 		ret |= WAKE_MAGICSECURE;
1112 
1113 	if (MLX5_CAP_GEN(mdev, wol_a))
1114 		ret |= WAKE_ARP;
1115 
1116 	if (MLX5_CAP_GEN(mdev, wol_b))
1117 		ret |= WAKE_BCAST;
1118 
1119 	if (MLX5_CAP_GEN(mdev, wol_m))
1120 		ret |= WAKE_MCAST;
1121 
1122 	if (MLX5_CAP_GEN(mdev, wol_u))
1123 		ret |= WAKE_UCAST;
1124 
1125 	if (MLX5_CAP_GEN(mdev, wol_p))
1126 		ret |= WAKE_PHY;
1127 
1128 	return ret;
1129 }
1130 
1131 static __u32 mlx5e_refomrat_wol_mode_mlx5_to_linux(u8 mode)
1132 {
1133 	__u32 ret = 0;
1134 
1135 	if (mode & MLX5_WOL_MAGIC)
1136 		ret |= WAKE_MAGIC;
1137 
1138 	if (mode & MLX5_WOL_SECURED_MAGIC)
1139 		ret |= WAKE_MAGICSECURE;
1140 
1141 	if (mode & MLX5_WOL_ARP)
1142 		ret |= WAKE_ARP;
1143 
1144 	if (mode & MLX5_WOL_BROADCAST)
1145 		ret |= WAKE_BCAST;
1146 
1147 	if (mode & MLX5_WOL_MULTICAST)
1148 		ret |= WAKE_MCAST;
1149 
1150 	if (mode & MLX5_WOL_UNICAST)
1151 		ret |= WAKE_UCAST;
1152 
1153 	if (mode & MLX5_WOL_PHY_ACTIVITY)
1154 		ret |= WAKE_PHY;
1155 
1156 	return ret;
1157 }
1158 
1159 static u8 mlx5e_refomrat_wol_mode_linux_to_mlx5(__u32 mode)
1160 {
1161 	u8 ret = 0;
1162 
1163 	if (mode & WAKE_MAGIC)
1164 		ret |= MLX5_WOL_MAGIC;
1165 
1166 	if (mode & WAKE_MAGICSECURE)
1167 		ret |= MLX5_WOL_SECURED_MAGIC;
1168 
1169 	if (mode & WAKE_ARP)
1170 		ret |= MLX5_WOL_ARP;
1171 
1172 	if (mode & WAKE_BCAST)
1173 		ret |= MLX5_WOL_BROADCAST;
1174 
1175 	if (mode & WAKE_MCAST)
1176 		ret |= MLX5_WOL_MULTICAST;
1177 
1178 	if (mode & WAKE_UCAST)
1179 		ret |= MLX5_WOL_UNICAST;
1180 
1181 	if (mode & WAKE_PHY)
1182 		ret |= MLX5_WOL_PHY_ACTIVITY;
1183 
1184 	return ret;
1185 }
1186 
1187 static void mlx5e_get_wol(struct net_device *netdev,
1188 			  struct ethtool_wolinfo *wol)
1189 {
1190 	struct mlx5e_priv *priv = netdev_priv(netdev);
1191 	struct mlx5_core_dev *mdev = priv->mdev;
1192 	u8 mlx5_wol_mode;
1193 	int err;
1194 
1195 	memset(wol, 0, sizeof(*wol));
1196 
1197 	wol->supported = mlx5e_get_wol_supported(mdev);
1198 	if (!wol->supported)
1199 		return;
1200 
1201 	err = mlx5_query_port_wol(mdev, &mlx5_wol_mode);
1202 	if (err)
1203 		return;
1204 
1205 	wol->wolopts = mlx5e_refomrat_wol_mode_mlx5_to_linux(mlx5_wol_mode);
1206 }
1207 
1208 static int mlx5e_set_wol(struct net_device *netdev, struct ethtool_wolinfo *wol)
1209 {
1210 	struct mlx5e_priv *priv = netdev_priv(netdev);
1211 	struct mlx5_core_dev *mdev = priv->mdev;
1212 	__u32 wol_supported = mlx5e_get_wol_supported(mdev);
1213 	u32 mlx5_wol_mode;
1214 
1215 	if (!wol_supported)
1216 		return -ENOTSUPP;
1217 
1218 	if (wol->wolopts & ~wol_supported)
1219 		return -EINVAL;
1220 
1221 	mlx5_wol_mode = mlx5e_refomrat_wol_mode_linux_to_mlx5(wol->wolopts);
1222 
1223 	return mlx5_set_port_wol(mdev, mlx5_wol_mode);
1224 }
1225 
1226 static int mlx5e_set_phys_id(struct net_device *dev,
1227 			     enum ethtool_phys_id_state state)
1228 {
1229 	struct mlx5e_priv *priv = netdev_priv(dev);
1230 	struct mlx5_core_dev *mdev = priv->mdev;
1231 	u16 beacon_duration;
1232 
1233 	if (!MLX5_CAP_GEN(mdev, beacon_led))
1234 		return -EOPNOTSUPP;
1235 
1236 	switch (state) {
1237 	case ETHTOOL_ID_ACTIVE:
1238 		beacon_duration = MLX5_BEACON_DURATION_INF;
1239 		break;
1240 	case ETHTOOL_ID_INACTIVE:
1241 		beacon_duration = MLX5_BEACON_DURATION_OFF;
1242 		break;
1243 	default:
1244 		return -EOPNOTSUPP;
1245 	}
1246 
1247 	return mlx5_set_port_beacon(mdev, beacon_duration);
1248 }
1249 
1250 static int mlx5e_get_module_info(struct net_device *netdev,
1251 				 struct ethtool_modinfo *modinfo)
1252 {
1253 	struct mlx5e_priv *priv = netdev_priv(netdev);
1254 	struct mlx5_core_dev *dev = priv->mdev;
1255 	int size_read = 0;
1256 	u8 data[4];
1257 
1258 	size_read = mlx5_query_module_eeprom(dev, 0, 2, data);
1259 	if (size_read < 2)
1260 		return -EIO;
1261 
1262 	/* data[0] = identifier byte */
1263 	switch (data[0]) {
1264 	case MLX5_MODULE_ID_QSFP:
1265 		modinfo->type       = ETH_MODULE_SFF_8436;
1266 		modinfo->eeprom_len = ETH_MODULE_SFF_8436_LEN;
1267 		break;
1268 	case MLX5_MODULE_ID_QSFP_PLUS:
1269 	case MLX5_MODULE_ID_QSFP28:
1270 		/* data[1] = revision id */
1271 		if (data[0] == MLX5_MODULE_ID_QSFP28 || data[1] >= 0x3) {
1272 			modinfo->type       = ETH_MODULE_SFF_8636;
1273 			modinfo->eeprom_len = ETH_MODULE_SFF_8636_LEN;
1274 		} else {
1275 			modinfo->type       = ETH_MODULE_SFF_8436;
1276 			modinfo->eeprom_len = ETH_MODULE_SFF_8436_LEN;
1277 		}
1278 		break;
1279 	case MLX5_MODULE_ID_SFP:
1280 		modinfo->type       = ETH_MODULE_SFF_8472;
1281 		modinfo->eeprom_len = ETH_MODULE_SFF_8472_LEN;
1282 		break;
1283 	default:
1284 		netdev_err(priv->netdev, "%s: cable type not recognized:0x%x\n",
1285 			   __func__, data[0]);
1286 		return -EINVAL;
1287 	}
1288 
1289 	return 0;
1290 }
1291 
1292 static int mlx5e_get_module_eeprom(struct net_device *netdev,
1293 				   struct ethtool_eeprom *ee,
1294 				   u8 *data)
1295 {
1296 	struct mlx5e_priv *priv = netdev_priv(netdev);
1297 	struct mlx5_core_dev *mdev = priv->mdev;
1298 	int offset = ee->offset;
1299 	int size_read;
1300 	int i = 0;
1301 
1302 	if (!ee->len)
1303 		return -EINVAL;
1304 
1305 	memset(data, 0, ee->len);
1306 
1307 	while (i < ee->len) {
1308 		size_read = mlx5_query_module_eeprom(mdev, offset, ee->len - i,
1309 						     data + i);
1310 
1311 		if (!size_read)
1312 			/* Done reading */
1313 			return 0;
1314 
1315 		if (size_read < 0) {
1316 			netdev_err(priv->netdev, "%s: mlx5_query_eeprom failed:0x%x\n",
1317 				   __func__, size_read);
1318 			return 0;
1319 		}
1320 
1321 		i += size_read;
1322 		offset += size_read;
1323 	}
1324 
1325 	return 0;
1326 }
1327 
1328 typedef int (*mlx5e_pflag_handler)(struct net_device *netdev, bool enable);
1329 
1330 static int set_pflag_rx_cqe_based_moder(struct net_device *netdev, bool enable)
1331 {
1332 	struct mlx5e_priv *priv = netdev_priv(netdev);
1333 	struct mlx5_core_dev *mdev = priv->mdev;
1334 	bool rx_mode_changed;
1335 	u8 rx_cq_period_mode;
1336 	int err = 0;
1337 	bool reset;
1338 
1339 	rx_cq_period_mode = enable ?
1340 		MLX5_CQ_PERIOD_MODE_START_FROM_CQE :
1341 		MLX5_CQ_PERIOD_MODE_START_FROM_EQE;
1342 	rx_mode_changed = rx_cq_period_mode != priv->params.rx_cq_period_mode;
1343 
1344 	if (rx_cq_period_mode == MLX5_CQ_PERIOD_MODE_START_FROM_CQE &&
1345 	    !MLX5_CAP_GEN(mdev, cq_period_start_from_cqe))
1346 		return -ENOTSUPP;
1347 
1348 	if (!rx_mode_changed)
1349 		return 0;
1350 
1351 	reset = test_bit(MLX5E_STATE_OPENED, &priv->state);
1352 	if (reset)
1353 		mlx5e_close_locked(netdev);
1354 
1355 	mlx5e_set_rx_cq_mode_params(&priv->params, rx_cq_period_mode);
1356 
1357 	if (reset)
1358 		err = mlx5e_open_locked(netdev);
1359 
1360 	return err;
1361 }
1362 
1363 static int mlx5e_handle_pflag(struct net_device *netdev,
1364 			      u32 wanted_flags,
1365 			      enum mlx5e_priv_flag flag,
1366 			      mlx5e_pflag_handler pflag_handler)
1367 {
1368 	struct mlx5e_priv *priv = netdev_priv(netdev);
1369 	bool enable = !!(wanted_flags & flag);
1370 	u32 changes = wanted_flags ^ priv->pflags;
1371 	int err;
1372 
1373 	if (!(changes & flag))
1374 		return 0;
1375 
1376 	err = pflag_handler(netdev, enable);
1377 	if (err) {
1378 		netdev_err(netdev, "%s private flag 0x%x failed err %d\n",
1379 			   enable ? "Enable" : "Disable", flag, err);
1380 		return err;
1381 	}
1382 
1383 	MLX5E_SET_PRIV_FLAG(priv, flag, enable);
1384 	return 0;
1385 }
1386 
1387 static int mlx5e_set_priv_flags(struct net_device *netdev, u32 pflags)
1388 {
1389 	struct mlx5e_priv *priv = netdev_priv(netdev);
1390 	int err;
1391 
1392 	mutex_lock(&priv->state_lock);
1393 
1394 	err = mlx5e_handle_pflag(netdev, pflags,
1395 				 MLX5E_PFLAG_RX_CQE_BASED_MODER,
1396 				 set_pflag_rx_cqe_based_moder);
1397 
1398 	mutex_unlock(&priv->state_lock);
1399 	return err ? -EINVAL : 0;
1400 }
1401 
1402 static u32 mlx5e_get_priv_flags(struct net_device *netdev)
1403 {
1404 	struct mlx5e_priv *priv = netdev_priv(netdev);
1405 
1406 	return priv->pflags;
1407 }
1408 
1409 static int mlx5e_set_rxnfc(struct net_device *dev, struct ethtool_rxnfc *cmd)
1410 {
1411 	int err = 0;
1412 	struct mlx5e_priv *priv = netdev_priv(dev);
1413 
1414 	switch (cmd->cmd) {
1415 	case ETHTOOL_SRXCLSRLINS:
1416 		err = mlx5e_ethtool_flow_replace(priv, &cmd->fs);
1417 		break;
1418 	case ETHTOOL_SRXCLSRLDEL:
1419 		err = mlx5e_ethtool_flow_remove(priv, cmd->fs.location);
1420 		break;
1421 	default:
1422 		err = -EOPNOTSUPP;
1423 		break;
1424 	}
1425 
1426 	return err;
1427 }
1428 
1429 const struct ethtool_ops mlx5e_ethtool_ops = {
1430 	.get_drvinfo       = mlx5e_get_drvinfo,
1431 	.get_link          = ethtool_op_get_link,
1432 	.get_strings       = mlx5e_get_strings,
1433 	.get_sset_count    = mlx5e_get_sset_count,
1434 	.get_ethtool_stats = mlx5e_get_ethtool_stats,
1435 	.get_ringparam     = mlx5e_get_ringparam,
1436 	.set_ringparam     = mlx5e_set_ringparam,
1437 	.get_channels      = mlx5e_get_channels,
1438 	.set_channels      = mlx5e_set_channels,
1439 	.get_coalesce      = mlx5e_get_coalesce,
1440 	.set_coalesce      = mlx5e_set_coalesce,
1441 	.get_link_ksettings  = mlx5e_get_link_ksettings,
1442 	.set_link_ksettings  = mlx5e_set_link_ksettings,
1443 	.get_rxfh_key_size   = mlx5e_get_rxfh_key_size,
1444 	.get_rxfh_indir_size = mlx5e_get_rxfh_indir_size,
1445 	.get_rxfh          = mlx5e_get_rxfh,
1446 	.set_rxfh          = mlx5e_set_rxfh,
1447 	.get_rxnfc         = mlx5e_get_rxnfc,
1448 	.set_rxnfc         = mlx5e_set_rxnfc,
1449 	.get_tunable       = mlx5e_get_tunable,
1450 	.set_tunable       = mlx5e_set_tunable,
1451 	.get_pauseparam    = mlx5e_get_pauseparam,
1452 	.set_pauseparam    = mlx5e_set_pauseparam,
1453 	.get_ts_info       = mlx5e_get_ts_info,
1454 	.set_phys_id       = mlx5e_set_phys_id,
1455 	.get_wol	   = mlx5e_get_wol,
1456 	.set_wol	   = mlx5e_set_wol,
1457 	.get_module_info   = mlx5e_get_module_info,
1458 	.get_module_eeprom = mlx5e_get_module_eeprom,
1459 	.get_priv_flags    = mlx5e_get_priv_flags,
1460 	.set_priv_flags    = mlx5e_set_priv_flags
1461 };
1462