1 /******************************************************************************
2
3 Copyright (c) 2013-2018, Intel Corporation
4 All rights reserved.
5
6 Redistribution and use in source and binary forms, with or without
7 modification, are permitted provided that the following conditions are met:
8
9 1. Redistributions of source code must retain the above copyright notice,
10 this list of conditions and the following disclaimer.
11
12 2. Redistributions in binary form must reproduce the above copyright
13 notice, this list of conditions and the following disclaimer in the
14 documentation and/or other materials provided with the distribution.
15
16 3. Neither the name of the Intel Corporation nor the names of its
17 contributors may be used to endorse or promote products derived from
18 this software without specific prior written permission.
19
20 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
21 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23 ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
24 LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
25 CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
26 SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
27 INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
28 CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
29 ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
30 POSSIBILITY OF SUCH DAMAGE.
31
32 ******************************************************************************/
33 /*$FreeBSD$*/
34
35 #include "i40e_type.h"
36 #include "i40e_adminq.h"
37 #include "i40e_prototype.h"
38 #include "virtchnl.h"
39
40
41 /**
42 * i40e_set_mac_type - Sets MAC type
43 * @hw: pointer to the HW structure
44 *
45 * This function sets the mac type of the adapter based on the
46 * vendor ID and device ID stored in the hw structure.
47 **/
i40e_set_mac_type(struct i40e_hw * hw)48 enum i40e_status_code i40e_set_mac_type(struct i40e_hw *hw)
49 {
50 enum i40e_status_code status = I40E_SUCCESS;
51
52 DEBUGFUNC("i40e_set_mac_type\n");
53
54 if (hw->vendor_id == I40E_INTEL_VENDOR_ID) {
55 switch (hw->device_id) {
56 case I40E_DEV_ID_SFP_XL710:
57 case I40E_DEV_ID_QEMU:
58 case I40E_DEV_ID_KX_B:
59 case I40E_DEV_ID_KX_C:
60 case I40E_DEV_ID_QSFP_A:
61 case I40E_DEV_ID_QSFP_B:
62 case I40E_DEV_ID_QSFP_C:
63 case I40E_DEV_ID_10G_BASE_T:
64 case I40E_DEV_ID_10G_BASE_T4:
65 case I40E_DEV_ID_20G_KR2:
66 case I40E_DEV_ID_20G_KR2_A:
67 case I40E_DEV_ID_25G_B:
68 case I40E_DEV_ID_25G_SFP28:
69 hw->mac.type = I40E_MAC_XL710;
70 break;
71 case I40E_DEV_ID_KX_X722:
72 case I40E_DEV_ID_QSFP_X722:
73 case I40E_DEV_ID_SFP_X722:
74 case I40E_DEV_ID_1G_BASE_T_X722:
75 case I40E_DEV_ID_10G_BASE_T_X722:
76 case I40E_DEV_ID_SFP_I_X722:
77 hw->mac.type = I40E_MAC_X722;
78 break;
79 case I40E_DEV_ID_X722_VF:
80 hw->mac.type = I40E_MAC_X722_VF;
81 break;
82 case I40E_DEV_ID_VF:
83 case I40E_DEV_ID_VF_HV:
84 case I40E_DEV_ID_ADAPTIVE_VF:
85 hw->mac.type = I40E_MAC_VF;
86 break;
87 default:
88 hw->mac.type = I40E_MAC_GENERIC;
89 break;
90 }
91 } else {
92 status = I40E_ERR_DEVICE_NOT_SUPPORTED;
93 }
94
95 DEBUGOUT2("i40e_set_mac_type found mac: %d, returns: %d\n",
96 hw->mac.type, status);
97 return status;
98 }
99
100 /**
101 * i40e_aq_str - convert AQ err code to a string
102 * @hw: pointer to the HW structure
103 * @aq_err: the AQ error code to convert
104 **/
i40e_aq_str(struct i40e_hw * hw,enum i40e_admin_queue_err aq_err)105 const char *i40e_aq_str(struct i40e_hw *hw, enum i40e_admin_queue_err aq_err)
106 {
107 switch (aq_err) {
108 case I40E_AQ_RC_OK:
109 return "OK";
110 case I40E_AQ_RC_EPERM:
111 return "I40E_AQ_RC_EPERM";
112 case I40E_AQ_RC_ENOENT:
113 return "I40E_AQ_RC_ENOENT";
114 case I40E_AQ_RC_ESRCH:
115 return "I40E_AQ_RC_ESRCH";
116 case I40E_AQ_RC_EINTR:
117 return "I40E_AQ_RC_EINTR";
118 case I40E_AQ_RC_EIO:
119 return "I40E_AQ_RC_EIO";
120 case I40E_AQ_RC_ENXIO:
121 return "I40E_AQ_RC_ENXIO";
122 case I40E_AQ_RC_E2BIG:
123 return "I40E_AQ_RC_E2BIG";
124 case I40E_AQ_RC_EAGAIN:
125 return "I40E_AQ_RC_EAGAIN";
126 case I40E_AQ_RC_ENOMEM:
127 return "I40E_AQ_RC_ENOMEM";
128 case I40E_AQ_RC_EACCES:
129 return "I40E_AQ_RC_EACCES";
130 case I40E_AQ_RC_EFAULT:
131 return "I40E_AQ_RC_EFAULT";
132 case I40E_AQ_RC_EBUSY:
133 return "I40E_AQ_RC_EBUSY";
134 case I40E_AQ_RC_EEXIST:
135 return "I40E_AQ_RC_EEXIST";
136 case I40E_AQ_RC_EINVAL:
137 return "I40E_AQ_RC_EINVAL";
138 case I40E_AQ_RC_ENOTTY:
139 return "I40E_AQ_RC_ENOTTY";
140 case I40E_AQ_RC_ENOSPC:
141 return "I40E_AQ_RC_ENOSPC";
142 case I40E_AQ_RC_ENOSYS:
143 return "I40E_AQ_RC_ENOSYS";
144 case I40E_AQ_RC_ERANGE:
145 return "I40E_AQ_RC_ERANGE";
146 case I40E_AQ_RC_EFLUSHED:
147 return "I40E_AQ_RC_EFLUSHED";
148 case I40E_AQ_RC_BAD_ADDR:
149 return "I40E_AQ_RC_BAD_ADDR";
150 case I40E_AQ_RC_EMODE:
151 return "I40E_AQ_RC_EMODE";
152 case I40E_AQ_RC_EFBIG:
153 return "I40E_AQ_RC_EFBIG";
154 }
155
156 snprintf(hw->err_str, sizeof(hw->err_str), "%d", aq_err);
157 return hw->err_str;
158 }
159
160 /**
161 * i40e_stat_str - convert status err code to a string
162 * @hw: pointer to the HW structure
163 * @stat_err: the status error code to convert
164 **/
i40e_stat_str(struct i40e_hw * hw,enum i40e_status_code stat_err)165 const char *i40e_stat_str(struct i40e_hw *hw, enum i40e_status_code stat_err)
166 {
167 switch (stat_err) {
168 case I40E_SUCCESS:
169 return "OK";
170 case I40E_ERR_NVM:
171 return "I40E_ERR_NVM";
172 case I40E_ERR_NVM_CHECKSUM:
173 return "I40E_ERR_NVM_CHECKSUM";
174 case I40E_ERR_PHY:
175 return "I40E_ERR_PHY";
176 case I40E_ERR_CONFIG:
177 return "I40E_ERR_CONFIG";
178 case I40E_ERR_PARAM:
179 return "I40E_ERR_PARAM";
180 case I40E_ERR_MAC_TYPE:
181 return "I40E_ERR_MAC_TYPE";
182 case I40E_ERR_UNKNOWN_PHY:
183 return "I40E_ERR_UNKNOWN_PHY";
184 case I40E_ERR_LINK_SETUP:
185 return "I40E_ERR_LINK_SETUP";
186 case I40E_ERR_ADAPTER_STOPPED:
187 return "I40E_ERR_ADAPTER_STOPPED";
188 case I40E_ERR_INVALID_MAC_ADDR:
189 return "I40E_ERR_INVALID_MAC_ADDR";
190 case I40E_ERR_DEVICE_NOT_SUPPORTED:
191 return "I40E_ERR_DEVICE_NOT_SUPPORTED";
192 case I40E_ERR_MASTER_REQUESTS_PENDING:
193 return "I40E_ERR_MASTER_REQUESTS_PENDING";
194 case I40E_ERR_INVALID_LINK_SETTINGS:
195 return "I40E_ERR_INVALID_LINK_SETTINGS";
196 case I40E_ERR_AUTONEG_NOT_COMPLETE:
197 return "I40E_ERR_AUTONEG_NOT_COMPLETE";
198 case I40E_ERR_RESET_FAILED:
199 return "I40E_ERR_RESET_FAILED";
200 case I40E_ERR_SWFW_SYNC:
201 return "I40E_ERR_SWFW_SYNC";
202 case I40E_ERR_NO_AVAILABLE_VSI:
203 return "I40E_ERR_NO_AVAILABLE_VSI";
204 case I40E_ERR_NO_MEMORY:
205 return "I40E_ERR_NO_MEMORY";
206 case I40E_ERR_BAD_PTR:
207 return "I40E_ERR_BAD_PTR";
208 case I40E_ERR_RING_FULL:
209 return "I40E_ERR_RING_FULL";
210 case I40E_ERR_INVALID_PD_ID:
211 return "I40E_ERR_INVALID_PD_ID";
212 case I40E_ERR_INVALID_QP_ID:
213 return "I40E_ERR_INVALID_QP_ID";
214 case I40E_ERR_INVALID_CQ_ID:
215 return "I40E_ERR_INVALID_CQ_ID";
216 case I40E_ERR_INVALID_CEQ_ID:
217 return "I40E_ERR_INVALID_CEQ_ID";
218 case I40E_ERR_INVALID_AEQ_ID:
219 return "I40E_ERR_INVALID_AEQ_ID";
220 case I40E_ERR_INVALID_SIZE:
221 return "I40E_ERR_INVALID_SIZE";
222 case I40E_ERR_INVALID_ARP_INDEX:
223 return "I40E_ERR_INVALID_ARP_INDEX";
224 case I40E_ERR_INVALID_FPM_FUNC_ID:
225 return "I40E_ERR_INVALID_FPM_FUNC_ID";
226 case I40E_ERR_QP_INVALID_MSG_SIZE:
227 return "I40E_ERR_QP_INVALID_MSG_SIZE";
228 case I40E_ERR_QP_TOOMANY_WRS_POSTED:
229 return "I40E_ERR_QP_TOOMANY_WRS_POSTED";
230 case I40E_ERR_INVALID_FRAG_COUNT:
231 return "I40E_ERR_INVALID_FRAG_COUNT";
232 case I40E_ERR_QUEUE_EMPTY:
233 return "I40E_ERR_QUEUE_EMPTY";
234 case I40E_ERR_INVALID_ALIGNMENT:
235 return "I40E_ERR_INVALID_ALIGNMENT";
236 case I40E_ERR_FLUSHED_QUEUE:
237 return "I40E_ERR_FLUSHED_QUEUE";
238 case I40E_ERR_INVALID_PUSH_PAGE_INDEX:
239 return "I40E_ERR_INVALID_PUSH_PAGE_INDEX";
240 case I40E_ERR_INVALID_IMM_DATA_SIZE:
241 return "I40E_ERR_INVALID_IMM_DATA_SIZE";
242 case I40E_ERR_TIMEOUT:
243 return "I40E_ERR_TIMEOUT";
244 case I40E_ERR_OPCODE_MISMATCH:
245 return "I40E_ERR_OPCODE_MISMATCH";
246 case I40E_ERR_CQP_COMPL_ERROR:
247 return "I40E_ERR_CQP_COMPL_ERROR";
248 case I40E_ERR_INVALID_VF_ID:
249 return "I40E_ERR_INVALID_VF_ID";
250 case I40E_ERR_INVALID_HMCFN_ID:
251 return "I40E_ERR_INVALID_HMCFN_ID";
252 case I40E_ERR_BACKING_PAGE_ERROR:
253 return "I40E_ERR_BACKING_PAGE_ERROR";
254 case I40E_ERR_NO_PBLCHUNKS_AVAILABLE:
255 return "I40E_ERR_NO_PBLCHUNKS_AVAILABLE";
256 case I40E_ERR_INVALID_PBLE_INDEX:
257 return "I40E_ERR_INVALID_PBLE_INDEX";
258 case I40E_ERR_INVALID_SD_INDEX:
259 return "I40E_ERR_INVALID_SD_INDEX";
260 case I40E_ERR_INVALID_PAGE_DESC_INDEX:
261 return "I40E_ERR_INVALID_PAGE_DESC_INDEX";
262 case I40E_ERR_INVALID_SD_TYPE:
263 return "I40E_ERR_INVALID_SD_TYPE";
264 case I40E_ERR_MEMCPY_FAILED:
265 return "I40E_ERR_MEMCPY_FAILED";
266 case I40E_ERR_INVALID_HMC_OBJ_INDEX:
267 return "I40E_ERR_INVALID_HMC_OBJ_INDEX";
268 case I40E_ERR_INVALID_HMC_OBJ_COUNT:
269 return "I40E_ERR_INVALID_HMC_OBJ_COUNT";
270 case I40E_ERR_INVALID_SRQ_ARM_LIMIT:
271 return "I40E_ERR_INVALID_SRQ_ARM_LIMIT";
272 case I40E_ERR_SRQ_ENABLED:
273 return "I40E_ERR_SRQ_ENABLED";
274 case I40E_ERR_ADMIN_QUEUE_ERROR:
275 return "I40E_ERR_ADMIN_QUEUE_ERROR";
276 case I40E_ERR_ADMIN_QUEUE_TIMEOUT:
277 return "I40E_ERR_ADMIN_QUEUE_TIMEOUT";
278 case I40E_ERR_BUF_TOO_SHORT:
279 return "I40E_ERR_BUF_TOO_SHORT";
280 case I40E_ERR_ADMIN_QUEUE_FULL:
281 return "I40E_ERR_ADMIN_QUEUE_FULL";
282 case I40E_ERR_ADMIN_QUEUE_NO_WORK:
283 return "I40E_ERR_ADMIN_QUEUE_NO_WORK";
284 case I40E_ERR_BAD_IWARP_CQE:
285 return "I40E_ERR_BAD_IWARP_CQE";
286 case I40E_ERR_NVM_BLANK_MODE:
287 return "I40E_ERR_NVM_BLANK_MODE";
288 case I40E_ERR_NOT_IMPLEMENTED:
289 return "I40E_ERR_NOT_IMPLEMENTED";
290 case I40E_ERR_PE_DOORBELL_NOT_ENABLED:
291 return "I40E_ERR_PE_DOORBELL_NOT_ENABLED";
292 case I40E_ERR_DIAG_TEST_FAILED:
293 return "I40E_ERR_DIAG_TEST_FAILED";
294 case I40E_ERR_NOT_READY:
295 return "I40E_ERR_NOT_READY";
296 case I40E_NOT_SUPPORTED:
297 return "I40E_NOT_SUPPORTED";
298 case I40E_ERR_FIRMWARE_API_VERSION:
299 return "I40E_ERR_FIRMWARE_API_VERSION";
300 case I40E_ERR_ADMIN_QUEUE_CRITICAL_ERROR:
301 return "I40E_ERR_ADMIN_QUEUE_CRITICAL_ERROR";
302 }
303
304 snprintf(hw->err_str, sizeof(hw->err_str), "%d", stat_err);
305 return hw->err_str;
306 }
307
308 /**
309 * i40e_debug_aq
310 * @hw: debug mask related to admin queue
311 * @mask: debug mask
312 * @desc: pointer to admin queue descriptor
313 * @buffer: pointer to command buffer
314 * @buf_len: max length of buffer
315 *
316 * Dumps debug log about adminq command with descriptor contents.
317 **/
i40e_debug_aq(struct i40e_hw * hw,enum i40e_debug_mask mask,void * desc,void * buffer,u16 buf_len)318 void i40e_debug_aq(struct i40e_hw *hw, enum i40e_debug_mask mask, void *desc,
319 void *buffer, u16 buf_len)
320 {
321 struct i40e_aq_desc *aq_desc = (struct i40e_aq_desc *)desc;
322 u8 *buf = (u8 *)buffer;
323 u16 len;
324 u16 i = 0;
325
326 if ((!(mask & hw->debug_mask)) || (desc == NULL))
327 return;
328
329 len = LE16_TO_CPU(aq_desc->datalen);
330
331 i40e_debug(hw, mask,
332 "AQ CMD: opcode 0x%04X, flags 0x%04X, datalen 0x%04X, retval 0x%04X\n",
333 LE16_TO_CPU(aq_desc->opcode),
334 LE16_TO_CPU(aq_desc->flags),
335 LE16_TO_CPU(aq_desc->datalen),
336 LE16_TO_CPU(aq_desc->retval));
337 i40e_debug(hw, mask, "\tcookie (h,l) 0x%08X 0x%08X\n",
338 LE32_TO_CPU(aq_desc->cookie_high),
339 LE32_TO_CPU(aq_desc->cookie_low));
340 i40e_debug(hw, mask, "\tparam (0,1) 0x%08X 0x%08X\n",
341 LE32_TO_CPU(aq_desc->params.internal.param0),
342 LE32_TO_CPU(aq_desc->params.internal.param1));
343 i40e_debug(hw, mask, "\taddr (h,l) 0x%08X 0x%08X\n",
344 LE32_TO_CPU(aq_desc->params.external.addr_high),
345 LE32_TO_CPU(aq_desc->params.external.addr_low));
346
347 if ((buffer != NULL) && (aq_desc->datalen != 0)) {
348 i40e_debug(hw, mask, "AQ CMD Buffer:\n");
349 if (buf_len < len)
350 len = buf_len;
351 /* write the full 16-byte chunks */
352 for (i = 0; i < (len - 16); i += 16)
353 i40e_debug(hw, mask,
354 "\t0x%04X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X\n",
355 i, buf[i], buf[i+1], buf[i+2], buf[i+3],
356 buf[i+4], buf[i+5], buf[i+6], buf[i+7],
357 buf[i+8], buf[i+9], buf[i+10], buf[i+11],
358 buf[i+12], buf[i+13], buf[i+14], buf[i+15]);
359 /* the most we could have left is 16 bytes, pad with zeros */
360 if (i < len) {
361 char d_buf[16];
362 int j, i_sav;
363
364 i_sav = i;
365 memset(d_buf, 0, sizeof(d_buf));
366 for (j = 0; i < len; j++, i++)
367 d_buf[j] = buf[i];
368 i40e_debug(hw, mask,
369 "\t0x%04X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X\n",
370 i_sav, d_buf[0], d_buf[1], d_buf[2], d_buf[3],
371 d_buf[4], d_buf[5], d_buf[6], d_buf[7],
372 d_buf[8], d_buf[9], d_buf[10], d_buf[11],
373 d_buf[12], d_buf[13], d_buf[14], d_buf[15]);
374 }
375 }
376 }
377
378 /**
379 * i40e_check_asq_alive
380 * @hw: pointer to the hw struct
381 *
382 * Returns TRUE if Queue is enabled else FALSE.
383 **/
i40e_check_asq_alive(struct i40e_hw * hw)384 bool i40e_check_asq_alive(struct i40e_hw *hw)
385 {
386 if (hw->aq.asq.len)
387 if (!i40e_is_vf(hw))
388 return !!(rd32(hw, hw->aq.asq.len) &
389 I40E_PF_ATQLEN_ATQENABLE_MASK);
390 if (i40e_is_vf(hw))
391 return !!(rd32(hw, hw->aq.asq.len) &
392 I40E_VF_ATQLEN1_ATQENABLE_MASK);
393 return FALSE;
394 }
395
396 /**
397 * i40e_aq_queue_shutdown
398 * @hw: pointer to the hw struct
399 * @unloading: is the driver unloading itself
400 *
401 * Tell the Firmware that we're shutting down the AdminQ and whether
402 * or not the driver is unloading as well.
403 **/
i40e_aq_queue_shutdown(struct i40e_hw * hw,bool unloading)404 enum i40e_status_code i40e_aq_queue_shutdown(struct i40e_hw *hw,
405 bool unloading)
406 {
407 struct i40e_aq_desc desc;
408 struct i40e_aqc_queue_shutdown *cmd =
409 (struct i40e_aqc_queue_shutdown *)&desc.params.raw;
410 enum i40e_status_code status;
411
412 i40e_fill_default_direct_cmd_desc(&desc,
413 i40e_aqc_opc_queue_shutdown);
414
415 if (unloading)
416 cmd->driver_unloading = CPU_TO_LE32(I40E_AQ_DRIVER_UNLOADING);
417 status = i40e_asq_send_command(hw, &desc, NULL, 0, NULL);
418
419 return status;
420 }
421
422 /**
423 * i40e_aq_get_set_rss_lut
424 * @hw: pointer to the hardware structure
425 * @vsi_id: vsi fw index
426 * @pf_lut: for PF table set TRUE, for VSI table set FALSE
427 * @lut: pointer to the lut buffer provided by the caller
428 * @lut_size: size of the lut buffer
429 * @set: set TRUE to set the table, FALSE to get the table
430 *
431 * Internal function to get or set RSS look up table
432 **/
i40e_aq_get_set_rss_lut(struct i40e_hw * hw,u16 vsi_id,bool pf_lut,u8 * lut,u16 lut_size,bool set)433 static enum i40e_status_code i40e_aq_get_set_rss_lut(struct i40e_hw *hw,
434 u16 vsi_id, bool pf_lut,
435 u8 *lut, u16 lut_size,
436 bool set)
437 {
438 enum i40e_status_code status;
439 struct i40e_aq_desc desc;
440 struct i40e_aqc_get_set_rss_lut *cmd_resp =
441 (struct i40e_aqc_get_set_rss_lut *)&desc.params.raw;
442
443 if (set)
444 i40e_fill_default_direct_cmd_desc(&desc,
445 i40e_aqc_opc_set_rss_lut);
446 else
447 i40e_fill_default_direct_cmd_desc(&desc,
448 i40e_aqc_opc_get_rss_lut);
449
450 /* Indirect command */
451 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
452 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_RD);
453
454 cmd_resp->vsi_id =
455 CPU_TO_LE16((u16)((vsi_id <<
456 I40E_AQC_SET_RSS_LUT_VSI_ID_SHIFT) &
457 I40E_AQC_SET_RSS_LUT_VSI_ID_MASK));
458 cmd_resp->vsi_id |= CPU_TO_LE16((u16)I40E_AQC_SET_RSS_LUT_VSI_VALID);
459
460 if (pf_lut)
461 cmd_resp->flags |= CPU_TO_LE16((u16)
462 ((I40E_AQC_SET_RSS_LUT_TABLE_TYPE_PF <<
463 I40E_AQC_SET_RSS_LUT_TABLE_TYPE_SHIFT) &
464 I40E_AQC_SET_RSS_LUT_TABLE_TYPE_MASK));
465 else
466 cmd_resp->flags |= CPU_TO_LE16((u16)
467 ((I40E_AQC_SET_RSS_LUT_TABLE_TYPE_VSI <<
468 I40E_AQC_SET_RSS_LUT_TABLE_TYPE_SHIFT) &
469 I40E_AQC_SET_RSS_LUT_TABLE_TYPE_MASK));
470
471 status = i40e_asq_send_command(hw, &desc, lut, lut_size, NULL);
472
473 return status;
474 }
475
476 /**
477 * i40e_aq_get_rss_lut
478 * @hw: pointer to the hardware structure
479 * @vsi_id: vsi fw index
480 * @pf_lut: for PF table set TRUE, for VSI table set FALSE
481 * @lut: pointer to the lut buffer provided by the caller
482 * @lut_size: size of the lut buffer
483 *
484 * get the RSS lookup table, PF or VSI type
485 **/
i40e_aq_get_rss_lut(struct i40e_hw * hw,u16 vsi_id,bool pf_lut,u8 * lut,u16 lut_size)486 enum i40e_status_code i40e_aq_get_rss_lut(struct i40e_hw *hw, u16 vsi_id,
487 bool pf_lut, u8 *lut, u16 lut_size)
488 {
489 return i40e_aq_get_set_rss_lut(hw, vsi_id, pf_lut, lut, lut_size,
490 FALSE);
491 }
492
493 /**
494 * i40e_aq_set_rss_lut
495 * @hw: pointer to the hardware structure
496 * @vsi_id: vsi fw index
497 * @pf_lut: for PF table set TRUE, for VSI table set FALSE
498 * @lut: pointer to the lut buffer provided by the caller
499 * @lut_size: size of the lut buffer
500 *
501 * set the RSS lookup table, PF or VSI type
502 **/
i40e_aq_set_rss_lut(struct i40e_hw * hw,u16 vsi_id,bool pf_lut,u8 * lut,u16 lut_size)503 enum i40e_status_code i40e_aq_set_rss_lut(struct i40e_hw *hw, u16 vsi_id,
504 bool pf_lut, u8 *lut, u16 lut_size)
505 {
506 return i40e_aq_get_set_rss_lut(hw, vsi_id, pf_lut, lut, lut_size, TRUE);
507 }
508
509 /**
510 * i40e_aq_get_set_rss_key
511 * @hw: pointer to the hw struct
512 * @vsi_id: vsi fw index
513 * @key: pointer to key info struct
514 * @set: set TRUE to set the key, FALSE to get the key
515 *
516 * get the RSS key per VSI
517 **/
i40e_aq_get_set_rss_key(struct i40e_hw * hw,u16 vsi_id,struct i40e_aqc_get_set_rss_key_data * key,bool set)518 static enum i40e_status_code i40e_aq_get_set_rss_key(struct i40e_hw *hw,
519 u16 vsi_id,
520 struct i40e_aqc_get_set_rss_key_data *key,
521 bool set)
522 {
523 enum i40e_status_code status;
524 struct i40e_aq_desc desc;
525 struct i40e_aqc_get_set_rss_key *cmd_resp =
526 (struct i40e_aqc_get_set_rss_key *)&desc.params.raw;
527 u16 key_size = sizeof(struct i40e_aqc_get_set_rss_key_data);
528
529 if (set)
530 i40e_fill_default_direct_cmd_desc(&desc,
531 i40e_aqc_opc_set_rss_key);
532 else
533 i40e_fill_default_direct_cmd_desc(&desc,
534 i40e_aqc_opc_get_rss_key);
535
536 /* Indirect command */
537 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
538 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_RD);
539
540 cmd_resp->vsi_id =
541 CPU_TO_LE16((u16)((vsi_id <<
542 I40E_AQC_SET_RSS_KEY_VSI_ID_SHIFT) &
543 I40E_AQC_SET_RSS_KEY_VSI_ID_MASK));
544 cmd_resp->vsi_id |= CPU_TO_LE16((u16)I40E_AQC_SET_RSS_KEY_VSI_VALID);
545
546 status = i40e_asq_send_command(hw, &desc, key, key_size, NULL);
547
548 return status;
549 }
550
551 /**
552 * i40e_aq_get_rss_key
553 * @hw: pointer to the hw struct
554 * @vsi_id: vsi fw index
555 * @key: pointer to key info struct
556 *
557 **/
i40e_aq_get_rss_key(struct i40e_hw * hw,u16 vsi_id,struct i40e_aqc_get_set_rss_key_data * key)558 enum i40e_status_code i40e_aq_get_rss_key(struct i40e_hw *hw,
559 u16 vsi_id,
560 struct i40e_aqc_get_set_rss_key_data *key)
561 {
562 return i40e_aq_get_set_rss_key(hw, vsi_id, key, FALSE);
563 }
564
565 /**
566 * i40e_aq_set_rss_key
567 * @hw: pointer to the hw struct
568 * @vsi_id: vsi fw index
569 * @key: pointer to key info struct
570 *
571 * set the RSS key per VSI
572 **/
i40e_aq_set_rss_key(struct i40e_hw * hw,u16 vsi_id,struct i40e_aqc_get_set_rss_key_data * key)573 enum i40e_status_code i40e_aq_set_rss_key(struct i40e_hw *hw,
574 u16 vsi_id,
575 struct i40e_aqc_get_set_rss_key_data *key)
576 {
577 return i40e_aq_get_set_rss_key(hw, vsi_id, key, TRUE);
578 }
579
580 /* The i40e_ptype_lookup table is used to convert from the 8-bit ptype in the
581 * hardware to a bit-field that can be used by SW to more easily determine the
582 * packet type.
583 *
584 * Macros are used to shorten the table lines and make this table human
585 * readable.
586 *
587 * We store the PTYPE in the top byte of the bit field - this is just so that
588 * we can check that the table doesn't have a row missing, as the index into
589 * the table should be the PTYPE.
590 *
591 * Typical work flow:
592 *
593 * IF NOT i40e_ptype_lookup[ptype].known
594 * THEN
595 * Packet is unknown
596 * ELSE IF i40e_ptype_lookup[ptype].outer_ip == I40E_RX_PTYPE_OUTER_IP
597 * Use the rest of the fields to look at the tunnels, inner protocols, etc
598 * ELSE
599 * Use the enum i40e_rx_l2_ptype to decode the packet type
600 * ENDIF
601 */
602
603 /* macro to make the table lines short */
604 #define I40E_PTT(PTYPE, OUTER_IP, OUTER_IP_VER, OUTER_FRAG, T, TE, TEF, I, PL)\
605 { PTYPE, \
606 1, \
607 I40E_RX_PTYPE_OUTER_##OUTER_IP, \
608 I40E_RX_PTYPE_OUTER_##OUTER_IP_VER, \
609 I40E_RX_PTYPE_##OUTER_FRAG, \
610 I40E_RX_PTYPE_TUNNEL_##T, \
611 I40E_RX_PTYPE_TUNNEL_END_##TE, \
612 I40E_RX_PTYPE_##TEF, \
613 I40E_RX_PTYPE_INNER_PROT_##I, \
614 I40E_RX_PTYPE_PAYLOAD_LAYER_##PL }
615
616 #define I40E_PTT_UNUSED_ENTRY(PTYPE) \
617 { PTYPE, 0, 0, 0, 0, 0, 0, 0, 0, 0 }
618
619 /* shorter macros makes the table fit but are terse */
620 #define I40E_RX_PTYPE_NOF I40E_RX_PTYPE_NOT_FRAG
621 #define I40E_RX_PTYPE_FRG I40E_RX_PTYPE_FRAG
622 #define I40E_RX_PTYPE_INNER_PROT_TS I40E_RX_PTYPE_INNER_PROT_TIMESYNC
623
624 /* Lookup table mapping the HW PTYPE to the bit field for decoding */
625 struct i40e_rx_ptype_decoded i40e_ptype_lookup[] = {
626 /* L2 Packet types */
627 I40E_PTT_UNUSED_ENTRY(0),
628 I40E_PTT(1, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY2),
629 I40E_PTT(2, L2, NONE, NOF, NONE, NONE, NOF, TS, PAY2),
630 I40E_PTT(3, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY2),
631 I40E_PTT_UNUSED_ENTRY(4),
632 I40E_PTT_UNUSED_ENTRY(5),
633 I40E_PTT(6, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY2),
634 I40E_PTT(7, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY2),
635 I40E_PTT_UNUSED_ENTRY(8),
636 I40E_PTT_UNUSED_ENTRY(9),
637 I40E_PTT(10, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY2),
638 I40E_PTT(11, L2, NONE, NOF, NONE, NONE, NOF, NONE, NONE),
639 I40E_PTT(12, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY3),
640 I40E_PTT(13, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY3),
641 I40E_PTT(14, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY3),
642 I40E_PTT(15, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY3),
643 I40E_PTT(16, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY3),
644 I40E_PTT(17, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY3),
645 I40E_PTT(18, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY3),
646 I40E_PTT(19, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY3),
647 I40E_PTT(20, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY3),
648 I40E_PTT(21, L2, NONE, NOF, NONE, NONE, NOF, NONE, PAY3),
649
650 /* Non Tunneled IPv4 */
651 I40E_PTT(22, IP, IPV4, FRG, NONE, NONE, NOF, NONE, PAY3),
652 I40E_PTT(23, IP, IPV4, NOF, NONE, NONE, NOF, NONE, PAY3),
653 I40E_PTT(24, IP, IPV4, NOF, NONE, NONE, NOF, UDP, PAY4),
654 I40E_PTT_UNUSED_ENTRY(25),
655 I40E_PTT(26, IP, IPV4, NOF, NONE, NONE, NOF, TCP, PAY4),
656 I40E_PTT(27, IP, IPV4, NOF, NONE, NONE, NOF, SCTP, PAY4),
657 I40E_PTT(28, IP, IPV4, NOF, NONE, NONE, NOF, ICMP, PAY4),
658
659 /* IPv4 --> IPv4 */
660 I40E_PTT(29, IP, IPV4, NOF, IP_IP, IPV4, FRG, NONE, PAY3),
661 I40E_PTT(30, IP, IPV4, NOF, IP_IP, IPV4, NOF, NONE, PAY3),
662 I40E_PTT(31, IP, IPV4, NOF, IP_IP, IPV4, NOF, UDP, PAY4),
663 I40E_PTT_UNUSED_ENTRY(32),
664 I40E_PTT(33, IP, IPV4, NOF, IP_IP, IPV4, NOF, TCP, PAY4),
665 I40E_PTT(34, IP, IPV4, NOF, IP_IP, IPV4, NOF, SCTP, PAY4),
666 I40E_PTT(35, IP, IPV4, NOF, IP_IP, IPV4, NOF, ICMP, PAY4),
667
668 /* IPv4 --> IPv6 */
669 I40E_PTT(36, IP, IPV4, NOF, IP_IP, IPV6, FRG, NONE, PAY3),
670 I40E_PTT(37, IP, IPV4, NOF, IP_IP, IPV6, NOF, NONE, PAY3),
671 I40E_PTT(38, IP, IPV4, NOF, IP_IP, IPV6, NOF, UDP, PAY4),
672 I40E_PTT_UNUSED_ENTRY(39),
673 I40E_PTT(40, IP, IPV4, NOF, IP_IP, IPV6, NOF, TCP, PAY4),
674 I40E_PTT(41, IP, IPV4, NOF, IP_IP, IPV6, NOF, SCTP, PAY4),
675 I40E_PTT(42, IP, IPV4, NOF, IP_IP, IPV6, NOF, ICMP, PAY4),
676
677 /* IPv4 --> GRE/NAT */
678 I40E_PTT(43, IP, IPV4, NOF, IP_GRENAT, NONE, NOF, NONE, PAY3),
679
680 /* IPv4 --> GRE/NAT --> IPv4 */
681 I40E_PTT(44, IP, IPV4, NOF, IP_GRENAT, IPV4, FRG, NONE, PAY3),
682 I40E_PTT(45, IP, IPV4, NOF, IP_GRENAT, IPV4, NOF, NONE, PAY3),
683 I40E_PTT(46, IP, IPV4, NOF, IP_GRENAT, IPV4, NOF, UDP, PAY4),
684 I40E_PTT_UNUSED_ENTRY(47),
685 I40E_PTT(48, IP, IPV4, NOF, IP_GRENAT, IPV4, NOF, TCP, PAY4),
686 I40E_PTT(49, IP, IPV4, NOF, IP_GRENAT, IPV4, NOF, SCTP, PAY4),
687 I40E_PTT(50, IP, IPV4, NOF, IP_GRENAT, IPV4, NOF, ICMP, PAY4),
688
689 /* IPv4 --> GRE/NAT --> IPv6 */
690 I40E_PTT(51, IP, IPV4, NOF, IP_GRENAT, IPV6, FRG, NONE, PAY3),
691 I40E_PTT(52, IP, IPV4, NOF, IP_GRENAT, IPV6, NOF, NONE, PAY3),
692 I40E_PTT(53, IP, IPV4, NOF, IP_GRENAT, IPV6, NOF, UDP, PAY4),
693 I40E_PTT_UNUSED_ENTRY(54),
694 I40E_PTT(55, IP, IPV4, NOF, IP_GRENAT, IPV6, NOF, TCP, PAY4),
695 I40E_PTT(56, IP, IPV4, NOF, IP_GRENAT, IPV6, NOF, SCTP, PAY4),
696 I40E_PTT(57, IP, IPV4, NOF, IP_GRENAT, IPV6, NOF, ICMP, PAY4),
697
698 /* IPv4 --> GRE/NAT --> MAC */
699 I40E_PTT(58, IP, IPV4, NOF, IP_GRENAT_MAC, NONE, NOF, NONE, PAY3),
700
701 /* IPv4 --> GRE/NAT --> MAC --> IPv4 */
702 I40E_PTT(59, IP, IPV4, NOF, IP_GRENAT_MAC, IPV4, FRG, NONE, PAY3),
703 I40E_PTT(60, IP, IPV4, NOF, IP_GRENAT_MAC, IPV4, NOF, NONE, PAY3),
704 I40E_PTT(61, IP, IPV4, NOF, IP_GRENAT_MAC, IPV4, NOF, UDP, PAY4),
705 I40E_PTT_UNUSED_ENTRY(62),
706 I40E_PTT(63, IP, IPV4, NOF, IP_GRENAT_MAC, IPV4, NOF, TCP, PAY4),
707 I40E_PTT(64, IP, IPV4, NOF, IP_GRENAT_MAC, IPV4, NOF, SCTP, PAY4),
708 I40E_PTT(65, IP, IPV4, NOF, IP_GRENAT_MAC, IPV4, NOF, ICMP, PAY4),
709
710 /* IPv4 --> GRE/NAT -> MAC --> IPv6 */
711 I40E_PTT(66, IP, IPV4, NOF, IP_GRENAT_MAC, IPV6, FRG, NONE, PAY3),
712 I40E_PTT(67, IP, IPV4, NOF, IP_GRENAT_MAC, IPV6, NOF, NONE, PAY3),
713 I40E_PTT(68, IP, IPV4, NOF, IP_GRENAT_MAC, IPV6, NOF, UDP, PAY4),
714 I40E_PTT_UNUSED_ENTRY(69),
715 I40E_PTT(70, IP, IPV4, NOF, IP_GRENAT_MAC, IPV6, NOF, TCP, PAY4),
716 I40E_PTT(71, IP, IPV4, NOF, IP_GRENAT_MAC, IPV6, NOF, SCTP, PAY4),
717 I40E_PTT(72, IP, IPV4, NOF, IP_GRENAT_MAC, IPV6, NOF, ICMP, PAY4),
718
719 /* IPv4 --> GRE/NAT --> MAC/VLAN */
720 I40E_PTT(73, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, NONE, NOF, NONE, PAY3),
721
722 /* IPv4 ---> GRE/NAT -> MAC/VLAN --> IPv4 */
723 I40E_PTT(74, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV4, FRG, NONE, PAY3),
724 I40E_PTT(75, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV4, NOF, NONE, PAY3),
725 I40E_PTT(76, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV4, NOF, UDP, PAY4),
726 I40E_PTT_UNUSED_ENTRY(77),
727 I40E_PTT(78, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV4, NOF, TCP, PAY4),
728 I40E_PTT(79, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV4, NOF, SCTP, PAY4),
729 I40E_PTT(80, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV4, NOF, ICMP, PAY4),
730
731 /* IPv4 -> GRE/NAT -> MAC/VLAN --> IPv6 */
732 I40E_PTT(81, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV6, FRG, NONE, PAY3),
733 I40E_PTT(82, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV6, NOF, NONE, PAY3),
734 I40E_PTT(83, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV6, NOF, UDP, PAY4),
735 I40E_PTT_UNUSED_ENTRY(84),
736 I40E_PTT(85, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV6, NOF, TCP, PAY4),
737 I40E_PTT(86, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV6, NOF, SCTP, PAY4),
738 I40E_PTT(87, IP, IPV4, NOF, IP_GRENAT_MAC_VLAN, IPV6, NOF, ICMP, PAY4),
739
740 /* Non Tunneled IPv6 */
741 I40E_PTT(88, IP, IPV6, FRG, NONE, NONE, NOF, NONE, PAY3),
742 I40E_PTT(89, IP, IPV6, NOF, NONE, NONE, NOF, NONE, PAY3),
743 I40E_PTT(90, IP, IPV6, NOF, NONE, NONE, NOF, UDP, PAY4),
744 I40E_PTT_UNUSED_ENTRY(91),
745 I40E_PTT(92, IP, IPV6, NOF, NONE, NONE, NOF, TCP, PAY4),
746 I40E_PTT(93, IP, IPV6, NOF, NONE, NONE, NOF, SCTP, PAY4),
747 I40E_PTT(94, IP, IPV6, NOF, NONE, NONE, NOF, ICMP, PAY4),
748
749 /* IPv6 --> IPv4 */
750 I40E_PTT(95, IP, IPV6, NOF, IP_IP, IPV4, FRG, NONE, PAY3),
751 I40E_PTT(96, IP, IPV6, NOF, IP_IP, IPV4, NOF, NONE, PAY3),
752 I40E_PTT(97, IP, IPV6, NOF, IP_IP, IPV4, NOF, UDP, PAY4),
753 I40E_PTT_UNUSED_ENTRY(98),
754 I40E_PTT(99, IP, IPV6, NOF, IP_IP, IPV4, NOF, TCP, PAY4),
755 I40E_PTT(100, IP, IPV6, NOF, IP_IP, IPV4, NOF, SCTP, PAY4),
756 I40E_PTT(101, IP, IPV6, NOF, IP_IP, IPV4, NOF, ICMP, PAY4),
757
758 /* IPv6 --> IPv6 */
759 I40E_PTT(102, IP, IPV6, NOF, IP_IP, IPV6, FRG, NONE, PAY3),
760 I40E_PTT(103, IP, IPV6, NOF, IP_IP, IPV6, NOF, NONE, PAY3),
761 I40E_PTT(104, IP, IPV6, NOF, IP_IP, IPV6, NOF, UDP, PAY4),
762 I40E_PTT_UNUSED_ENTRY(105),
763 I40E_PTT(106, IP, IPV6, NOF, IP_IP, IPV6, NOF, TCP, PAY4),
764 I40E_PTT(107, IP, IPV6, NOF, IP_IP, IPV6, NOF, SCTP, PAY4),
765 I40E_PTT(108, IP, IPV6, NOF, IP_IP, IPV6, NOF, ICMP, PAY4),
766
767 /* IPv6 --> GRE/NAT */
768 I40E_PTT(109, IP, IPV6, NOF, IP_GRENAT, NONE, NOF, NONE, PAY3),
769
770 /* IPv6 --> GRE/NAT -> IPv4 */
771 I40E_PTT(110, IP, IPV6, NOF, IP_GRENAT, IPV4, FRG, NONE, PAY3),
772 I40E_PTT(111, IP, IPV6, NOF, IP_GRENAT, IPV4, NOF, NONE, PAY3),
773 I40E_PTT(112, IP, IPV6, NOF, IP_GRENAT, IPV4, NOF, UDP, PAY4),
774 I40E_PTT_UNUSED_ENTRY(113),
775 I40E_PTT(114, IP, IPV6, NOF, IP_GRENAT, IPV4, NOF, TCP, PAY4),
776 I40E_PTT(115, IP, IPV6, NOF, IP_GRENAT, IPV4, NOF, SCTP, PAY4),
777 I40E_PTT(116, IP, IPV6, NOF, IP_GRENAT, IPV4, NOF, ICMP, PAY4),
778
779 /* IPv6 --> GRE/NAT -> IPv6 */
780 I40E_PTT(117, IP, IPV6, NOF, IP_GRENAT, IPV6, FRG, NONE, PAY3),
781 I40E_PTT(118, IP, IPV6, NOF, IP_GRENAT, IPV6, NOF, NONE, PAY3),
782 I40E_PTT(119, IP, IPV6, NOF, IP_GRENAT, IPV6, NOF, UDP, PAY4),
783 I40E_PTT_UNUSED_ENTRY(120),
784 I40E_PTT(121, IP, IPV6, NOF, IP_GRENAT, IPV6, NOF, TCP, PAY4),
785 I40E_PTT(122, IP, IPV6, NOF, IP_GRENAT, IPV6, NOF, SCTP, PAY4),
786 I40E_PTT(123, IP, IPV6, NOF, IP_GRENAT, IPV6, NOF, ICMP, PAY4),
787
788 /* IPv6 --> GRE/NAT -> MAC */
789 I40E_PTT(124, IP, IPV6, NOF, IP_GRENAT_MAC, NONE, NOF, NONE, PAY3),
790
791 /* IPv6 --> GRE/NAT -> MAC -> IPv4 */
792 I40E_PTT(125, IP, IPV6, NOF, IP_GRENAT_MAC, IPV4, FRG, NONE, PAY3),
793 I40E_PTT(126, IP, IPV6, NOF, IP_GRENAT_MAC, IPV4, NOF, NONE, PAY3),
794 I40E_PTT(127, IP, IPV6, NOF, IP_GRENAT_MAC, IPV4, NOF, UDP, PAY4),
795 I40E_PTT_UNUSED_ENTRY(128),
796 I40E_PTT(129, IP, IPV6, NOF, IP_GRENAT_MAC, IPV4, NOF, TCP, PAY4),
797 I40E_PTT(130, IP, IPV6, NOF, IP_GRENAT_MAC, IPV4, NOF, SCTP, PAY4),
798 I40E_PTT(131, IP, IPV6, NOF, IP_GRENAT_MAC, IPV4, NOF, ICMP, PAY4),
799
800 /* IPv6 --> GRE/NAT -> MAC -> IPv6 */
801 I40E_PTT(132, IP, IPV6, NOF, IP_GRENAT_MAC, IPV6, FRG, NONE, PAY3),
802 I40E_PTT(133, IP, IPV6, NOF, IP_GRENAT_MAC, IPV6, NOF, NONE, PAY3),
803 I40E_PTT(134, IP, IPV6, NOF, IP_GRENAT_MAC, IPV6, NOF, UDP, PAY4),
804 I40E_PTT_UNUSED_ENTRY(135),
805 I40E_PTT(136, IP, IPV6, NOF, IP_GRENAT_MAC, IPV6, NOF, TCP, PAY4),
806 I40E_PTT(137, IP, IPV6, NOF, IP_GRENAT_MAC, IPV6, NOF, SCTP, PAY4),
807 I40E_PTT(138, IP, IPV6, NOF, IP_GRENAT_MAC, IPV6, NOF, ICMP, PAY4),
808
809 /* IPv6 --> GRE/NAT -> MAC/VLAN */
810 I40E_PTT(139, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, NONE, NOF, NONE, PAY3),
811
812 /* IPv6 --> GRE/NAT -> MAC/VLAN --> IPv4 */
813 I40E_PTT(140, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV4, FRG, NONE, PAY3),
814 I40E_PTT(141, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV4, NOF, NONE, PAY3),
815 I40E_PTT(142, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV4, NOF, UDP, PAY4),
816 I40E_PTT_UNUSED_ENTRY(143),
817 I40E_PTT(144, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV4, NOF, TCP, PAY4),
818 I40E_PTT(145, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV4, NOF, SCTP, PAY4),
819 I40E_PTT(146, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV4, NOF, ICMP, PAY4),
820
821 /* IPv6 --> GRE/NAT -> MAC/VLAN --> IPv6 */
822 I40E_PTT(147, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV6, FRG, NONE, PAY3),
823 I40E_PTT(148, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV6, NOF, NONE, PAY3),
824 I40E_PTT(149, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV6, NOF, UDP, PAY4),
825 I40E_PTT_UNUSED_ENTRY(150),
826 I40E_PTT(151, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV6, NOF, TCP, PAY4),
827 I40E_PTT(152, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV6, NOF, SCTP, PAY4),
828 I40E_PTT(153, IP, IPV6, NOF, IP_GRENAT_MAC_VLAN, IPV6, NOF, ICMP, PAY4),
829
830 /* unused entries */
831 I40E_PTT_UNUSED_ENTRY(154),
832 I40E_PTT_UNUSED_ENTRY(155),
833 I40E_PTT_UNUSED_ENTRY(156),
834 I40E_PTT_UNUSED_ENTRY(157),
835 I40E_PTT_UNUSED_ENTRY(158),
836 I40E_PTT_UNUSED_ENTRY(159),
837
838 I40E_PTT_UNUSED_ENTRY(160),
839 I40E_PTT_UNUSED_ENTRY(161),
840 I40E_PTT_UNUSED_ENTRY(162),
841 I40E_PTT_UNUSED_ENTRY(163),
842 I40E_PTT_UNUSED_ENTRY(164),
843 I40E_PTT_UNUSED_ENTRY(165),
844 I40E_PTT_UNUSED_ENTRY(166),
845 I40E_PTT_UNUSED_ENTRY(167),
846 I40E_PTT_UNUSED_ENTRY(168),
847 I40E_PTT_UNUSED_ENTRY(169),
848
849 I40E_PTT_UNUSED_ENTRY(170),
850 I40E_PTT_UNUSED_ENTRY(171),
851 I40E_PTT_UNUSED_ENTRY(172),
852 I40E_PTT_UNUSED_ENTRY(173),
853 I40E_PTT_UNUSED_ENTRY(174),
854 I40E_PTT_UNUSED_ENTRY(175),
855 I40E_PTT_UNUSED_ENTRY(176),
856 I40E_PTT_UNUSED_ENTRY(177),
857 I40E_PTT_UNUSED_ENTRY(178),
858 I40E_PTT_UNUSED_ENTRY(179),
859
860 I40E_PTT_UNUSED_ENTRY(180),
861 I40E_PTT_UNUSED_ENTRY(181),
862 I40E_PTT_UNUSED_ENTRY(182),
863 I40E_PTT_UNUSED_ENTRY(183),
864 I40E_PTT_UNUSED_ENTRY(184),
865 I40E_PTT_UNUSED_ENTRY(185),
866 I40E_PTT_UNUSED_ENTRY(186),
867 I40E_PTT_UNUSED_ENTRY(187),
868 I40E_PTT_UNUSED_ENTRY(188),
869 I40E_PTT_UNUSED_ENTRY(189),
870
871 I40E_PTT_UNUSED_ENTRY(190),
872 I40E_PTT_UNUSED_ENTRY(191),
873 I40E_PTT_UNUSED_ENTRY(192),
874 I40E_PTT_UNUSED_ENTRY(193),
875 I40E_PTT_UNUSED_ENTRY(194),
876 I40E_PTT_UNUSED_ENTRY(195),
877 I40E_PTT_UNUSED_ENTRY(196),
878 I40E_PTT_UNUSED_ENTRY(197),
879 I40E_PTT_UNUSED_ENTRY(198),
880 I40E_PTT_UNUSED_ENTRY(199),
881
882 I40E_PTT_UNUSED_ENTRY(200),
883 I40E_PTT_UNUSED_ENTRY(201),
884 I40E_PTT_UNUSED_ENTRY(202),
885 I40E_PTT_UNUSED_ENTRY(203),
886 I40E_PTT_UNUSED_ENTRY(204),
887 I40E_PTT_UNUSED_ENTRY(205),
888 I40E_PTT_UNUSED_ENTRY(206),
889 I40E_PTT_UNUSED_ENTRY(207),
890 I40E_PTT_UNUSED_ENTRY(208),
891 I40E_PTT_UNUSED_ENTRY(209),
892
893 I40E_PTT_UNUSED_ENTRY(210),
894 I40E_PTT_UNUSED_ENTRY(211),
895 I40E_PTT_UNUSED_ENTRY(212),
896 I40E_PTT_UNUSED_ENTRY(213),
897 I40E_PTT_UNUSED_ENTRY(214),
898 I40E_PTT_UNUSED_ENTRY(215),
899 I40E_PTT_UNUSED_ENTRY(216),
900 I40E_PTT_UNUSED_ENTRY(217),
901 I40E_PTT_UNUSED_ENTRY(218),
902 I40E_PTT_UNUSED_ENTRY(219),
903
904 I40E_PTT_UNUSED_ENTRY(220),
905 I40E_PTT_UNUSED_ENTRY(221),
906 I40E_PTT_UNUSED_ENTRY(222),
907 I40E_PTT_UNUSED_ENTRY(223),
908 I40E_PTT_UNUSED_ENTRY(224),
909 I40E_PTT_UNUSED_ENTRY(225),
910 I40E_PTT_UNUSED_ENTRY(226),
911 I40E_PTT_UNUSED_ENTRY(227),
912 I40E_PTT_UNUSED_ENTRY(228),
913 I40E_PTT_UNUSED_ENTRY(229),
914
915 I40E_PTT_UNUSED_ENTRY(230),
916 I40E_PTT_UNUSED_ENTRY(231),
917 I40E_PTT_UNUSED_ENTRY(232),
918 I40E_PTT_UNUSED_ENTRY(233),
919 I40E_PTT_UNUSED_ENTRY(234),
920 I40E_PTT_UNUSED_ENTRY(235),
921 I40E_PTT_UNUSED_ENTRY(236),
922 I40E_PTT_UNUSED_ENTRY(237),
923 I40E_PTT_UNUSED_ENTRY(238),
924 I40E_PTT_UNUSED_ENTRY(239),
925
926 I40E_PTT_UNUSED_ENTRY(240),
927 I40E_PTT_UNUSED_ENTRY(241),
928 I40E_PTT_UNUSED_ENTRY(242),
929 I40E_PTT_UNUSED_ENTRY(243),
930 I40E_PTT_UNUSED_ENTRY(244),
931 I40E_PTT_UNUSED_ENTRY(245),
932 I40E_PTT_UNUSED_ENTRY(246),
933 I40E_PTT_UNUSED_ENTRY(247),
934 I40E_PTT_UNUSED_ENTRY(248),
935 I40E_PTT_UNUSED_ENTRY(249),
936
937 I40E_PTT_UNUSED_ENTRY(250),
938 I40E_PTT_UNUSED_ENTRY(251),
939 I40E_PTT_UNUSED_ENTRY(252),
940 I40E_PTT_UNUSED_ENTRY(253),
941 I40E_PTT_UNUSED_ENTRY(254),
942 I40E_PTT_UNUSED_ENTRY(255)
943 };
944
945
946 /**
947 * i40e_validate_mac_addr - Validate unicast MAC address
948 * @mac_addr: pointer to MAC address
949 *
950 * Tests a MAC address to ensure it is a valid Individual Address
951 **/
i40e_validate_mac_addr(u8 * mac_addr)952 enum i40e_status_code i40e_validate_mac_addr(u8 *mac_addr)
953 {
954 enum i40e_status_code status = I40E_SUCCESS;
955
956 DEBUGFUNC("i40e_validate_mac_addr");
957
958 /* Broadcast addresses ARE multicast addresses
959 * Make sure it is not a multicast address
960 * Reject the zero address
961 */
962 if (I40E_IS_MULTICAST(mac_addr) ||
963 (mac_addr[0] == 0 && mac_addr[1] == 0 && mac_addr[2] == 0 &&
964 mac_addr[3] == 0 && mac_addr[4] == 0 && mac_addr[5] == 0))
965 status = I40E_ERR_INVALID_MAC_ADDR;
966
967 return status;
968 }
969
970 /**
971 * i40e_init_shared_code - Initialize the shared code
972 * @hw: pointer to hardware structure
973 *
974 * This assigns the MAC type and PHY code and inits the NVM.
975 * Does not touch the hardware. This function must be called prior to any
976 * other function in the shared code. The i40e_hw structure should be
977 * memset to 0 prior to calling this function. The following fields in
978 * hw structure should be filled in prior to calling this function:
979 * hw_addr, back, device_id, vendor_id, subsystem_device_id,
980 * subsystem_vendor_id, and revision_id
981 **/
i40e_init_shared_code(struct i40e_hw * hw)982 enum i40e_status_code i40e_init_shared_code(struct i40e_hw *hw)
983 {
984 enum i40e_status_code status = I40E_SUCCESS;
985 u32 port, ari, func_rid;
986
987 DEBUGFUNC("i40e_init_shared_code");
988
989 i40e_set_mac_type(hw);
990
991 switch (hw->mac.type) {
992 case I40E_MAC_XL710:
993 case I40E_MAC_X722:
994 break;
995 default:
996 return I40E_ERR_DEVICE_NOT_SUPPORTED;
997 }
998
999 hw->phy.get_link_info = TRUE;
1000
1001 /* Determine port number and PF number*/
1002 port = (rd32(hw, I40E_PFGEN_PORTNUM) & I40E_PFGEN_PORTNUM_PORT_NUM_MASK)
1003 >> I40E_PFGEN_PORTNUM_PORT_NUM_SHIFT;
1004 hw->port = (u8)port;
1005 ari = (rd32(hw, I40E_GLPCI_CAPSUP) & I40E_GLPCI_CAPSUP_ARI_EN_MASK) >>
1006 I40E_GLPCI_CAPSUP_ARI_EN_SHIFT;
1007 func_rid = rd32(hw, I40E_PF_FUNC_RID);
1008 if (ari)
1009 hw->pf_id = (u8)(func_rid & 0xff);
1010 else
1011 hw->pf_id = (u8)(func_rid & 0x7);
1012
1013 if (hw->mac.type == I40E_MAC_X722)
1014 hw->flags |= I40E_HW_FLAG_AQ_SRCTL_ACCESS_ENABLE |
1015 I40E_HW_FLAG_NVM_READ_REQUIRES_LOCK;
1016
1017 status = i40e_init_nvm(hw);
1018 return status;
1019 }
1020
1021 /**
1022 * i40e_aq_mac_address_read - Retrieve the MAC addresses
1023 * @hw: pointer to the hw struct
1024 * @flags: a return indicator of what addresses were added to the addr store
1025 * @addrs: the requestor's mac addr store
1026 * @cmd_details: pointer to command details structure or NULL
1027 **/
i40e_aq_mac_address_read(struct i40e_hw * hw,u16 * flags,struct i40e_aqc_mac_address_read_data * addrs,struct i40e_asq_cmd_details * cmd_details)1028 static enum i40e_status_code i40e_aq_mac_address_read(struct i40e_hw *hw,
1029 u16 *flags,
1030 struct i40e_aqc_mac_address_read_data *addrs,
1031 struct i40e_asq_cmd_details *cmd_details)
1032 {
1033 struct i40e_aq_desc desc;
1034 struct i40e_aqc_mac_address_read *cmd_data =
1035 (struct i40e_aqc_mac_address_read *)&desc.params.raw;
1036 enum i40e_status_code status;
1037
1038 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_mac_address_read);
1039 desc.flags |= CPU_TO_LE16(I40E_AQ_FLAG_BUF);
1040
1041 status = i40e_asq_send_command(hw, &desc, addrs,
1042 sizeof(*addrs), cmd_details);
1043 *flags = LE16_TO_CPU(cmd_data->command_flags);
1044
1045 return status;
1046 }
1047
1048 /**
1049 * i40e_aq_mac_address_write - Change the MAC addresses
1050 * @hw: pointer to the hw struct
1051 * @flags: indicates which MAC to be written
1052 * @mac_addr: address to write
1053 * @cmd_details: pointer to command details structure or NULL
1054 **/
i40e_aq_mac_address_write(struct i40e_hw * hw,u16 flags,u8 * mac_addr,struct i40e_asq_cmd_details * cmd_details)1055 enum i40e_status_code i40e_aq_mac_address_write(struct i40e_hw *hw,
1056 u16 flags, u8 *mac_addr,
1057 struct i40e_asq_cmd_details *cmd_details)
1058 {
1059 struct i40e_aq_desc desc;
1060 struct i40e_aqc_mac_address_write *cmd_data =
1061 (struct i40e_aqc_mac_address_write *)&desc.params.raw;
1062 enum i40e_status_code status;
1063
1064 i40e_fill_default_direct_cmd_desc(&desc,
1065 i40e_aqc_opc_mac_address_write);
1066 cmd_data->command_flags = CPU_TO_LE16(flags);
1067 cmd_data->mac_sah = CPU_TO_LE16((u16)mac_addr[0] << 8 | mac_addr[1]);
1068 cmd_data->mac_sal = CPU_TO_LE32(((u32)mac_addr[2] << 24) |
1069 ((u32)mac_addr[3] << 16) |
1070 ((u32)mac_addr[4] << 8) |
1071 mac_addr[5]);
1072
1073 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
1074
1075 return status;
1076 }
1077
1078 /**
1079 * i40e_get_mac_addr - get MAC address
1080 * @hw: pointer to the HW structure
1081 * @mac_addr: pointer to MAC address
1082 *
1083 * Reads the adapter's MAC address from register
1084 **/
i40e_get_mac_addr(struct i40e_hw * hw,u8 * mac_addr)1085 enum i40e_status_code i40e_get_mac_addr(struct i40e_hw *hw, u8 *mac_addr)
1086 {
1087 struct i40e_aqc_mac_address_read_data addrs;
1088 enum i40e_status_code status;
1089 u16 flags = 0;
1090
1091 status = i40e_aq_mac_address_read(hw, &flags, &addrs, NULL);
1092
1093 if (flags & I40E_AQC_LAN_ADDR_VALID)
1094 i40e_memcpy(mac_addr, &addrs.pf_lan_mac, sizeof(addrs.pf_lan_mac),
1095 I40E_NONDMA_TO_NONDMA);
1096
1097 return status;
1098 }
1099
1100 /**
1101 * i40e_get_port_mac_addr - get Port MAC address
1102 * @hw: pointer to the HW structure
1103 * @mac_addr: pointer to Port MAC address
1104 *
1105 * Reads the adapter's Port MAC address
1106 **/
i40e_get_port_mac_addr(struct i40e_hw * hw,u8 * mac_addr)1107 enum i40e_status_code i40e_get_port_mac_addr(struct i40e_hw *hw, u8 *mac_addr)
1108 {
1109 struct i40e_aqc_mac_address_read_data addrs;
1110 enum i40e_status_code status;
1111 u16 flags = 0;
1112
1113 status = i40e_aq_mac_address_read(hw, &flags, &addrs, NULL);
1114 if (status)
1115 return status;
1116
1117 if (flags & I40E_AQC_PORT_ADDR_VALID)
1118 i40e_memcpy(mac_addr, &addrs.port_mac, sizeof(addrs.port_mac),
1119 I40E_NONDMA_TO_NONDMA);
1120 else
1121 status = I40E_ERR_INVALID_MAC_ADDR;
1122
1123 return status;
1124 }
1125
1126 /**
1127 * i40e_pre_tx_queue_cfg - pre tx queue configure
1128 * @hw: pointer to the HW structure
1129 * @queue: target pf queue index
1130 * @enable: state change request
1131 *
1132 * Handles hw requirement to indicate intention to enable
1133 * or disable target queue.
1134 **/
i40e_pre_tx_queue_cfg(struct i40e_hw * hw,u32 queue,bool enable)1135 void i40e_pre_tx_queue_cfg(struct i40e_hw *hw, u32 queue, bool enable)
1136 {
1137 u32 abs_queue_idx = hw->func_caps.base_queue + queue;
1138 u32 reg_block = 0;
1139 u32 reg_val;
1140
1141 if (abs_queue_idx >= 128) {
1142 reg_block = abs_queue_idx / 128;
1143 abs_queue_idx %= 128;
1144 }
1145
1146 reg_val = rd32(hw, I40E_GLLAN_TXPRE_QDIS(reg_block));
1147 reg_val &= ~I40E_GLLAN_TXPRE_QDIS_QINDX_MASK;
1148 reg_val |= (abs_queue_idx << I40E_GLLAN_TXPRE_QDIS_QINDX_SHIFT);
1149
1150 if (enable)
1151 reg_val |= I40E_GLLAN_TXPRE_QDIS_CLEAR_QDIS_MASK;
1152 else
1153 reg_val |= I40E_GLLAN_TXPRE_QDIS_SET_QDIS_MASK;
1154
1155 wr32(hw, I40E_GLLAN_TXPRE_QDIS(reg_block), reg_val);
1156 }
1157
1158 /**
1159 * i40e_read_pba_string - Reads part number string from EEPROM
1160 * @hw: pointer to hardware structure
1161 * @pba_num: stores the part number string from the EEPROM
1162 * @pba_num_size: part number string buffer length
1163 *
1164 * Reads the part number string from the EEPROM.
1165 **/
i40e_read_pba_string(struct i40e_hw * hw,u8 * pba_num,u32 pba_num_size)1166 enum i40e_status_code i40e_read_pba_string(struct i40e_hw *hw, u8 *pba_num,
1167 u32 pba_num_size)
1168 {
1169 enum i40e_status_code status = I40E_SUCCESS;
1170 u16 pba_word = 0;
1171 u16 pba_size = 0;
1172 u16 pba_ptr = 0;
1173 u16 i = 0;
1174
1175 status = i40e_read_nvm_word(hw, I40E_SR_PBA_FLAGS, &pba_word);
1176 if ((status != I40E_SUCCESS) || (pba_word != 0xFAFA)) {
1177 DEBUGOUT("Failed to read PBA flags or flag is invalid.\n");
1178 return status;
1179 }
1180
1181 status = i40e_read_nvm_word(hw, I40E_SR_PBA_BLOCK_PTR, &pba_ptr);
1182 if (status != I40E_SUCCESS) {
1183 DEBUGOUT("Failed to read PBA Block pointer.\n");
1184 return status;
1185 }
1186
1187 status = i40e_read_nvm_word(hw, pba_ptr, &pba_size);
1188 if (status != I40E_SUCCESS) {
1189 DEBUGOUT("Failed to read PBA Block size.\n");
1190 return status;
1191 }
1192
1193 /* Subtract one to get PBA word count (PBA Size word is included in
1194 * total size)
1195 */
1196 pba_size--;
1197 if (pba_num_size < (((u32)pba_size * 2) + 1)) {
1198 DEBUGOUT("Buffer to small for PBA data.\n");
1199 return I40E_ERR_PARAM;
1200 }
1201
1202 for (i = 0; i < pba_size; i++) {
1203 status = i40e_read_nvm_word(hw, (pba_ptr + 1) + i, &pba_word);
1204 if (status != I40E_SUCCESS) {
1205 DEBUGOUT1("Failed to read PBA Block word %d.\n", i);
1206 return status;
1207 }
1208
1209 pba_num[(i * 2)] = (pba_word >> 8) & 0xFF;
1210 pba_num[(i * 2) + 1] = pba_word & 0xFF;
1211 }
1212 pba_num[(pba_size * 2)] = '\0';
1213
1214 return status;
1215 }
1216
1217 /**
1218 * i40e_get_media_type - Gets media type
1219 * @hw: pointer to the hardware structure
1220 **/
i40e_get_media_type(struct i40e_hw * hw)1221 static enum i40e_media_type i40e_get_media_type(struct i40e_hw *hw)
1222 {
1223 enum i40e_media_type media;
1224
1225 switch (hw->phy.link_info.phy_type) {
1226 case I40E_PHY_TYPE_10GBASE_SR:
1227 case I40E_PHY_TYPE_10GBASE_LR:
1228 case I40E_PHY_TYPE_1000BASE_SX:
1229 case I40E_PHY_TYPE_1000BASE_LX:
1230 case I40E_PHY_TYPE_40GBASE_SR4:
1231 case I40E_PHY_TYPE_40GBASE_LR4:
1232 case I40E_PHY_TYPE_25GBASE_LR:
1233 case I40E_PHY_TYPE_25GBASE_SR:
1234 media = I40E_MEDIA_TYPE_FIBER;
1235 break;
1236 case I40E_PHY_TYPE_100BASE_TX:
1237 case I40E_PHY_TYPE_1000BASE_T:
1238 case I40E_PHY_TYPE_10GBASE_T:
1239 media = I40E_MEDIA_TYPE_BASET;
1240 break;
1241 case I40E_PHY_TYPE_10GBASE_CR1_CU:
1242 case I40E_PHY_TYPE_40GBASE_CR4_CU:
1243 case I40E_PHY_TYPE_10GBASE_CR1:
1244 case I40E_PHY_TYPE_40GBASE_CR4:
1245 case I40E_PHY_TYPE_10GBASE_SFPP_CU:
1246 case I40E_PHY_TYPE_40GBASE_AOC:
1247 case I40E_PHY_TYPE_10GBASE_AOC:
1248 case I40E_PHY_TYPE_25GBASE_CR:
1249 case I40E_PHY_TYPE_25GBASE_AOC:
1250 case I40E_PHY_TYPE_25GBASE_ACC:
1251 media = I40E_MEDIA_TYPE_DA;
1252 break;
1253 case I40E_PHY_TYPE_1000BASE_KX:
1254 case I40E_PHY_TYPE_10GBASE_KX4:
1255 case I40E_PHY_TYPE_10GBASE_KR:
1256 case I40E_PHY_TYPE_40GBASE_KR4:
1257 case I40E_PHY_TYPE_20GBASE_KR2:
1258 case I40E_PHY_TYPE_25GBASE_KR:
1259 media = I40E_MEDIA_TYPE_BACKPLANE;
1260 break;
1261 case I40E_PHY_TYPE_SGMII:
1262 case I40E_PHY_TYPE_XAUI:
1263 case I40E_PHY_TYPE_XFI:
1264 case I40E_PHY_TYPE_XLAUI:
1265 case I40E_PHY_TYPE_XLPPI:
1266 default:
1267 media = I40E_MEDIA_TYPE_UNKNOWN;
1268 break;
1269 }
1270
1271 return media;
1272 }
1273
1274 #define I40E_PF_RESET_WAIT_COUNT 200
1275 /**
1276 * i40e_pf_reset - Reset the PF
1277 * @hw: pointer to the hardware structure
1278 *
1279 * Assuming someone else has triggered a global reset,
1280 * assure the global reset is complete and then reset the PF
1281 **/
i40e_pf_reset(struct i40e_hw * hw)1282 enum i40e_status_code i40e_pf_reset(struct i40e_hw *hw)
1283 {
1284 u32 cnt = 0;
1285 u32 cnt1 = 0;
1286 u32 reg = 0;
1287 u32 grst_del;
1288
1289 /* Poll for Global Reset steady state in case of recent GRST.
1290 * The grst delay value is in 100ms units, and we'll wait a
1291 * couple counts longer to be sure we don't just miss the end.
1292 */
1293 grst_del = (rd32(hw, I40E_GLGEN_RSTCTL) &
1294 I40E_GLGEN_RSTCTL_GRSTDEL_MASK) >>
1295 I40E_GLGEN_RSTCTL_GRSTDEL_SHIFT;
1296
1297 grst_del = grst_del * 20;
1298
1299 for (cnt = 0; cnt < grst_del; cnt++) {
1300 reg = rd32(hw, I40E_GLGEN_RSTAT);
1301 if (!(reg & I40E_GLGEN_RSTAT_DEVSTATE_MASK))
1302 break;
1303 i40e_msec_delay(100);
1304 }
1305 if (reg & I40E_GLGEN_RSTAT_DEVSTATE_MASK) {
1306 DEBUGOUT("Global reset polling failed to complete.\n");
1307 return I40E_ERR_RESET_FAILED;
1308 }
1309
1310 /* Now Wait for the FW to be ready */
1311 for (cnt1 = 0; cnt1 < I40E_PF_RESET_WAIT_COUNT; cnt1++) {
1312 reg = rd32(hw, I40E_GLNVM_ULD);
1313 reg &= (I40E_GLNVM_ULD_CONF_CORE_DONE_MASK |
1314 I40E_GLNVM_ULD_CONF_GLOBAL_DONE_MASK);
1315 if (reg == (I40E_GLNVM_ULD_CONF_CORE_DONE_MASK |
1316 I40E_GLNVM_ULD_CONF_GLOBAL_DONE_MASK)) {
1317 DEBUGOUT1("Core and Global modules ready %d\n", cnt1);
1318 break;
1319 }
1320 i40e_msec_delay(10);
1321 }
1322 if (!(reg & (I40E_GLNVM_ULD_CONF_CORE_DONE_MASK |
1323 I40E_GLNVM_ULD_CONF_GLOBAL_DONE_MASK))) {
1324 DEBUGOUT("wait for FW Reset complete timedout\n");
1325 DEBUGOUT1("I40E_GLNVM_ULD = 0x%x\n", reg);
1326 return I40E_ERR_RESET_FAILED;
1327 }
1328
1329 /* If there was a Global Reset in progress when we got here,
1330 * we don't need to do the PF Reset
1331 */
1332 if (!cnt) {
1333 u32 reg2 = 0;
1334
1335 reg = rd32(hw, I40E_PFGEN_CTRL);
1336 wr32(hw, I40E_PFGEN_CTRL,
1337 (reg | I40E_PFGEN_CTRL_PFSWR_MASK));
1338 for (cnt = 0; cnt < I40E_PF_RESET_WAIT_COUNT; cnt++) {
1339 reg = rd32(hw, I40E_PFGEN_CTRL);
1340 if (!(reg & I40E_PFGEN_CTRL_PFSWR_MASK))
1341 break;
1342 reg2 = rd32(hw, I40E_GLGEN_RSTAT);
1343 if (reg2 & I40E_GLGEN_RSTAT_DEVSTATE_MASK) {
1344 DEBUGOUT("Core reset upcoming. Skipping PF reset request.\n");
1345 DEBUGOUT1("I40E_GLGEN_RSTAT = 0x%x\n", reg2);
1346 return I40E_ERR_NOT_READY;
1347 }
1348 i40e_msec_delay(1);
1349 }
1350 if (reg & I40E_PFGEN_CTRL_PFSWR_MASK) {
1351 DEBUGOUT("PF reset polling failed to complete.\n");
1352 return I40E_ERR_RESET_FAILED;
1353 }
1354 }
1355
1356 i40e_clear_pxe_mode(hw);
1357
1358
1359 return I40E_SUCCESS;
1360 }
1361
1362 /**
1363 * i40e_clear_hw - clear out any left over hw state
1364 * @hw: pointer to the hw struct
1365 *
1366 * Clear queues and interrupts, typically called at init time,
1367 * but after the capabilities have been found so we know how many
1368 * queues and msix vectors have been allocated.
1369 **/
i40e_clear_hw(struct i40e_hw * hw)1370 void i40e_clear_hw(struct i40e_hw *hw)
1371 {
1372 u32 num_queues, base_queue;
1373 u32 num_pf_int;
1374 u32 num_vf_int;
1375 u32 num_vfs;
1376 u32 i, j;
1377 u32 val;
1378 u32 eol = 0x7ff;
1379
1380 /* get number of interrupts, queues, and vfs */
1381 val = rd32(hw, I40E_GLPCI_CNF2);
1382 num_pf_int = (val & I40E_GLPCI_CNF2_MSI_X_PF_N_MASK) >>
1383 I40E_GLPCI_CNF2_MSI_X_PF_N_SHIFT;
1384 num_vf_int = (val & I40E_GLPCI_CNF2_MSI_X_VF_N_MASK) >>
1385 I40E_GLPCI_CNF2_MSI_X_VF_N_SHIFT;
1386
1387 val = rd32(hw, I40E_PFLAN_QALLOC);
1388 base_queue = (val & I40E_PFLAN_QALLOC_FIRSTQ_MASK) >>
1389 I40E_PFLAN_QALLOC_FIRSTQ_SHIFT;
1390 j = (val & I40E_PFLAN_QALLOC_LASTQ_MASK) >>
1391 I40E_PFLAN_QALLOC_LASTQ_SHIFT;
1392 if (val & I40E_PFLAN_QALLOC_VALID_MASK)
1393 num_queues = (j - base_queue) + 1;
1394 else
1395 num_queues = 0;
1396
1397 val = rd32(hw, I40E_PF_VT_PFALLOC);
1398 i = (val & I40E_PF_VT_PFALLOC_FIRSTVF_MASK) >>
1399 I40E_PF_VT_PFALLOC_FIRSTVF_SHIFT;
1400 j = (val & I40E_PF_VT_PFALLOC_LASTVF_MASK) >>
1401 I40E_PF_VT_PFALLOC_LASTVF_SHIFT;
1402 if (val & I40E_PF_VT_PFALLOC_VALID_MASK)
1403 num_vfs = (j - i) + 1;
1404 else
1405 num_vfs = 0;
1406
1407 /* stop all the interrupts */
1408 wr32(hw, I40E_PFINT_ICR0_ENA, 0);
1409 val = 0x3 << I40E_PFINT_DYN_CTLN_ITR_INDX_SHIFT;
1410 for (i = 0; i < num_pf_int - 2; i++)
1411 wr32(hw, I40E_PFINT_DYN_CTLN(i), val);
1412
1413 /* Set the FIRSTQ_INDX field to 0x7FF in PFINT_LNKLSTx */
1414 val = eol << I40E_PFINT_LNKLST0_FIRSTQ_INDX_SHIFT;
1415 wr32(hw, I40E_PFINT_LNKLST0, val);
1416 for (i = 0; i < num_pf_int - 2; i++)
1417 wr32(hw, I40E_PFINT_LNKLSTN(i), val);
1418 val = eol << I40E_VPINT_LNKLST0_FIRSTQ_INDX_SHIFT;
1419 for (i = 0; i < num_vfs; i++)
1420 wr32(hw, I40E_VPINT_LNKLST0(i), val);
1421 for (i = 0; i < num_vf_int - 2; i++)
1422 wr32(hw, I40E_VPINT_LNKLSTN(i), val);
1423
1424 /* warn the HW of the coming Tx disables */
1425 for (i = 0; i < num_queues; i++) {
1426 u32 abs_queue_idx = base_queue + i;
1427 u32 reg_block = 0;
1428
1429 if (abs_queue_idx >= 128) {
1430 reg_block = abs_queue_idx / 128;
1431 abs_queue_idx %= 128;
1432 }
1433
1434 val = rd32(hw, I40E_GLLAN_TXPRE_QDIS(reg_block));
1435 val &= ~I40E_GLLAN_TXPRE_QDIS_QINDX_MASK;
1436 val |= (abs_queue_idx << I40E_GLLAN_TXPRE_QDIS_QINDX_SHIFT);
1437 val |= I40E_GLLAN_TXPRE_QDIS_SET_QDIS_MASK;
1438
1439 wr32(hw, I40E_GLLAN_TXPRE_QDIS(reg_block), val);
1440 }
1441 i40e_usec_delay(400);
1442
1443 /* stop all the queues */
1444 for (i = 0; i < num_queues; i++) {
1445 wr32(hw, I40E_QINT_TQCTL(i), 0);
1446 wr32(hw, I40E_QTX_ENA(i), 0);
1447 wr32(hw, I40E_QINT_RQCTL(i), 0);
1448 wr32(hw, I40E_QRX_ENA(i), 0);
1449 }
1450
1451 /* short wait for all queue disables to settle */
1452 i40e_usec_delay(50);
1453 }
1454
1455 /**
1456 * i40e_clear_pxe_mode - clear pxe operations mode
1457 * @hw: pointer to the hw struct
1458 *
1459 * Make sure all PXE mode settings are cleared, including things
1460 * like descriptor fetch/write-back mode.
1461 **/
i40e_clear_pxe_mode(struct i40e_hw * hw)1462 void i40e_clear_pxe_mode(struct i40e_hw *hw)
1463 {
1464 if (i40e_check_asq_alive(hw))
1465 i40e_aq_clear_pxe_mode(hw, NULL);
1466 }
1467
1468 /**
1469 * i40e_led_is_mine - helper to find matching led
1470 * @hw: pointer to the hw struct
1471 * @idx: index into GPIO registers
1472 *
1473 * returns: 0 if no match, otherwise the value of the GPIO_CTL register
1474 */
i40e_led_is_mine(struct i40e_hw * hw,int idx)1475 static u32 i40e_led_is_mine(struct i40e_hw *hw, int idx)
1476 {
1477 u32 gpio_val = 0;
1478 u32 port;
1479
1480 if (!hw->func_caps.led[idx])
1481 return 0;
1482
1483 gpio_val = rd32(hw, I40E_GLGEN_GPIO_CTL(idx));
1484 port = (gpio_val & I40E_GLGEN_GPIO_CTL_PRT_NUM_MASK) >>
1485 I40E_GLGEN_GPIO_CTL_PRT_NUM_SHIFT;
1486
1487 /* if PRT_NUM_NA is 1 then this LED is not port specific, OR
1488 * if it is not our port then ignore
1489 */
1490 if ((gpio_val & I40E_GLGEN_GPIO_CTL_PRT_NUM_NA_MASK) ||
1491 (port != hw->port))
1492 return 0;
1493
1494 return gpio_val;
1495 }
1496
1497 #define I40E_COMBINED_ACTIVITY 0xA
1498 #define I40E_FILTER_ACTIVITY 0xE
1499 #define I40E_LINK_ACTIVITY 0xC
1500 #define I40E_MAC_ACTIVITY 0xD
1501 #define I40E_LED0 22
1502
1503 /**
1504 * i40e_led_get - return current on/off mode
1505 * @hw: pointer to the hw struct
1506 *
1507 * The value returned is the 'mode' field as defined in the
1508 * GPIO register definitions: 0x0 = off, 0xf = on, and other
1509 * values are variations of possible behaviors relating to
1510 * blink, link, and wire.
1511 **/
i40e_led_get(struct i40e_hw * hw)1512 u32 i40e_led_get(struct i40e_hw *hw)
1513 {
1514 u32 current_mode = 0;
1515 u32 mode = 0;
1516 int i;
1517
1518 /* as per the documentation GPIO 22-29 are the LED
1519 * GPIO pins named LED0..LED7
1520 */
1521 for (i = I40E_LED0; i <= I40E_GLGEN_GPIO_CTL_MAX_INDEX; i++) {
1522 u32 gpio_val = i40e_led_is_mine(hw, i);
1523
1524 if (!gpio_val)
1525 continue;
1526
1527 /* ignore gpio LED src mode entries related to the activity
1528 * LEDs
1529 */
1530 current_mode = ((gpio_val & I40E_GLGEN_GPIO_CTL_LED_MODE_MASK)
1531 >> I40E_GLGEN_GPIO_CTL_LED_MODE_SHIFT);
1532 switch (current_mode) {
1533 case I40E_COMBINED_ACTIVITY:
1534 case I40E_FILTER_ACTIVITY:
1535 case I40E_MAC_ACTIVITY:
1536 case I40E_LINK_ACTIVITY:
1537 continue;
1538 default:
1539 break;
1540 }
1541
1542 mode = (gpio_val & I40E_GLGEN_GPIO_CTL_LED_MODE_MASK) >>
1543 I40E_GLGEN_GPIO_CTL_LED_MODE_SHIFT;
1544 break;
1545 }
1546
1547 return mode;
1548 }
1549
1550 /**
1551 * i40e_led_set - set new on/off mode
1552 * @hw: pointer to the hw struct
1553 * @mode: 0=off, 0xf=on (else see manual for mode details)
1554 * @blink: TRUE if the LED should blink when on, FALSE if steady
1555 *
1556 * if this function is used to turn on the blink it should
1557 * be used to disable the blink when restoring the original state.
1558 **/
i40e_led_set(struct i40e_hw * hw,u32 mode,bool blink)1559 void i40e_led_set(struct i40e_hw *hw, u32 mode, bool blink)
1560 {
1561 u32 current_mode = 0;
1562 int i;
1563
1564 if (mode & 0xfffffff0)
1565 DEBUGOUT1("invalid mode passed in %X\n", mode);
1566
1567 /* as per the documentation GPIO 22-29 are the LED
1568 * GPIO pins named LED0..LED7
1569 */
1570 for (i = I40E_LED0; i <= I40E_GLGEN_GPIO_CTL_MAX_INDEX; i++) {
1571 u32 gpio_val = i40e_led_is_mine(hw, i);
1572
1573 if (!gpio_val)
1574 continue;
1575
1576 /* ignore gpio LED src mode entries related to the activity
1577 * LEDs
1578 */
1579 current_mode = ((gpio_val & I40E_GLGEN_GPIO_CTL_LED_MODE_MASK)
1580 >> I40E_GLGEN_GPIO_CTL_LED_MODE_SHIFT);
1581 switch (current_mode) {
1582 case I40E_COMBINED_ACTIVITY:
1583 case I40E_FILTER_ACTIVITY:
1584 case I40E_MAC_ACTIVITY:
1585 case I40E_LINK_ACTIVITY:
1586 continue;
1587 default:
1588 break;
1589 }
1590
1591 gpio_val &= ~I40E_GLGEN_GPIO_CTL_LED_MODE_MASK;
1592 /* this & is a bit of paranoia, but serves as a range check */
1593 gpio_val |= ((mode << I40E_GLGEN_GPIO_CTL_LED_MODE_SHIFT) &
1594 I40E_GLGEN_GPIO_CTL_LED_MODE_MASK);
1595
1596 if (blink)
1597 gpio_val |= BIT(I40E_GLGEN_GPIO_CTL_LED_BLINK_SHIFT);
1598 else
1599 gpio_val &= ~BIT(I40E_GLGEN_GPIO_CTL_LED_BLINK_SHIFT);
1600
1601 wr32(hw, I40E_GLGEN_GPIO_CTL(i), gpio_val);
1602 break;
1603 }
1604 }
1605
1606 /* Admin command wrappers */
1607
1608 /**
1609 * i40e_aq_get_phy_capabilities
1610 * @hw: pointer to the hw struct
1611 * @abilities: structure for PHY capabilities to be filled
1612 * @qualified_modules: report Qualified Modules
1613 * @report_init: report init capabilities (active are default)
1614 * @cmd_details: pointer to command details structure or NULL
1615 *
1616 * Returns the various PHY abilities supported on the Port.
1617 **/
i40e_aq_get_phy_capabilities(struct i40e_hw * hw,bool qualified_modules,bool report_init,struct i40e_aq_get_phy_abilities_resp * abilities,struct i40e_asq_cmd_details * cmd_details)1618 enum i40e_status_code i40e_aq_get_phy_capabilities(struct i40e_hw *hw,
1619 bool qualified_modules, bool report_init,
1620 struct i40e_aq_get_phy_abilities_resp *abilities,
1621 struct i40e_asq_cmd_details *cmd_details)
1622 {
1623 struct i40e_aq_desc desc;
1624 enum i40e_status_code status;
1625 u16 max_delay = I40E_MAX_PHY_TIMEOUT, total_delay = 0;
1626 u16 abilities_size = sizeof(struct i40e_aq_get_phy_abilities_resp);
1627
1628 if (!abilities)
1629 return I40E_ERR_PARAM;
1630
1631 do {
1632 i40e_fill_default_direct_cmd_desc(&desc,
1633 i40e_aqc_opc_get_phy_abilities);
1634
1635 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
1636 if (abilities_size > I40E_AQ_LARGE_BUF)
1637 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
1638
1639 if (qualified_modules)
1640 desc.params.external.param0 |=
1641 CPU_TO_LE32(I40E_AQ_PHY_REPORT_QUALIFIED_MODULES);
1642
1643 if (report_init)
1644 desc.params.external.param0 |=
1645 CPU_TO_LE32(I40E_AQ_PHY_REPORT_INITIAL_VALUES);
1646
1647 status = i40e_asq_send_command(hw, &desc, abilities,
1648 abilities_size, cmd_details);
1649
1650 if (status != I40E_SUCCESS)
1651 break;
1652
1653 if (hw->aq.asq_last_status == I40E_AQ_RC_EIO) {
1654 status = I40E_ERR_UNKNOWN_PHY;
1655 break;
1656 } else if (hw->aq.asq_last_status == I40E_AQ_RC_EAGAIN) {
1657 i40e_msec_delay(1);
1658 total_delay++;
1659 status = I40E_ERR_TIMEOUT;
1660 }
1661 } while ((hw->aq.asq_last_status != I40E_AQ_RC_OK) &&
1662 (total_delay < max_delay));
1663
1664 if (status != I40E_SUCCESS)
1665 return status;
1666
1667 if (report_init) {
1668 if (hw->mac.type == I40E_MAC_XL710 &&
1669 hw->aq.api_maj_ver == I40E_FW_API_VERSION_MAJOR &&
1670 hw->aq.api_min_ver >= I40E_MINOR_VER_GET_LINK_INFO_XL710) {
1671 status = i40e_aq_get_link_info(hw, TRUE, NULL, NULL);
1672 } else {
1673 hw->phy.phy_types = LE32_TO_CPU(abilities->phy_type);
1674 hw->phy.phy_types |=
1675 ((u64)abilities->phy_type_ext << 32);
1676 }
1677 }
1678
1679 return status;
1680 }
1681
1682 /**
1683 * i40e_aq_set_phy_config
1684 * @hw: pointer to the hw struct
1685 * @config: structure with PHY configuration to be set
1686 * @cmd_details: pointer to command details structure or NULL
1687 *
1688 * Set the various PHY configuration parameters
1689 * supported on the Port.One or more of the Set PHY config parameters may be
1690 * ignored in an MFP mode as the PF may not have the privilege to set some
1691 * of the PHY Config parameters. This status will be indicated by the
1692 * command response.
1693 **/
i40e_aq_set_phy_config(struct i40e_hw * hw,struct i40e_aq_set_phy_config * config,struct i40e_asq_cmd_details * cmd_details)1694 enum i40e_status_code i40e_aq_set_phy_config(struct i40e_hw *hw,
1695 struct i40e_aq_set_phy_config *config,
1696 struct i40e_asq_cmd_details *cmd_details)
1697 {
1698 struct i40e_aq_desc desc;
1699 struct i40e_aq_set_phy_config *cmd =
1700 (struct i40e_aq_set_phy_config *)&desc.params.raw;
1701 enum i40e_status_code status;
1702
1703 if (!config)
1704 return I40E_ERR_PARAM;
1705
1706 i40e_fill_default_direct_cmd_desc(&desc,
1707 i40e_aqc_opc_set_phy_config);
1708
1709 *cmd = *config;
1710
1711 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
1712
1713 return status;
1714 }
1715
1716 /**
1717 * i40e_set_fc
1718 * @hw: pointer to the hw struct
1719 * @aq_failures: buffer to return AdminQ failure information
1720 * @atomic_restart: whether to enable atomic link restart
1721 *
1722 * Set the requested flow control mode using set_phy_config.
1723 **/
i40e_set_fc(struct i40e_hw * hw,u8 * aq_failures,bool atomic_restart)1724 enum i40e_status_code i40e_set_fc(struct i40e_hw *hw, u8 *aq_failures,
1725 bool atomic_restart)
1726 {
1727 enum i40e_fc_mode fc_mode = hw->fc.requested_mode;
1728 struct i40e_aq_get_phy_abilities_resp abilities;
1729 struct i40e_aq_set_phy_config config;
1730 enum i40e_status_code status;
1731 u8 pause_mask = 0x0;
1732
1733 *aq_failures = 0x0;
1734
1735 switch (fc_mode) {
1736 case I40E_FC_FULL:
1737 pause_mask |= I40E_AQ_PHY_FLAG_PAUSE_TX;
1738 pause_mask |= I40E_AQ_PHY_FLAG_PAUSE_RX;
1739 break;
1740 case I40E_FC_RX_PAUSE:
1741 pause_mask |= I40E_AQ_PHY_FLAG_PAUSE_RX;
1742 break;
1743 case I40E_FC_TX_PAUSE:
1744 pause_mask |= I40E_AQ_PHY_FLAG_PAUSE_TX;
1745 break;
1746 default:
1747 break;
1748 }
1749
1750 /* Get the current phy config */
1751 status = i40e_aq_get_phy_capabilities(hw, FALSE, false, &abilities,
1752 NULL);
1753 if (status) {
1754 *aq_failures |= I40E_SET_FC_AQ_FAIL_GET;
1755 return status;
1756 }
1757
1758 memset(&config, 0, sizeof(config));
1759 /* clear the old pause settings */
1760 config.abilities = abilities.abilities & ~(I40E_AQ_PHY_FLAG_PAUSE_TX) &
1761 ~(I40E_AQ_PHY_FLAG_PAUSE_RX);
1762 /* set the new abilities */
1763 config.abilities |= pause_mask;
1764 /* If the abilities have changed, then set the new config */
1765 if (config.abilities != abilities.abilities) {
1766 /* Auto restart link so settings take effect */
1767 if (atomic_restart)
1768 config.abilities |= I40E_AQ_PHY_ENABLE_ATOMIC_LINK;
1769 /* Copy over all the old settings */
1770 config.phy_type = abilities.phy_type;
1771 config.phy_type_ext = abilities.phy_type_ext;
1772 config.link_speed = abilities.link_speed;
1773 config.eee_capability = abilities.eee_capability;
1774 config.eeer = abilities.eeer_val;
1775 config.low_power_ctrl = abilities.d3_lpan;
1776 config.fec_config = abilities.fec_cfg_curr_mod_ext_info &
1777 I40E_AQ_PHY_FEC_CONFIG_MASK;
1778 status = i40e_aq_set_phy_config(hw, &config, NULL);
1779
1780 if (status)
1781 *aq_failures |= I40E_SET_FC_AQ_FAIL_SET;
1782 }
1783 /* Update the link info */
1784 status = i40e_update_link_info(hw);
1785 if (status) {
1786 /* Wait a little bit (on 40G cards it sometimes takes a really
1787 * long time for link to come back from the atomic reset)
1788 * and try once more
1789 */
1790 i40e_msec_delay(1000);
1791 status = i40e_update_link_info(hw);
1792 }
1793 if (status)
1794 *aq_failures |= I40E_SET_FC_AQ_FAIL_UPDATE;
1795
1796 return status;
1797 }
1798
1799 /**
1800 * i40e_aq_set_mac_config
1801 * @hw: pointer to the hw struct
1802 * @max_frame_size: Maximum Frame Size to be supported by the port
1803 * @crc_en: Tell HW to append a CRC to outgoing frames
1804 * @pacing: Pacing configurations
1805 * @cmd_details: pointer to command details structure or NULL
1806 *
1807 * Configure MAC settings for frame size, jumbo frame support and the
1808 * addition of a CRC by the hardware.
1809 **/
i40e_aq_set_mac_config(struct i40e_hw * hw,u16 max_frame_size,bool crc_en,u16 pacing,struct i40e_asq_cmd_details * cmd_details)1810 enum i40e_status_code i40e_aq_set_mac_config(struct i40e_hw *hw,
1811 u16 max_frame_size,
1812 bool crc_en, u16 pacing,
1813 struct i40e_asq_cmd_details *cmd_details)
1814 {
1815 struct i40e_aq_desc desc;
1816 struct i40e_aq_set_mac_config *cmd =
1817 (struct i40e_aq_set_mac_config *)&desc.params.raw;
1818 enum i40e_status_code status;
1819
1820 if (max_frame_size == 0)
1821 return I40E_ERR_PARAM;
1822
1823 i40e_fill_default_direct_cmd_desc(&desc,
1824 i40e_aqc_opc_set_mac_config);
1825
1826 cmd->max_frame_size = CPU_TO_LE16(max_frame_size);
1827 cmd->params = ((u8)pacing & 0x0F) << 3;
1828 if (crc_en)
1829 cmd->params |= I40E_AQ_SET_MAC_CONFIG_CRC_EN;
1830
1831 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
1832
1833 return status;
1834 }
1835
1836 /**
1837 * i40e_aq_clear_pxe_mode
1838 * @hw: pointer to the hw struct
1839 * @cmd_details: pointer to command details structure or NULL
1840 *
1841 * Tell the firmware that the driver is taking over from PXE
1842 **/
i40e_aq_clear_pxe_mode(struct i40e_hw * hw,struct i40e_asq_cmd_details * cmd_details)1843 enum i40e_status_code i40e_aq_clear_pxe_mode(struct i40e_hw *hw,
1844 struct i40e_asq_cmd_details *cmd_details)
1845 {
1846 enum i40e_status_code status;
1847 struct i40e_aq_desc desc;
1848 struct i40e_aqc_clear_pxe *cmd =
1849 (struct i40e_aqc_clear_pxe *)&desc.params.raw;
1850
1851 i40e_fill_default_direct_cmd_desc(&desc,
1852 i40e_aqc_opc_clear_pxe_mode);
1853
1854 cmd->rx_cnt = 0x2;
1855
1856 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
1857
1858 wr32(hw, I40E_GLLAN_RCTL_0, 0x1);
1859
1860 return status;
1861 }
1862
1863 /**
1864 * i40e_aq_set_link_restart_an
1865 * @hw: pointer to the hw struct
1866 * @enable_link: if TRUE: enable link, if FALSE: disable link
1867 * @cmd_details: pointer to command details structure or NULL
1868 *
1869 * Sets up the link and restarts the Auto-Negotiation over the link.
1870 **/
i40e_aq_set_link_restart_an(struct i40e_hw * hw,bool enable_link,struct i40e_asq_cmd_details * cmd_details)1871 enum i40e_status_code i40e_aq_set_link_restart_an(struct i40e_hw *hw,
1872 bool enable_link, struct i40e_asq_cmd_details *cmd_details)
1873 {
1874 struct i40e_aq_desc desc;
1875 struct i40e_aqc_set_link_restart_an *cmd =
1876 (struct i40e_aqc_set_link_restart_an *)&desc.params.raw;
1877 enum i40e_status_code status;
1878
1879 i40e_fill_default_direct_cmd_desc(&desc,
1880 i40e_aqc_opc_set_link_restart_an);
1881
1882 cmd->command = I40E_AQ_PHY_RESTART_AN;
1883 if (enable_link)
1884 cmd->command |= I40E_AQ_PHY_LINK_ENABLE;
1885 else
1886 cmd->command &= ~I40E_AQ_PHY_LINK_ENABLE;
1887
1888 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
1889
1890 return status;
1891 }
1892
1893 /**
1894 * i40e_aq_get_link_info
1895 * @hw: pointer to the hw struct
1896 * @enable_lse: enable/disable LinkStatusEvent reporting
1897 * @link: pointer to link status structure - optional
1898 * @cmd_details: pointer to command details structure or NULL
1899 *
1900 * Returns the link status of the adapter.
1901 **/
i40e_aq_get_link_info(struct i40e_hw * hw,bool enable_lse,struct i40e_link_status * link,struct i40e_asq_cmd_details * cmd_details)1902 enum i40e_status_code i40e_aq_get_link_info(struct i40e_hw *hw,
1903 bool enable_lse, struct i40e_link_status *link,
1904 struct i40e_asq_cmd_details *cmd_details)
1905 {
1906 struct i40e_aq_desc desc;
1907 struct i40e_aqc_get_link_status *resp =
1908 (struct i40e_aqc_get_link_status *)&desc.params.raw;
1909 struct i40e_link_status *hw_link_info = &hw->phy.link_info;
1910 enum i40e_status_code status;
1911 bool tx_pause, rx_pause;
1912 u16 command_flags;
1913
1914 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_get_link_status);
1915
1916 if (enable_lse)
1917 command_flags = I40E_AQ_LSE_ENABLE;
1918 else
1919 command_flags = I40E_AQ_LSE_DISABLE;
1920 resp->command_flags = CPU_TO_LE16(command_flags);
1921
1922 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
1923
1924 if (status != I40E_SUCCESS)
1925 goto aq_get_link_info_exit;
1926
1927 /* save off old link status information */
1928 i40e_memcpy(&hw->phy.link_info_old, hw_link_info,
1929 sizeof(*hw_link_info), I40E_NONDMA_TO_NONDMA);
1930
1931 /* update link status */
1932 hw_link_info->phy_type = (enum i40e_aq_phy_type)resp->phy_type;
1933 hw->phy.media_type = i40e_get_media_type(hw);
1934 hw_link_info->link_speed = (enum i40e_aq_link_speed)resp->link_speed;
1935 hw_link_info->link_info = resp->link_info;
1936 hw_link_info->an_info = resp->an_info;
1937 hw_link_info->fec_info = resp->config & (I40E_AQ_CONFIG_FEC_KR_ENA |
1938 I40E_AQ_CONFIG_FEC_RS_ENA);
1939 hw_link_info->ext_info = resp->ext_info;
1940 hw_link_info->loopback = resp->loopback & I40E_AQ_LOOPBACK_MASK;
1941 hw_link_info->max_frame_size = LE16_TO_CPU(resp->max_frame_size);
1942 hw_link_info->pacing = resp->config & I40E_AQ_CONFIG_PACING_MASK;
1943
1944 /* update fc info */
1945 tx_pause = !!(resp->an_info & I40E_AQ_LINK_PAUSE_TX);
1946 rx_pause = !!(resp->an_info & I40E_AQ_LINK_PAUSE_RX);
1947 if (tx_pause & rx_pause)
1948 hw->fc.current_mode = I40E_FC_FULL;
1949 else if (tx_pause)
1950 hw->fc.current_mode = I40E_FC_TX_PAUSE;
1951 else if (rx_pause)
1952 hw->fc.current_mode = I40E_FC_RX_PAUSE;
1953 else
1954 hw->fc.current_mode = I40E_FC_NONE;
1955
1956 if (resp->config & I40E_AQ_CONFIG_CRC_ENA)
1957 hw_link_info->crc_enable = TRUE;
1958 else
1959 hw_link_info->crc_enable = FALSE;
1960
1961 if (resp->command_flags & CPU_TO_LE16(I40E_AQ_LSE_IS_ENABLED))
1962 hw_link_info->lse_enable = TRUE;
1963 else
1964 hw_link_info->lse_enable = FALSE;
1965
1966 if ((hw->mac.type == I40E_MAC_XL710) &&
1967 (hw->aq.fw_maj_ver < 4 || (hw->aq.fw_maj_ver == 4 &&
1968 hw->aq.fw_min_ver < 40)) && hw_link_info->phy_type == 0xE)
1969 hw_link_info->phy_type = I40E_PHY_TYPE_10GBASE_SFPP_CU;
1970
1971 if (hw->aq.api_maj_ver == I40E_FW_API_VERSION_MAJOR &&
1972 hw->aq.api_min_ver >= 7) {
1973 __le32 tmp;
1974
1975 i40e_memcpy(&tmp, resp->link_type, sizeof(tmp),
1976 I40E_NONDMA_TO_NONDMA);
1977 hw->phy.phy_types = LE32_TO_CPU(tmp);
1978 hw->phy.phy_types |= ((u64)resp->link_type_ext << 32);
1979 }
1980
1981 /* save link status information */
1982 if (link)
1983 i40e_memcpy(link, hw_link_info, sizeof(*hw_link_info),
1984 I40E_NONDMA_TO_NONDMA);
1985
1986 /* flag cleared so helper functions don't call AQ again */
1987 hw->phy.get_link_info = FALSE;
1988
1989 aq_get_link_info_exit:
1990 return status;
1991 }
1992
1993 /**
1994 * i40e_aq_set_phy_int_mask
1995 * @hw: pointer to the hw struct
1996 * @mask: interrupt mask to be set
1997 * @cmd_details: pointer to command details structure or NULL
1998 *
1999 * Set link interrupt mask.
2000 **/
i40e_aq_set_phy_int_mask(struct i40e_hw * hw,u16 mask,struct i40e_asq_cmd_details * cmd_details)2001 enum i40e_status_code i40e_aq_set_phy_int_mask(struct i40e_hw *hw,
2002 u16 mask,
2003 struct i40e_asq_cmd_details *cmd_details)
2004 {
2005 struct i40e_aq_desc desc;
2006 struct i40e_aqc_set_phy_int_mask *cmd =
2007 (struct i40e_aqc_set_phy_int_mask *)&desc.params.raw;
2008 enum i40e_status_code status;
2009
2010 i40e_fill_default_direct_cmd_desc(&desc,
2011 i40e_aqc_opc_set_phy_int_mask);
2012
2013 cmd->event_mask = CPU_TO_LE16(mask);
2014
2015 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2016
2017 return status;
2018 }
2019
2020 /**
2021 * i40e_aq_get_local_advt_reg
2022 * @hw: pointer to the hw struct
2023 * @advt_reg: local AN advertisement register value
2024 * @cmd_details: pointer to command details structure or NULL
2025 *
2026 * Get the Local AN advertisement register value.
2027 **/
i40e_aq_get_local_advt_reg(struct i40e_hw * hw,u64 * advt_reg,struct i40e_asq_cmd_details * cmd_details)2028 enum i40e_status_code i40e_aq_get_local_advt_reg(struct i40e_hw *hw,
2029 u64 *advt_reg,
2030 struct i40e_asq_cmd_details *cmd_details)
2031 {
2032 struct i40e_aq_desc desc;
2033 struct i40e_aqc_an_advt_reg *resp =
2034 (struct i40e_aqc_an_advt_reg *)&desc.params.raw;
2035 enum i40e_status_code status;
2036
2037 i40e_fill_default_direct_cmd_desc(&desc,
2038 i40e_aqc_opc_get_local_advt_reg);
2039
2040 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2041
2042 if (status != I40E_SUCCESS)
2043 goto aq_get_local_advt_reg_exit;
2044
2045 *advt_reg = (u64)(LE16_TO_CPU(resp->local_an_reg1)) << 32;
2046 *advt_reg |= LE32_TO_CPU(resp->local_an_reg0);
2047
2048 aq_get_local_advt_reg_exit:
2049 return status;
2050 }
2051
2052 /**
2053 * i40e_aq_set_local_advt_reg
2054 * @hw: pointer to the hw struct
2055 * @advt_reg: local AN advertisement register value
2056 * @cmd_details: pointer to command details structure or NULL
2057 *
2058 * Get the Local AN advertisement register value.
2059 **/
i40e_aq_set_local_advt_reg(struct i40e_hw * hw,u64 advt_reg,struct i40e_asq_cmd_details * cmd_details)2060 enum i40e_status_code i40e_aq_set_local_advt_reg(struct i40e_hw *hw,
2061 u64 advt_reg,
2062 struct i40e_asq_cmd_details *cmd_details)
2063 {
2064 struct i40e_aq_desc desc;
2065 struct i40e_aqc_an_advt_reg *cmd =
2066 (struct i40e_aqc_an_advt_reg *)&desc.params.raw;
2067 enum i40e_status_code status;
2068
2069 i40e_fill_default_direct_cmd_desc(&desc,
2070 i40e_aqc_opc_get_local_advt_reg);
2071
2072 cmd->local_an_reg0 = CPU_TO_LE32(I40E_LO_DWORD(advt_reg));
2073 cmd->local_an_reg1 = CPU_TO_LE16(I40E_HI_DWORD(advt_reg));
2074
2075 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2076
2077 return status;
2078 }
2079
2080 /**
2081 * i40e_aq_get_partner_advt
2082 * @hw: pointer to the hw struct
2083 * @advt_reg: AN partner advertisement register value
2084 * @cmd_details: pointer to command details structure or NULL
2085 *
2086 * Get the link partner AN advertisement register value.
2087 **/
i40e_aq_get_partner_advt(struct i40e_hw * hw,u64 * advt_reg,struct i40e_asq_cmd_details * cmd_details)2088 enum i40e_status_code i40e_aq_get_partner_advt(struct i40e_hw *hw,
2089 u64 *advt_reg,
2090 struct i40e_asq_cmd_details *cmd_details)
2091 {
2092 struct i40e_aq_desc desc;
2093 struct i40e_aqc_an_advt_reg *resp =
2094 (struct i40e_aqc_an_advt_reg *)&desc.params.raw;
2095 enum i40e_status_code status;
2096
2097 i40e_fill_default_direct_cmd_desc(&desc,
2098 i40e_aqc_opc_get_partner_advt);
2099
2100 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2101
2102 if (status != I40E_SUCCESS)
2103 goto aq_get_partner_advt_exit;
2104
2105 *advt_reg = (u64)(LE16_TO_CPU(resp->local_an_reg1)) << 32;
2106 *advt_reg |= LE32_TO_CPU(resp->local_an_reg0);
2107
2108 aq_get_partner_advt_exit:
2109 return status;
2110 }
2111
2112 /**
2113 * i40e_aq_set_lb_modes
2114 * @hw: pointer to the hw struct
2115 * @lb_modes: loopback mode to be set
2116 * @cmd_details: pointer to command details structure or NULL
2117 *
2118 * Sets loopback modes.
2119 **/
2120 enum i40e_status_code
i40e_aq_set_lb_modes(struct i40e_hw * hw,u8 lb_level,u8 lb_type,u8 speed,struct i40e_asq_cmd_details * cmd_details)2121 i40e_aq_set_lb_modes(struct i40e_hw *hw, u8 lb_level, u8 lb_type, u8 speed,
2122 struct i40e_asq_cmd_details *cmd_details)
2123 {
2124 struct i40e_aq_desc desc;
2125 struct i40e_aqc_set_lb_mode *cmd =
2126 (struct i40e_aqc_set_lb_mode *)&desc.params.raw;
2127 enum i40e_status_code status;
2128
2129 i40e_fill_default_direct_cmd_desc(&desc,
2130 i40e_aqc_opc_set_lb_modes);
2131
2132 cmd->lb_level = lb_level;
2133 cmd->lb_type = lb_type;
2134 cmd->speed = speed;
2135 if (speed)
2136 cmd->force_speed = 1;
2137
2138 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2139
2140 return status;
2141 }
2142
2143 /**
2144 * i40e_aq_set_phy_debug
2145 * @hw: pointer to the hw struct
2146 * @cmd_flags: debug command flags
2147 * @cmd_details: pointer to command details structure or NULL
2148 *
2149 * Reset the external PHY.
2150 **/
i40e_aq_set_phy_debug(struct i40e_hw * hw,u8 cmd_flags,struct i40e_asq_cmd_details * cmd_details)2151 enum i40e_status_code i40e_aq_set_phy_debug(struct i40e_hw *hw, u8 cmd_flags,
2152 struct i40e_asq_cmd_details *cmd_details)
2153 {
2154 struct i40e_aq_desc desc;
2155 struct i40e_aqc_set_phy_debug *cmd =
2156 (struct i40e_aqc_set_phy_debug *)&desc.params.raw;
2157 enum i40e_status_code status;
2158
2159 i40e_fill_default_direct_cmd_desc(&desc,
2160 i40e_aqc_opc_set_phy_debug);
2161
2162 cmd->command_flags = cmd_flags;
2163
2164 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2165
2166 return status;
2167 }
2168
2169 /**
2170 * i40e_aq_add_vsi
2171 * @hw: pointer to the hw struct
2172 * @vsi_ctx: pointer to a vsi context struct
2173 * @cmd_details: pointer to command details structure or NULL
2174 *
2175 * Add a VSI context to the hardware.
2176 **/
i40e_aq_add_vsi(struct i40e_hw * hw,struct i40e_vsi_context * vsi_ctx,struct i40e_asq_cmd_details * cmd_details)2177 enum i40e_status_code i40e_aq_add_vsi(struct i40e_hw *hw,
2178 struct i40e_vsi_context *vsi_ctx,
2179 struct i40e_asq_cmd_details *cmd_details)
2180 {
2181 struct i40e_aq_desc desc;
2182 struct i40e_aqc_add_get_update_vsi *cmd =
2183 (struct i40e_aqc_add_get_update_vsi *)&desc.params.raw;
2184 struct i40e_aqc_add_get_update_vsi_completion *resp =
2185 (struct i40e_aqc_add_get_update_vsi_completion *)
2186 &desc.params.raw;
2187 enum i40e_status_code status;
2188
2189 i40e_fill_default_direct_cmd_desc(&desc,
2190 i40e_aqc_opc_add_vsi);
2191
2192 cmd->uplink_seid = CPU_TO_LE16(vsi_ctx->uplink_seid);
2193 cmd->connection_type = vsi_ctx->connection_type;
2194 cmd->vf_id = vsi_ctx->vf_num;
2195 cmd->vsi_flags = CPU_TO_LE16(vsi_ctx->flags);
2196
2197 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
2198
2199 status = i40e_asq_send_command(hw, &desc, &vsi_ctx->info,
2200 sizeof(vsi_ctx->info), cmd_details);
2201
2202 if (status != I40E_SUCCESS)
2203 goto aq_add_vsi_exit;
2204
2205 vsi_ctx->seid = LE16_TO_CPU(resp->seid);
2206 vsi_ctx->vsi_number = LE16_TO_CPU(resp->vsi_number);
2207 vsi_ctx->vsis_allocated = LE16_TO_CPU(resp->vsi_used);
2208 vsi_ctx->vsis_unallocated = LE16_TO_CPU(resp->vsi_free);
2209
2210 aq_add_vsi_exit:
2211 return status;
2212 }
2213
2214 /**
2215 * i40e_aq_set_default_vsi
2216 * @hw: pointer to the hw struct
2217 * @seid: vsi number
2218 * @cmd_details: pointer to command details structure or NULL
2219 **/
i40e_aq_set_default_vsi(struct i40e_hw * hw,u16 seid,struct i40e_asq_cmd_details * cmd_details)2220 enum i40e_status_code i40e_aq_set_default_vsi(struct i40e_hw *hw,
2221 u16 seid,
2222 struct i40e_asq_cmd_details *cmd_details)
2223 {
2224 struct i40e_aq_desc desc;
2225 struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
2226 (struct i40e_aqc_set_vsi_promiscuous_modes *)
2227 &desc.params.raw;
2228 enum i40e_status_code status;
2229
2230 i40e_fill_default_direct_cmd_desc(&desc,
2231 i40e_aqc_opc_set_vsi_promiscuous_modes);
2232
2233 cmd->promiscuous_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_DEFAULT);
2234 cmd->valid_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_DEFAULT);
2235 cmd->seid = CPU_TO_LE16(seid);
2236
2237 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2238
2239 return status;
2240 }
2241
2242 /**
2243 * i40e_aq_clear_default_vsi
2244 * @hw: pointer to the hw struct
2245 * @seid: vsi number
2246 * @cmd_details: pointer to command details structure or NULL
2247 **/
i40e_aq_clear_default_vsi(struct i40e_hw * hw,u16 seid,struct i40e_asq_cmd_details * cmd_details)2248 enum i40e_status_code i40e_aq_clear_default_vsi(struct i40e_hw *hw,
2249 u16 seid,
2250 struct i40e_asq_cmd_details *cmd_details)
2251 {
2252 struct i40e_aq_desc desc;
2253 struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
2254 (struct i40e_aqc_set_vsi_promiscuous_modes *)
2255 &desc.params.raw;
2256 enum i40e_status_code status;
2257
2258 i40e_fill_default_direct_cmd_desc(&desc,
2259 i40e_aqc_opc_set_vsi_promiscuous_modes);
2260
2261 cmd->promiscuous_flags = CPU_TO_LE16(0);
2262 cmd->valid_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_DEFAULT);
2263 cmd->seid = CPU_TO_LE16(seid);
2264
2265 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2266
2267 return status;
2268 }
2269
2270 /**
2271 * i40e_aq_set_vsi_unicast_promiscuous
2272 * @hw: pointer to the hw struct
2273 * @seid: vsi number
2274 * @set: set unicast promiscuous enable/disable
2275 * @cmd_details: pointer to command details structure or NULL
2276 * @rx_only_promisc: flag to decide if egress traffic gets mirrored in promisc
2277 **/
i40e_aq_set_vsi_unicast_promiscuous(struct i40e_hw * hw,u16 seid,bool set,struct i40e_asq_cmd_details * cmd_details,bool rx_only_promisc)2278 enum i40e_status_code i40e_aq_set_vsi_unicast_promiscuous(struct i40e_hw *hw,
2279 u16 seid, bool set,
2280 struct i40e_asq_cmd_details *cmd_details,
2281 bool rx_only_promisc)
2282 {
2283 struct i40e_aq_desc desc;
2284 struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
2285 (struct i40e_aqc_set_vsi_promiscuous_modes *)&desc.params.raw;
2286 enum i40e_status_code status;
2287 u16 flags = 0;
2288
2289 i40e_fill_default_direct_cmd_desc(&desc,
2290 i40e_aqc_opc_set_vsi_promiscuous_modes);
2291
2292 if (set) {
2293 flags |= I40E_AQC_SET_VSI_PROMISC_UNICAST;
2294 if (rx_only_promisc &&
2295 (((hw->aq.api_maj_ver == 1) && (hw->aq.api_min_ver >= 5)) ||
2296 (hw->aq.api_maj_ver > 1)))
2297 flags |= I40E_AQC_SET_VSI_PROMISC_TX;
2298 }
2299
2300 cmd->promiscuous_flags = CPU_TO_LE16(flags);
2301
2302 cmd->valid_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_PROMISC_UNICAST);
2303 if (((hw->aq.api_maj_ver >= 1) && (hw->aq.api_min_ver >= 5)) ||
2304 (hw->aq.api_maj_ver > 1))
2305 cmd->valid_flags |= CPU_TO_LE16(I40E_AQC_SET_VSI_PROMISC_TX);
2306
2307 cmd->seid = CPU_TO_LE16(seid);
2308 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2309
2310 return status;
2311 }
2312
2313 /**
2314 * i40e_aq_set_vsi_multicast_promiscuous
2315 * @hw: pointer to the hw struct
2316 * @seid: vsi number
2317 * @set: set multicast promiscuous enable/disable
2318 * @cmd_details: pointer to command details structure or NULL
2319 **/
i40e_aq_set_vsi_multicast_promiscuous(struct i40e_hw * hw,u16 seid,bool set,struct i40e_asq_cmd_details * cmd_details)2320 enum i40e_status_code i40e_aq_set_vsi_multicast_promiscuous(struct i40e_hw *hw,
2321 u16 seid, bool set, struct i40e_asq_cmd_details *cmd_details)
2322 {
2323 struct i40e_aq_desc desc;
2324 struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
2325 (struct i40e_aqc_set_vsi_promiscuous_modes *)&desc.params.raw;
2326 enum i40e_status_code status;
2327 u16 flags = 0;
2328
2329 i40e_fill_default_direct_cmd_desc(&desc,
2330 i40e_aqc_opc_set_vsi_promiscuous_modes);
2331
2332 if (set)
2333 flags |= I40E_AQC_SET_VSI_PROMISC_MULTICAST;
2334
2335 cmd->promiscuous_flags = CPU_TO_LE16(flags);
2336
2337 cmd->valid_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_PROMISC_MULTICAST);
2338
2339 cmd->seid = CPU_TO_LE16(seid);
2340 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2341
2342 return status;
2343 }
2344
2345 /**
2346 * i40e_aq_set_vsi_full_promiscuous
2347 * @hw: pointer to the hw struct
2348 * @seid: VSI number
2349 * @set: set promiscuous enable/disable
2350 * @cmd_details: pointer to command details structure or NULL
2351 **/
i40e_aq_set_vsi_full_promiscuous(struct i40e_hw * hw,u16 seid,bool set,struct i40e_asq_cmd_details * cmd_details)2352 enum i40e_status_code i40e_aq_set_vsi_full_promiscuous(struct i40e_hw *hw,
2353 u16 seid, bool set,
2354 struct i40e_asq_cmd_details *cmd_details)
2355 {
2356 struct i40e_aq_desc desc;
2357 struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
2358 (struct i40e_aqc_set_vsi_promiscuous_modes *)&desc.params.raw;
2359 enum i40e_status_code status;
2360 u16 flags = 0;
2361
2362 i40e_fill_default_direct_cmd_desc(&desc,
2363 i40e_aqc_opc_set_vsi_promiscuous_modes);
2364
2365 if (set)
2366 flags = I40E_AQC_SET_VSI_PROMISC_UNICAST |
2367 I40E_AQC_SET_VSI_PROMISC_MULTICAST |
2368 I40E_AQC_SET_VSI_PROMISC_BROADCAST;
2369
2370 cmd->promiscuous_flags = CPU_TO_LE16(flags);
2371
2372 cmd->valid_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_PROMISC_UNICAST |
2373 I40E_AQC_SET_VSI_PROMISC_MULTICAST |
2374 I40E_AQC_SET_VSI_PROMISC_BROADCAST);
2375
2376 cmd->seid = CPU_TO_LE16(seid);
2377 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2378
2379 return status;
2380 }
2381
2382 /**
2383 * i40e_aq_set_vsi_mc_promisc_on_vlan
2384 * @hw: pointer to the hw struct
2385 * @seid: vsi number
2386 * @enable: set MAC L2 layer unicast promiscuous enable/disable for a given VLAN
2387 * @vid: The VLAN tag filter - capture any multicast packet with this VLAN tag
2388 * @cmd_details: pointer to command details structure or NULL
2389 **/
i40e_aq_set_vsi_mc_promisc_on_vlan(struct i40e_hw * hw,u16 seid,bool enable,u16 vid,struct i40e_asq_cmd_details * cmd_details)2390 enum i40e_status_code i40e_aq_set_vsi_mc_promisc_on_vlan(struct i40e_hw *hw,
2391 u16 seid, bool enable, u16 vid,
2392 struct i40e_asq_cmd_details *cmd_details)
2393 {
2394 struct i40e_aq_desc desc;
2395 struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
2396 (struct i40e_aqc_set_vsi_promiscuous_modes *)&desc.params.raw;
2397 enum i40e_status_code status;
2398 u16 flags = 0;
2399
2400 i40e_fill_default_direct_cmd_desc(&desc,
2401 i40e_aqc_opc_set_vsi_promiscuous_modes);
2402
2403 if (enable)
2404 flags |= I40E_AQC_SET_VSI_PROMISC_MULTICAST;
2405
2406 cmd->promiscuous_flags = CPU_TO_LE16(flags);
2407 cmd->valid_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_PROMISC_MULTICAST);
2408 cmd->seid = CPU_TO_LE16(seid);
2409 cmd->vlan_tag = CPU_TO_LE16(vid | I40E_AQC_SET_VSI_VLAN_VALID);
2410
2411 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2412
2413 return status;
2414 }
2415
2416 /**
2417 * i40e_aq_set_vsi_uc_promisc_on_vlan
2418 * @hw: pointer to the hw struct
2419 * @seid: vsi number
2420 * @enable: set MAC L2 layer unicast promiscuous enable/disable for a given VLAN
2421 * @vid: The VLAN tag filter - capture any unicast packet with this VLAN tag
2422 * @cmd_details: pointer to command details structure or NULL
2423 **/
i40e_aq_set_vsi_uc_promisc_on_vlan(struct i40e_hw * hw,u16 seid,bool enable,u16 vid,struct i40e_asq_cmd_details * cmd_details)2424 enum i40e_status_code i40e_aq_set_vsi_uc_promisc_on_vlan(struct i40e_hw *hw,
2425 u16 seid, bool enable, u16 vid,
2426 struct i40e_asq_cmd_details *cmd_details)
2427 {
2428 struct i40e_aq_desc desc;
2429 struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
2430 (struct i40e_aqc_set_vsi_promiscuous_modes *)&desc.params.raw;
2431 enum i40e_status_code status;
2432 u16 flags = 0;
2433
2434 i40e_fill_default_direct_cmd_desc(&desc,
2435 i40e_aqc_opc_set_vsi_promiscuous_modes);
2436
2437 if (enable)
2438 flags |= I40E_AQC_SET_VSI_PROMISC_UNICAST;
2439
2440 cmd->promiscuous_flags = CPU_TO_LE16(flags);
2441 cmd->valid_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_PROMISC_UNICAST);
2442 cmd->seid = CPU_TO_LE16(seid);
2443 cmd->vlan_tag = CPU_TO_LE16(vid | I40E_AQC_SET_VSI_VLAN_VALID);
2444
2445 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2446
2447 return status;
2448 }
2449
2450 /**
2451 * i40e_aq_set_vsi_bc_promisc_on_vlan
2452 * @hw: pointer to the hw struct
2453 * @seid: vsi number
2454 * @enable: set broadcast promiscuous enable/disable for a given VLAN
2455 * @vid: The VLAN tag filter - capture any broadcast packet with this VLAN tag
2456 * @cmd_details: pointer to command details structure or NULL
2457 **/
i40e_aq_set_vsi_bc_promisc_on_vlan(struct i40e_hw * hw,u16 seid,bool enable,u16 vid,struct i40e_asq_cmd_details * cmd_details)2458 enum i40e_status_code i40e_aq_set_vsi_bc_promisc_on_vlan(struct i40e_hw *hw,
2459 u16 seid, bool enable, u16 vid,
2460 struct i40e_asq_cmd_details *cmd_details)
2461 {
2462 struct i40e_aq_desc desc;
2463 struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
2464 (struct i40e_aqc_set_vsi_promiscuous_modes *)&desc.params.raw;
2465 enum i40e_status_code status;
2466 u16 flags = 0;
2467
2468 i40e_fill_default_direct_cmd_desc(&desc,
2469 i40e_aqc_opc_set_vsi_promiscuous_modes);
2470
2471 if (enable)
2472 flags |= I40E_AQC_SET_VSI_PROMISC_BROADCAST;
2473
2474 cmd->promiscuous_flags = CPU_TO_LE16(flags);
2475 cmd->valid_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_PROMISC_BROADCAST);
2476 cmd->seid = CPU_TO_LE16(seid);
2477 cmd->vlan_tag = CPU_TO_LE16(vid | I40E_AQC_SET_VSI_VLAN_VALID);
2478
2479 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2480
2481 return status;
2482 }
2483
2484 /**
2485 * i40e_aq_set_vsi_broadcast
2486 * @hw: pointer to the hw struct
2487 * @seid: vsi number
2488 * @set_filter: TRUE to set filter, FALSE to clear filter
2489 * @cmd_details: pointer to command details structure or NULL
2490 *
2491 * Set or clear the broadcast promiscuous flag (filter) for a given VSI.
2492 **/
i40e_aq_set_vsi_broadcast(struct i40e_hw * hw,u16 seid,bool set_filter,struct i40e_asq_cmd_details * cmd_details)2493 enum i40e_status_code i40e_aq_set_vsi_broadcast(struct i40e_hw *hw,
2494 u16 seid, bool set_filter,
2495 struct i40e_asq_cmd_details *cmd_details)
2496 {
2497 struct i40e_aq_desc desc;
2498 struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
2499 (struct i40e_aqc_set_vsi_promiscuous_modes *)&desc.params.raw;
2500 enum i40e_status_code status;
2501
2502 i40e_fill_default_direct_cmd_desc(&desc,
2503 i40e_aqc_opc_set_vsi_promiscuous_modes);
2504
2505 if (set_filter)
2506 cmd->promiscuous_flags
2507 |= CPU_TO_LE16(I40E_AQC_SET_VSI_PROMISC_BROADCAST);
2508 else
2509 cmd->promiscuous_flags
2510 &= CPU_TO_LE16(~I40E_AQC_SET_VSI_PROMISC_BROADCAST);
2511
2512 cmd->valid_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_PROMISC_BROADCAST);
2513 cmd->seid = CPU_TO_LE16(seid);
2514 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2515
2516 return status;
2517 }
2518
2519 /**
2520 * i40e_aq_set_vsi_vlan_promisc - control the VLAN promiscuous setting
2521 * @hw: pointer to the hw struct
2522 * @seid: vsi number
2523 * @enable: set MAC L2 layer unicast promiscuous enable/disable for a given VLAN
2524 * @cmd_details: pointer to command details structure or NULL
2525 **/
i40e_aq_set_vsi_vlan_promisc(struct i40e_hw * hw,u16 seid,bool enable,struct i40e_asq_cmd_details * cmd_details)2526 enum i40e_status_code i40e_aq_set_vsi_vlan_promisc(struct i40e_hw *hw,
2527 u16 seid, bool enable,
2528 struct i40e_asq_cmd_details *cmd_details)
2529 {
2530 struct i40e_aq_desc desc;
2531 struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
2532 (struct i40e_aqc_set_vsi_promiscuous_modes *)&desc.params.raw;
2533 enum i40e_status_code status;
2534 u16 flags = 0;
2535
2536 i40e_fill_default_direct_cmd_desc(&desc,
2537 i40e_aqc_opc_set_vsi_promiscuous_modes);
2538 if (enable)
2539 flags |= I40E_AQC_SET_VSI_PROMISC_VLAN;
2540
2541 cmd->promiscuous_flags = CPU_TO_LE16(flags);
2542 cmd->valid_flags = CPU_TO_LE16(I40E_AQC_SET_VSI_PROMISC_VLAN);
2543 cmd->seid = CPU_TO_LE16(seid);
2544
2545 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2546
2547 return status;
2548 }
2549
2550 /**
2551 * i40e_get_vsi_params - get VSI configuration info
2552 * @hw: pointer to the hw struct
2553 * @vsi_ctx: pointer to a vsi context struct
2554 * @cmd_details: pointer to command details structure or NULL
2555 **/
i40e_aq_get_vsi_params(struct i40e_hw * hw,struct i40e_vsi_context * vsi_ctx,struct i40e_asq_cmd_details * cmd_details)2556 enum i40e_status_code i40e_aq_get_vsi_params(struct i40e_hw *hw,
2557 struct i40e_vsi_context *vsi_ctx,
2558 struct i40e_asq_cmd_details *cmd_details)
2559 {
2560 struct i40e_aq_desc desc;
2561 struct i40e_aqc_add_get_update_vsi *cmd =
2562 (struct i40e_aqc_add_get_update_vsi *)&desc.params.raw;
2563 struct i40e_aqc_add_get_update_vsi_completion *resp =
2564 (struct i40e_aqc_add_get_update_vsi_completion *)
2565 &desc.params.raw;
2566 enum i40e_status_code status;
2567
2568 i40e_fill_default_direct_cmd_desc(&desc,
2569 i40e_aqc_opc_get_vsi_parameters);
2570
2571 cmd->uplink_seid = CPU_TO_LE16(vsi_ctx->seid);
2572
2573 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
2574
2575 status = i40e_asq_send_command(hw, &desc, &vsi_ctx->info,
2576 sizeof(vsi_ctx->info), NULL);
2577
2578 if (status != I40E_SUCCESS)
2579 goto aq_get_vsi_params_exit;
2580
2581 vsi_ctx->seid = LE16_TO_CPU(resp->seid);
2582 vsi_ctx->vsi_number = LE16_TO_CPU(resp->vsi_number);
2583 vsi_ctx->vsis_allocated = LE16_TO_CPU(resp->vsi_used);
2584 vsi_ctx->vsis_unallocated = LE16_TO_CPU(resp->vsi_free);
2585
2586 aq_get_vsi_params_exit:
2587 return status;
2588 }
2589
2590 /**
2591 * i40e_aq_update_vsi_params
2592 * @hw: pointer to the hw struct
2593 * @vsi_ctx: pointer to a vsi context struct
2594 * @cmd_details: pointer to command details structure or NULL
2595 *
2596 * Update a VSI context.
2597 **/
i40e_aq_update_vsi_params(struct i40e_hw * hw,struct i40e_vsi_context * vsi_ctx,struct i40e_asq_cmd_details * cmd_details)2598 enum i40e_status_code i40e_aq_update_vsi_params(struct i40e_hw *hw,
2599 struct i40e_vsi_context *vsi_ctx,
2600 struct i40e_asq_cmd_details *cmd_details)
2601 {
2602 struct i40e_aq_desc desc;
2603 struct i40e_aqc_add_get_update_vsi *cmd =
2604 (struct i40e_aqc_add_get_update_vsi *)&desc.params.raw;
2605 struct i40e_aqc_add_get_update_vsi_completion *resp =
2606 (struct i40e_aqc_add_get_update_vsi_completion *)
2607 &desc.params.raw;
2608 enum i40e_status_code status;
2609
2610 i40e_fill_default_direct_cmd_desc(&desc,
2611 i40e_aqc_opc_update_vsi_parameters);
2612 cmd->uplink_seid = CPU_TO_LE16(vsi_ctx->seid);
2613
2614 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
2615
2616 status = i40e_asq_send_command(hw, &desc, &vsi_ctx->info,
2617 sizeof(vsi_ctx->info), cmd_details);
2618
2619 vsi_ctx->vsis_allocated = LE16_TO_CPU(resp->vsi_used);
2620 vsi_ctx->vsis_unallocated = LE16_TO_CPU(resp->vsi_free);
2621
2622 return status;
2623 }
2624
2625 /**
2626 * i40e_aq_get_switch_config
2627 * @hw: pointer to the hardware structure
2628 * @buf: pointer to the result buffer
2629 * @buf_size: length of input buffer
2630 * @start_seid: seid to start for the report, 0 == beginning
2631 * @cmd_details: pointer to command details structure or NULL
2632 *
2633 * Fill the buf with switch configuration returned from AdminQ command
2634 **/
i40e_aq_get_switch_config(struct i40e_hw * hw,struct i40e_aqc_get_switch_config_resp * buf,u16 buf_size,u16 * start_seid,struct i40e_asq_cmd_details * cmd_details)2635 enum i40e_status_code i40e_aq_get_switch_config(struct i40e_hw *hw,
2636 struct i40e_aqc_get_switch_config_resp *buf,
2637 u16 buf_size, u16 *start_seid,
2638 struct i40e_asq_cmd_details *cmd_details)
2639 {
2640 struct i40e_aq_desc desc;
2641 struct i40e_aqc_switch_seid *scfg =
2642 (struct i40e_aqc_switch_seid *)&desc.params.raw;
2643 enum i40e_status_code status;
2644
2645 i40e_fill_default_direct_cmd_desc(&desc,
2646 i40e_aqc_opc_get_switch_config);
2647 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
2648 if (buf_size > I40E_AQ_LARGE_BUF)
2649 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
2650 scfg->seid = CPU_TO_LE16(*start_seid);
2651
2652 status = i40e_asq_send_command(hw, &desc, buf, buf_size, cmd_details);
2653 *start_seid = LE16_TO_CPU(scfg->seid);
2654
2655 return status;
2656 }
2657
2658 /**
2659 * i40e_aq_set_switch_config
2660 * @hw: pointer to the hardware structure
2661 * @flags: bit flag values to set
2662 * @mode: cloud filter mode
2663 * @valid_flags: which bit flags to set
2664 * @cmd_details: pointer to command details structure or NULL
2665 *
2666 * Set switch configuration bits
2667 **/
i40e_aq_set_switch_config(struct i40e_hw * hw,u16 flags,u16 valid_flags,u8 mode,struct i40e_asq_cmd_details * cmd_details)2668 enum i40e_status_code i40e_aq_set_switch_config(struct i40e_hw *hw,
2669 u16 flags, u16 valid_flags, u8 mode,
2670 struct i40e_asq_cmd_details *cmd_details)
2671 {
2672 struct i40e_aq_desc desc;
2673 struct i40e_aqc_set_switch_config *scfg =
2674 (struct i40e_aqc_set_switch_config *)&desc.params.raw;
2675 enum i40e_status_code status;
2676
2677 i40e_fill_default_direct_cmd_desc(&desc,
2678 i40e_aqc_opc_set_switch_config);
2679 scfg->flags = CPU_TO_LE16(flags);
2680 scfg->valid_flags = CPU_TO_LE16(valid_flags);
2681 scfg->mode = mode;
2682 if (hw->flags & I40E_HW_FLAG_802_1AD_CAPABLE) {
2683 scfg->switch_tag = CPU_TO_LE16(hw->switch_tag);
2684 scfg->first_tag = CPU_TO_LE16(hw->first_tag);
2685 scfg->second_tag = CPU_TO_LE16(hw->second_tag);
2686 }
2687 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2688
2689 return status;
2690 }
2691
2692 /**
2693 * i40e_aq_get_firmware_version
2694 * @hw: pointer to the hw struct
2695 * @fw_major_version: firmware major version
2696 * @fw_minor_version: firmware minor version
2697 * @fw_build: firmware build number
2698 * @api_major_version: major queue version
2699 * @api_minor_version: minor queue version
2700 * @cmd_details: pointer to command details structure or NULL
2701 *
2702 * Get the firmware version from the admin queue commands
2703 **/
i40e_aq_get_firmware_version(struct i40e_hw * hw,u16 * fw_major_version,u16 * fw_minor_version,u32 * fw_build,u16 * api_major_version,u16 * api_minor_version,struct i40e_asq_cmd_details * cmd_details)2704 enum i40e_status_code i40e_aq_get_firmware_version(struct i40e_hw *hw,
2705 u16 *fw_major_version, u16 *fw_minor_version,
2706 u32 *fw_build,
2707 u16 *api_major_version, u16 *api_minor_version,
2708 struct i40e_asq_cmd_details *cmd_details)
2709 {
2710 struct i40e_aq_desc desc;
2711 struct i40e_aqc_get_version *resp =
2712 (struct i40e_aqc_get_version *)&desc.params.raw;
2713 enum i40e_status_code status;
2714
2715 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_get_version);
2716
2717 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2718
2719 if (status == I40E_SUCCESS) {
2720 if (fw_major_version != NULL)
2721 *fw_major_version = LE16_TO_CPU(resp->fw_major);
2722 if (fw_minor_version != NULL)
2723 *fw_minor_version = LE16_TO_CPU(resp->fw_minor);
2724 if (fw_build != NULL)
2725 *fw_build = LE32_TO_CPU(resp->fw_build);
2726 if (api_major_version != NULL)
2727 *api_major_version = LE16_TO_CPU(resp->api_major);
2728 if (api_minor_version != NULL)
2729 *api_minor_version = LE16_TO_CPU(resp->api_minor);
2730
2731 /* A workaround to fix the API version in SW */
2732 if (api_major_version && api_minor_version &&
2733 fw_major_version && fw_minor_version &&
2734 ((*api_major_version == 1) && (*api_minor_version == 1)) &&
2735 (((*fw_major_version == 4) && (*fw_minor_version >= 2)) ||
2736 (*fw_major_version > 4)))
2737 *api_minor_version = 2;
2738 }
2739
2740 return status;
2741 }
2742
2743 /**
2744 * i40e_aq_send_driver_version
2745 * @hw: pointer to the hw struct
2746 * @dv: driver's major, minor version
2747 * @cmd_details: pointer to command details structure or NULL
2748 *
2749 * Send the driver version to the firmware
2750 **/
i40e_aq_send_driver_version(struct i40e_hw * hw,struct i40e_driver_version * dv,struct i40e_asq_cmd_details * cmd_details)2751 enum i40e_status_code i40e_aq_send_driver_version(struct i40e_hw *hw,
2752 struct i40e_driver_version *dv,
2753 struct i40e_asq_cmd_details *cmd_details)
2754 {
2755 struct i40e_aq_desc desc;
2756 struct i40e_aqc_driver_version *cmd =
2757 (struct i40e_aqc_driver_version *)&desc.params.raw;
2758 enum i40e_status_code status;
2759 u16 len;
2760
2761 if (dv == NULL)
2762 return I40E_ERR_PARAM;
2763
2764 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_driver_version);
2765
2766 desc.flags |= CPU_TO_LE16(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD);
2767 cmd->driver_major_ver = dv->major_version;
2768 cmd->driver_minor_ver = dv->minor_version;
2769 cmd->driver_build_ver = dv->build_version;
2770 cmd->driver_subbuild_ver = dv->subbuild_version;
2771
2772 len = 0;
2773 while (len < sizeof(dv->driver_string) &&
2774 (dv->driver_string[len] < 0x80) &&
2775 dv->driver_string[len])
2776 len++;
2777 status = i40e_asq_send_command(hw, &desc, dv->driver_string,
2778 len, cmd_details);
2779
2780 return status;
2781 }
2782
2783 /**
2784 * i40e_get_link_status - get status of the HW network link
2785 * @hw: pointer to the hw struct
2786 * @link_up: pointer to bool (TRUE/FALSE = linkup/linkdown)
2787 *
2788 * Variable link_up TRUE if link is up, FALSE if link is down.
2789 * The variable link_up is invalid if returned value of status != I40E_SUCCESS
2790 *
2791 * Side effect: LinkStatusEvent reporting becomes enabled
2792 **/
i40e_get_link_status(struct i40e_hw * hw,bool * link_up)2793 enum i40e_status_code i40e_get_link_status(struct i40e_hw *hw, bool *link_up)
2794 {
2795 enum i40e_status_code status = I40E_SUCCESS;
2796
2797 if (hw->phy.get_link_info) {
2798 status = i40e_update_link_info(hw);
2799
2800 if (status != I40E_SUCCESS)
2801 i40e_debug(hw, I40E_DEBUG_LINK, "get link failed: status %d\n",
2802 status);
2803 }
2804
2805 *link_up = hw->phy.link_info.link_info & I40E_AQ_LINK_UP;
2806
2807 return status;
2808 }
2809
2810 /**
2811 * i40e_updatelink_status - update status of the HW network link
2812 * @hw: pointer to the hw struct
2813 **/
i40e_update_link_info(struct i40e_hw * hw)2814 enum i40e_status_code i40e_update_link_info(struct i40e_hw *hw)
2815 {
2816 struct i40e_aq_get_phy_abilities_resp abilities;
2817 enum i40e_status_code status = I40E_SUCCESS;
2818
2819 status = i40e_aq_get_link_info(hw, TRUE, NULL, NULL);
2820 if (status)
2821 return status;
2822
2823 /* extra checking needed to ensure link info to user is timely */
2824 if ((hw->phy.link_info.link_info & I40E_AQ_MEDIA_AVAILABLE) &&
2825 ((hw->phy.link_info.link_info & I40E_AQ_LINK_UP) ||
2826 !(hw->phy.link_info_old.link_info & I40E_AQ_LINK_UP))) {
2827 status = i40e_aq_get_phy_capabilities(hw, FALSE, false,
2828 &abilities, NULL);
2829 if (status)
2830 return status;
2831
2832 hw->phy.link_info.req_fec_info =
2833 abilities.fec_cfg_curr_mod_ext_info &
2834 (I40E_AQ_REQUEST_FEC_KR | I40E_AQ_REQUEST_FEC_RS);
2835
2836 i40e_memcpy(hw->phy.link_info.module_type, &abilities.module_type,
2837 sizeof(hw->phy.link_info.module_type), I40E_NONDMA_TO_NONDMA);
2838 }
2839 return status;
2840 }
2841
2842
2843 /**
2844 * i40e_get_link_speed
2845 * @hw: pointer to the hw struct
2846 *
2847 * Returns the link speed of the adapter.
2848 **/
i40e_get_link_speed(struct i40e_hw * hw)2849 enum i40e_aq_link_speed i40e_get_link_speed(struct i40e_hw *hw)
2850 {
2851 enum i40e_aq_link_speed speed = I40E_LINK_SPEED_UNKNOWN;
2852 enum i40e_status_code status = I40E_SUCCESS;
2853
2854 if (hw->phy.get_link_info) {
2855 status = i40e_aq_get_link_info(hw, TRUE, NULL, NULL);
2856
2857 if (status != I40E_SUCCESS)
2858 goto i40e_link_speed_exit;
2859 }
2860
2861 speed = hw->phy.link_info.link_speed;
2862
2863 i40e_link_speed_exit:
2864 return speed;
2865 }
2866
2867 /**
2868 * i40e_aq_add_veb - Insert a VEB between the VSI and the MAC
2869 * @hw: pointer to the hw struct
2870 * @uplink_seid: the MAC or other gizmo SEID
2871 * @downlink_seid: the VSI SEID
2872 * @enabled_tc: bitmap of TCs to be enabled
2873 * @default_port: TRUE for default port VSI, FALSE for control port
2874 * @veb_seid: pointer to where to put the resulting VEB SEID
2875 * @enable_stats: TRUE to turn on VEB stats
2876 * @cmd_details: pointer to command details structure or NULL
2877 *
2878 * This asks the FW to add a VEB between the uplink and downlink
2879 * elements. If the uplink SEID is 0, this will be a floating VEB.
2880 **/
i40e_aq_add_veb(struct i40e_hw * hw,u16 uplink_seid,u16 downlink_seid,u8 enabled_tc,bool default_port,u16 * veb_seid,bool enable_stats,struct i40e_asq_cmd_details * cmd_details)2881 enum i40e_status_code i40e_aq_add_veb(struct i40e_hw *hw, u16 uplink_seid,
2882 u16 downlink_seid, u8 enabled_tc,
2883 bool default_port, u16 *veb_seid,
2884 bool enable_stats,
2885 struct i40e_asq_cmd_details *cmd_details)
2886 {
2887 struct i40e_aq_desc desc;
2888 struct i40e_aqc_add_veb *cmd =
2889 (struct i40e_aqc_add_veb *)&desc.params.raw;
2890 struct i40e_aqc_add_veb_completion *resp =
2891 (struct i40e_aqc_add_veb_completion *)&desc.params.raw;
2892 enum i40e_status_code status;
2893 u16 veb_flags = 0;
2894
2895 /* SEIDs need to either both be set or both be 0 for floating VEB */
2896 if (!!uplink_seid != !!downlink_seid)
2897 return I40E_ERR_PARAM;
2898
2899 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_add_veb);
2900
2901 cmd->uplink_seid = CPU_TO_LE16(uplink_seid);
2902 cmd->downlink_seid = CPU_TO_LE16(downlink_seid);
2903 cmd->enable_tcs = enabled_tc;
2904 if (!uplink_seid)
2905 veb_flags |= I40E_AQC_ADD_VEB_FLOATING;
2906 if (default_port)
2907 veb_flags |= I40E_AQC_ADD_VEB_PORT_TYPE_DEFAULT;
2908 else
2909 veb_flags |= I40E_AQC_ADD_VEB_PORT_TYPE_DATA;
2910
2911 /* reverse logic here: set the bitflag to disable the stats */
2912 if (!enable_stats)
2913 veb_flags |= I40E_AQC_ADD_VEB_ENABLE_DISABLE_STATS;
2914
2915 cmd->veb_flags = CPU_TO_LE16(veb_flags);
2916
2917 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2918
2919 if (!status && veb_seid)
2920 *veb_seid = LE16_TO_CPU(resp->veb_seid);
2921
2922 return status;
2923 }
2924
2925 /**
2926 * i40e_aq_get_veb_parameters - Retrieve VEB parameters
2927 * @hw: pointer to the hw struct
2928 * @veb_seid: the SEID of the VEB to query
2929 * @switch_id: the uplink switch id
2930 * @floating: set to TRUE if the VEB is floating
2931 * @statistic_index: index of the stats counter block for this VEB
2932 * @vebs_used: number of VEB's used by function
2933 * @vebs_free: total VEB's not reserved by any function
2934 * @cmd_details: pointer to command details structure or NULL
2935 *
2936 * This retrieves the parameters for a particular VEB, specified by
2937 * uplink_seid, and returns them to the caller.
2938 **/
i40e_aq_get_veb_parameters(struct i40e_hw * hw,u16 veb_seid,u16 * switch_id,bool * floating,u16 * statistic_index,u16 * vebs_used,u16 * vebs_free,struct i40e_asq_cmd_details * cmd_details)2939 enum i40e_status_code i40e_aq_get_veb_parameters(struct i40e_hw *hw,
2940 u16 veb_seid, u16 *switch_id,
2941 bool *floating, u16 *statistic_index,
2942 u16 *vebs_used, u16 *vebs_free,
2943 struct i40e_asq_cmd_details *cmd_details)
2944 {
2945 struct i40e_aq_desc desc;
2946 struct i40e_aqc_get_veb_parameters_completion *cmd_resp =
2947 (struct i40e_aqc_get_veb_parameters_completion *)
2948 &desc.params.raw;
2949 enum i40e_status_code status;
2950
2951 if (veb_seid == 0)
2952 return I40E_ERR_PARAM;
2953
2954 i40e_fill_default_direct_cmd_desc(&desc,
2955 i40e_aqc_opc_get_veb_parameters);
2956 cmd_resp->seid = CPU_TO_LE16(veb_seid);
2957
2958 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
2959 if (status)
2960 goto get_veb_exit;
2961
2962 if (switch_id)
2963 *switch_id = LE16_TO_CPU(cmd_resp->switch_id);
2964 if (statistic_index)
2965 *statistic_index = LE16_TO_CPU(cmd_resp->statistic_index);
2966 if (vebs_used)
2967 *vebs_used = LE16_TO_CPU(cmd_resp->vebs_used);
2968 if (vebs_free)
2969 *vebs_free = LE16_TO_CPU(cmd_resp->vebs_free);
2970 if (floating) {
2971 u16 flags = LE16_TO_CPU(cmd_resp->veb_flags);
2972
2973 if (flags & I40E_AQC_ADD_VEB_FLOATING)
2974 *floating = TRUE;
2975 else
2976 *floating = FALSE;
2977 }
2978
2979 get_veb_exit:
2980 return status;
2981 }
2982
2983 /**
2984 * i40e_aq_add_macvlan
2985 * @hw: pointer to the hw struct
2986 * @seid: VSI for the mac address
2987 * @mv_list: list of macvlans to be added
2988 * @count: length of the list
2989 * @cmd_details: pointer to command details structure or NULL
2990 *
2991 * Add MAC/VLAN addresses to the HW filtering
2992 **/
i40e_aq_add_macvlan(struct i40e_hw * hw,u16 seid,struct i40e_aqc_add_macvlan_element_data * mv_list,u16 count,struct i40e_asq_cmd_details * cmd_details)2993 enum i40e_status_code i40e_aq_add_macvlan(struct i40e_hw *hw, u16 seid,
2994 struct i40e_aqc_add_macvlan_element_data *mv_list,
2995 u16 count, struct i40e_asq_cmd_details *cmd_details)
2996 {
2997 struct i40e_aq_desc desc;
2998 struct i40e_aqc_macvlan *cmd =
2999 (struct i40e_aqc_macvlan *)&desc.params.raw;
3000 enum i40e_status_code status;
3001 u16 buf_size;
3002 int i;
3003
3004 if (count == 0 || !mv_list || !hw)
3005 return I40E_ERR_PARAM;
3006
3007 buf_size = count * sizeof(*mv_list);
3008
3009 /* prep the rest of the request */
3010 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_add_macvlan);
3011 cmd->num_addresses = CPU_TO_LE16(count);
3012 cmd->seid[0] = CPU_TO_LE16(I40E_AQC_MACVLAN_CMD_SEID_VALID | seid);
3013 cmd->seid[1] = 0;
3014 cmd->seid[2] = 0;
3015
3016 for (i = 0; i < count; i++)
3017 if (I40E_IS_MULTICAST(mv_list[i].mac_addr))
3018 mv_list[i].flags |=
3019 CPU_TO_LE16(I40E_AQC_MACVLAN_ADD_USE_SHARED_MAC);
3020
3021 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
3022 if (buf_size > I40E_AQ_LARGE_BUF)
3023 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
3024
3025 status = i40e_asq_send_command(hw, &desc, mv_list, buf_size,
3026 cmd_details);
3027
3028 return status;
3029 }
3030
3031 /**
3032 * i40e_aq_remove_macvlan
3033 * @hw: pointer to the hw struct
3034 * @seid: VSI for the mac address
3035 * @mv_list: list of macvlans to be removed
3036 * @count: length of the list
3037 * @cmd_details: pointer to command details structure or NULL
3038 *
3039 * Remove MAC/VLAN addresses from the HW filtering
3040 **/
i40e_aq_remove_macvlan(struct i40e_hw * hw,u16 seid,struct i40e_aqc_remove_macvlan_element_data * mv_list,u16 count,struct i40e_asq_cmd_details * cmd_details)3041 enum i40e_status_code i40e_aq_remove_macvlan(struct i40e_hw *hw, u16 seid,
3042 struct i40e_aqc_remove_macvlan_element_data *mv_list,
3043 u16 count, struct i40e_asq_cmd_details *cmd_details)
3044 {
3045 struct i40e_aq_desc desc;
3046 struct i40e_aqc_macvlan *cmd =
3047 (struct i40e_aqc_macvlan *)&desc.params.raw;
3048 enum i40e_status_code status;
3049 u16 buf_size;
3050
3051 if (count == 0 || !mv_list || !hw)
3052 return I40E_ERR_PARAM;
3053
3054 buf_size = count * sizeof(*mv_list);
3055
3056 /* prep the rest of the request */
3057 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_remove_macvlan);
3058 cmd->num_addresses = CPU_TO_LE16(count);
3059 cmd->seid[0] = CPU_TO_LE16(I40E_AQC_MACVLAN_CMD_SEID_VALID | seid);
3060 cmd->seid[1] = 0;
3061 cmd->seid[2] = 0;
3062
3063 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
3064 if (buf_size > I40E_AQ_LARGE_BUF)
3065 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
3066
3067 status = i40e_asq_send_command(hw, &desc, mv_list, buf_size,
3068 cmd_details);
3069
3070 return status;
3071 }
3072
3073 /**
3074 * i40e_mirrorrule_op - Internal helper function to add/delete mirror rule
3075 * @hw: pointer to the hw struct
3076 * @opcode: AQ opcode for add or delete mirror rule
3077 * @sw_seid: Switch SEID (to which rule refers)
3078 * @rule_type: Rule Type (ingress/egress/VLAN)
3079 * @id: Destination VSI SEID or Rule ID
3080 * @count: length of the list
3081 * @mr_list: list of mirrored VSI SEIDs or VLAN IDs
3082 * @cmd_details: pointer to command details structure or NULL
3083 * @rule_id: Rule ID returned from FW
3084 * @rules_used: Number of rules used in internal switch
3085 * @rules_free: Number of rules free in internal switch
3086 *
3087 * Add/Delete a mirror rule to a specific switch. Mirror rules are supported for
3088 * VEBs/VEPA elements only
3089 **/
i40e_mirrorrule_op(struct i40e_hw * hw,u16 opcode,u16 sw_seid,u16 rule_type,u16 id,u16 count,__le16 * mr_list,struct i40e_asq_cmd_details * cmd_details,u16 * rule_id,u16 * rules_used,u16 * rules_free)3090 static enum i40e_status_code i40e_mirrorrule_op(struct i40e_hw *hw,
3091 u16 opcode, u16 sw_seid, u16 rule_type, u16 id,
3092 u16 count, __le16 *mr_list,
3093 struct i40e_asq_cmd_details *cmd_details,
3094 u16 *rule_id, u16 *rules_used, u16 *rules_free)
3095 {
3096 struct i40e_aq_desc desc;
3097 struct i40e_aqc_add_delete_mirror_rule *cmd =
3098 (struct i40e_aqc_add_delete_mirror_rule *)&desc.params.raw;
3099 struct i40e_aqc_add_delete_mirror_rule_completion *resp =
3100 (struct i40e_aqc_add_delete_mirror_rule_completion *)&desc.params.raw;
3101 enum i40e_status_code status;
3102 u16 buf_size;
3103
3104 buf_size = count * sizeof(*mr_list);
3105
3106 /* prep the rest of the request */
3107 i40e_fill_default_direct_cmd_desc(&desc, opcode);
3108 cmd->seid = CPU_TO_LE16(sw_seid);
3109 cmd->rule_type = CPU_TO_LE16(rule_type &
3110 I40E_AQC_MIRROR_RULE_TYPE_MASK);
3111 cmd->num_entries = CPU_TO_LE16(count);
3112 /* Dest VSI for add, rule_id for delete */
3113 cmd->destination = CPU_TO_LE16(id);
3114 if (mr_list) {
3115 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF |
3116 I40E_AQ_FLAG_RD));
3117 if (buf_size > I40E_AQ_LARGE_BUF)
3118 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
3119 }
3120
3121 status = i40e_asq_send_command(hw, &desc, mr_list, buf_size,
3122 cmd_details);
3123 if (status == I40E_SUCCESS ||
3124 hw->aq.asq_last_status == I40E_AQ_RC_ENOSPC) {
3125 if (rule_id)
3126 *rule_id = LE16_TO_CPU(resp->rule_id);
3127 if (rules_used)
3128 *rules_used = LE16_TO_CPU(resp->mirror_rules_used);
3129 if (rules_free)
3130 *rules_free = LE16_TO_CPU(resp->mirror_rules_free);
3131 }
3132 return status;
3133 }
3134
3135 /**
3136 * i40e_aq_add_mirrorrule - add a mirror rule
3137 * @hw: pointer to the hw struct
3138 * @sw_seid: Switch SEID (to which rule refers)
3139 * @rule_type: Rule Type (ingress/egress/VLAN)
3140 * @dest_vsi: SEID of VSI to which packets will be mirrored
3141 * @count: length of the list
3142 * @mr_list: list of mirrored VSI SEIDs or VLAN IDs
3143 * @cmd_details: pointer to command details structure or NULL
3144 * @rule_id: Rule ID returned from FW
3145 * @rules_used: Number of rules used in internal switch
3146 * @rules_free: Number of rules free in internal switch
3147 *
3148 * Add mirror rule. Mirror rules are supported for VEBs or VEPA elements only
3149 **/
i40e_aq_add_mirrorrule(struct i40e_hw * hw,u16 sw_seid,u16 rule_type,u16 dest_vsi,u16 count,__le16 * mr_list,struct i40e_asq_cmd_details * cmd_details,u16 * rule_id,u16 * rules_used,u16 * rules_free)3150 enum i40e_status_code i40e_aq_add_mirrorrule(struct i40e_hw *hw, u16 sw_seid,
3151 u16 rule_type, u16 dest_vsi, u16 count, __le16 *mr_list,
3152 struct i40e_asq_cmd_details *cmd_details,
3153 u16 *rule_id, u16 *rules_used, u16 *rules_free)
3154 {
3155 if (!(rule_type == I40E_AQC_MIRROR_RULE_TYPE_ALL_INGRESS ||
3156 rule_type == I40E_AQC_MIRROR_RULE_TYPE_ALL_EGRESS)) {
3157 if (count == 0 || !mr_list)
3158 return I40E_ERR_PARAM;
3159 }
3160
3161 return i40e_mirrorrule_op(hw, i40e_aqc_opc_add_mirror_rule, sw_seid,
3162 rule_type, dest_vsi, count, mr_list,
3163 cmd_details, rule_id, rules_used, rules_free);
3164 }
3165
3166 /**
3167 * i40e_aq_delete_mirrorrule - delete a mirror rule
3168 * @hw: pointer to the hw struct
3169 * @sw_seid: Switch SEID (to which rule refers)
3170 * @rule_type: Rule Type (ingress/egress/VLAN)
3171 * @count: length of the list
3172 * @rule_id: Rule ID that is returned in the receive desc as part of
3173 * add_mirrorrule.
3174 * @mr_list: list of mirrored VLAN IDs to be removed
3175 * @cmd_details: pointer to command details structure or NULL
3176 * @rules_used: Number of rules used in internal switch
3177 * @rules_free: Number of rules free in internal switch
3178 *
3179 * Delete a mirror rule. Mirror rules are supported for VEBs/VEPA elements only
3180 **/
i40e_aq_delete_mirrorrule(struct i40e_hw * hw,u16 sw_seid,u16 rule_type,u16 rule_id,u16 count,__le16 * mr_list,struct i40e_asq_cmd_details * cmd_details,u16 * rules_used,u16 * rules_free)3181 enum i40e_status_code i40e_aq_delete_mirrorrule(struct i40e_hw *hw, u16 sw_seid,
3182 u16 rule_type, u16 rule_id, u16 count, __le16 *mr_list,
3183 struct i40e_asq_cmd_details *cmd_details,
3184 u16 *rules_used, u16 *rules_free)
3185 {
3186 /* Rule ID has to be valid except rule_type: INGRESS VLAN mirroring */
3187 if (rule_type == I40E_AQC_MIRROR_RULE_TYPE_VLAN) {
3188 /* count and mr_list shall be valid for rule_type INGRESS VLAN
3189 * mirroring. For other rule_type, count and rule_type should
3190 * not matter.
3191 */
3192 if (count == 0 || !mr_list)
3193 return I40E_ERR_PARAM;
3194 }
3195
3196 return i40e_mirrorrule_op(hw, i40e_aqc_opc_delete_mirror_rule, sw_seid,
3197 rule_type, rule_id, count, mr_list,
3198 cmd_details, NULL, rules_used, rules_free);
3199 }
3200
3201 /**
3202 * i40e_aq_add_vlan - Add VLAN ids to the HW filtering
3203 * @hw: pointer to the hw struct
3204 * @seid: VSI for the vlan filters
3205 * @v_list: list of vlan filters to be added
3206 * @count: length of the list
3207 * @cmd_details: pointer to command details structure or NULL
3208 **/
i40e_aq_add_vlan(struct i40e_hw * hw,u16 seid,struct i40e_aqc_add_remove_vlan_element_data * v_list,u8 count,struct i40e_asq_cmd_details * cmd_details)3209 enum i40e_status_code i40e_aq_add_vlan(struct i40e_hw *hw, u16 seid,
3210 struct i40e_aqc_add_remove_vlan_element_data *v_list,
3211 u8 count, struct i40e_asq_cmd_details *cmd_details)
3212 {
3213 struct i40e_aq_desc desc;
3214 struct i40e_aqc_macvlan *cmd =
3215 (struct i40e_aqc_macvlan *)&desc.params.raw;
3216 enum i40e_status_code status;
3217 u16 buf_size;
3218
3219 if (count == 0 || !v_list || !hw)
3220 return I40E_ERR_PARAM;
3221
3222 buf_size = count * sizeof(*v_list);
3223
3224 /* prep the rest of the request */
3225 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_add_vlan);
3226 cmd->num_addresses = CPU_TO_LE16(count);
3227 cmd->seid[0] = CPU_TO_LE16(seid | I40E_AQC_MACVLAN_CMD_SEID_VALID);
3228 cmd->seid[1] = 0;
3229 cmd->seid[2] = 0;
3230
3231 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
3232 if (buf_size > I40E_AQ_LARGE_BUF)
3233 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
3234
3235 status = i40e_asq_send_command(hw, &desc, v_list, buf_size,
3236 cmd_details);
3237
3238 return status;
3239 }
3240
3241 /**
3242 * i40e_aq_remove_vlan - Remove VLANs from the HW filtering
3243 * @hw: pointer to the hw struct
3244 * @seid: VSI for the vlan filters
3245 * @v_list: list of macvlans to be removed
3246 * @count: length of the list
3247 * @cmd_details: pointer to command details structure or NULL
3248 **/
i40e_aq_remove_vlan(struct i40e_hw * hw,u16 seid,struct i40e_aqc_add_remove_vlan_element_data * v_list,u8 count,struct i40e_asq_cmd_details * cmd_details)3249 enum i40e_status_code i40e_aq_remove_vlan(struct i40e_hw *hw, u16 seid,
3250 struct i40e_aqc_add_remove_vlan_element_data *v_list,
3251 u8 count, struct i40e_asq_cmd_details *cmd_details)
3252 {
3253 struct i40e_aq_desc desc;
3254 struct i40e_aqc_macvlan *cmd =
3255 (struct i40e_aqc_macvlan *)&desc.params.raw;
3256 enum i40e_status_code status;
3257 u16 buf_size;
3258
3259 if (count == 0 || !v_list || !hw)
3260 return I40E_ERR_PARAM;
3261
3262 buf_size = count * sizeof(*v_list);
3263
3264 /* prep the rest of the request */
3265 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_remove_vlan);
3266 cmd->num_addresses = CPU_TO_LE16(count);
3267 cmd->seid[0] = CPU_TO_LE16(seid | I40E_AQC_MACVLAN_CMD_SEID_VALID);
3268 cmd->seid[1] = 0;
3269 cmd->seid[2] = 0;
3270
3271 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
3272 if (buf_size > I40E_AQ_LARGE_BUF)
3273 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
3274
3275 status = i40e_asq_send_command(hw, &desc, v_list, buf_size,
3276 cmd_details);
3277
3278 return status;
3279 }
3280
3281 /**
3282 * i40e_aq_send_msg_to_vf
3283 * @hw: pointer to the hardware structure
3284 * @vfid: vf id to send msg
3285 * @v_opcode: opcodes for VF-PF communication
3286 * @v_retval: return error code
3287 * @msg: pointer to the msg buffer
3288 * @msglen: msg length
3289 * @cmd_details: pointer to command details
3290 *
3291 * send msg to vf
3292 **/
i40e_aq_send_msg_to_vf(struct i40e_hw * hw,u16 vfid,u32 v_opcode,u32 v_retval,u8 * msg,u16 msglen,struct i40e_asq_cmd_details * cmd_details)3293 enum i40e_status_code i40e_aq_send_msg_to_vf(struct i40e_hw *hw, u16 vfid,
3294 u32 v_opcode, u32 v_retval, u8 *msg, u16 msglen,
3295 struct i40e_asq_cmd_details *cmd_details)
3296 {
3297 struct i40e_aq_desc desc;
3298 struct i40e_aqc_pf_vf_message *cmd =
3299 (struct i40e_aqc_pf_vf_message *)&desc.params.raw;
3300 enum i40e_status_code status;
3301
3302 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_send_msg_to_vf);
3303 cmd->id = CPU_TO_LE32(vfid);
3304 desc.cookie_high = CPU_TO_LE32(v_opcode);
3305 desc.cookie_low = CPU_TO_LE32(v_retval);
3306 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_SI);
3307 if (msglen) {
3308 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF |
3309 I40E_AQ_FLAG_RD));
3310 if (msglen > I40E_AQ_LARGE_BUF)
3311 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
3312 desc.datalen = CPU_TO_LE16(msglen);
3313 }
3314 status = i40e_asq_send_command(hw, &desc, msg, msglen, cmd_details);
3315
3316 return status;
3317 }
3318
3319 /**
3320 * i40e_aq_debug_read_register
3321 * @hw: pointer to the hw struct
3322 * @reg_addr: register address
3323 * @reg_val: register value
3324 * @cmd_details: pointer to command details structure or NULL
3325 *
3326 * Read the register using the admin queue commands
3327 **/
i40e_aq_debug_read_register(struct i40e_hw * hw,u32 reg_addr,u64 * reg_val,struct i40e_asq_cmd_details * cmd_details)3328 enum i40e_status_code i40e_aq_debug_read_register(struct i40e_hw *hw,
3329 u32 reg_addr, u64 *reg_val,
3330 struct i40e_asq_cmd_details *cmd_details)
3331 {
3332 struct i40e_aq_desc desc;
3333 struct i40e_aqc_debug_reg_read_write *cmd_resp =
3334 (struct i40e_aqc_debug_reg_read_write *)&desc.params.raw;
3335 enum i40e_status_code status;
3336
3337 if (reg_val == NULL)
3338 return I40E_ERR_PARAM;
3339
3340 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_debug_read_reg);
3341
3342 cmd_resp->address = CPU_TO_LE32(reg_addr);
3343
3344 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
3345
3346 if (status == I40E_SUCCESS) {
3347 *reg_val = ((u64)LE32_TO_CPU(cmd_resp->value_high) << 32) |
3348 (u64)LE32_TO_CPU(cmd_resp->value_low);
3349 }
3350
3351 return status;
3352 }
3353
3354 /**
3355 * i40e_aq_debug_write_register
3356 * @hw: pointer to the hw struct
3357 * @reg_addr: register address
3358 * @reg_val: register value
3359 * @cmd_details: pointer to command details structure or NULL
3360 *
3361 * Write to a register using the admin queue commands
3362 **/
i40e_aq_debug_write_register(struct i40e_hw * hw,u32 reg_addr,u64 reg_val,struct i40e_asq_cmd_details * cmd_details)3363 enum i40e_status_code i40e_aq_debug_write_register(struct i40e_hw *hw,
3364 u32 reg_addr, u64 reg_val,
3365 struct i40e_asq_cmd_details *cmd_details)
3366 {
3367 struct i40e_aq_desc desc;
3368 struct i40e_aqc_debug_reg_read_write *cmd =
3369 (struct i40e_aqc_debug_reg_read_write *)&desc.params.raw;
3370 enum i40e_status_code status;
3371
3372 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_debug_write_reg);
3373
3374 cmd->address = CPU_TO_LE32(reg_addr);
3375 cmd->value_high = CPU_TO_LE32((u32)(reg_val >> 32));
3376 cmd->value_low = CPU_TO_LE32((u32)(reg_val & 0xFFFFFFFF));
3377
3378 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
3379
3380 return status;
3381 }
3382
3383 /**
3384 * i40e_aq_request_resource
3385 * @hw: pointer to the hw struct
3386 * @resource: resource id
3387 * @access: access type
3388 * @sdp_number: resource number
3389 * @timeout: the maximum time in ms that the driver may hold the resource
3390 * @cmd_details: pointer to command details structure or NULL
3391 *
3392 * requests common resource using the admin queue commands
3393 **/
i40e_aq_request_resource(struct i40e_hw * hw,enum i40e_aq_resources_ids resource,enum i40e_aq_resource_access_type access,u8 sdp_number,u64 * timeout,struct i40e_asq_cmd_details * cmd_details)3394 enum i40e_status_code i40e_aq_request_resource(struct i40e_hw *hw,
3395 enum i40e_aq_resources_ids resource,
3396 enum i40e_aq_resource_access_type access,
3397 u8 sdp_number, u64 *timeout,
3398 struct i40e_asq_cmd_details *cmd_details)
3399 {
3400 struct i40e_aq_desc desc;
3401 struct i40e_aqc_request_resource *cmd_resp =
3402 (struct i40e_aqc_request_resource *)&desc.params.raw;
3403 enum i40e_status_code status;
3404
3405 DEBUGFUNC("i40e_aq_request_resource");
3406
3407 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_request_resource);
3408
3409 cmd_resp->resource_id = CPU_TO_LE16(resource);
3410 cmd_resp->access_type = CPU_TO_LE16(access);
3411 cmd_resp->resource_number = CPU_TO_LE32(sdp_number);
3412
3413 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
3414 /* The completion specifies the maximum time in ms that the driver
3415 * may hold the resource in the Timeout field.
3416 * If the resource is held by someone else, the command completes with
3417 * busy return value and the timeout field indicates the maximum time
3418 * the current owner of the resource has to free it.
3419 */
3420 if (status == I40E_SUCCESS || hw->aq.asq_last_status == I40E_AQ_RC_EBUSY)
3421 *timeout = LE32_TO_CPU(cmd_resp->timeout);
3422
3423 return status;
3424 }
3425
3426 /**
3427 * i40e_aq_release_resource
3428 * @hw: pointer to the hw struct
3429 * @resource: resource id
3430 * @sdp_number: resource number
3431 * @cmd_details: pointer to command details structure or NULL
3432 *
3433 * release common resource using the admin queue commands
3434 **/
i40e_aq_release_resource(struct i40e_hw * hw,enum i40e_aq_resources_ids resource,u8 sdp_number,struct i40e_asq_cmd_details * cmd_details)3435 enum i40e_status_code i40e_aq_release_resource(struct i40e_hw *hw,
3436 enum i40e_aq_resources_ids resource,
3437 u8 sdp_number,
3438 struct i40e_asq_cmd_details *cmd_details)
3439 {
3440 struct i40e_aq_desc desc;
3441 struct i40e_aqc_request_resource *cmd =
3442 (struct i40e_aqc_request_resource *)&desc.params.raw;
3443 enum i40e_status_code status;
3444
3445 DEBUGFUNC("i40e_aq_release_resource");
3446
3447 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_release_resource);
3448
3449 cmd->resource_id = CPU_TO_LE16(resource);
3450 cmd->resource_number = CPU_TO_LE32(sdp_number);
3451
3452 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
3453
3454 return status;
3455 }
3456
3457 /**
3458 * i40e_aq_read_nvm
3459 * @hw: pointer to the hw struct
3460 * @module_pointer: module pointer location in words from the NVM beginning
3461 * @offset: byte offset from the module beginning
3462 * @length: length of the section to be read (in bytes from the offset)
3463 * @data: command buffer (size [bytes] = length)
3464 * @last_command: tells if this is the last command in a series
3465 * @cmd_details: pointer to command details structure or NULL
3466 *
3467 * Read the NVM using the admin queue commands
3468 **/
i40e_aq_read_nvm(struct i40e_hw * hw,u8 module_pointer,u32 offset,u16 length,void * data,bool last_command,struct i40e_asq_cmd_details * cmd_details)3469 enum i40e_status_code i40e_aq_read_nvm(struct i40e_hw *hw, u8 module_pointer,
3470 u32 offset, u16 length, void *data,
3471 bool last_command,
3472 struct i40e_asq_cmd_details *cmd_details)
3473 {
3474 struct i40e_aq_desc desc;
3475 struct i40e_aqc_nvm_update *cmd =
3476 (struct i40e_aqc_nvm_update *)&desc.params.raw;
3477 enum i40e_status_code status;
3478
3479 DEBUGFUNC("i40e_aq_read_nvm");
3480
3481 /* In offset the highest byte must be zeroed. */
3482 if (offset & 0xFF000000) {
3483 status = I40E_ERR_PARAM;
3484 goto i40e_aq_read_nvm_exit;
3485 }
3486
3487 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_nvm_read);
3488
3489 /* If this is the last command in a series, set the proper flag. */
3490 if (last_command)
3491 cmd->command_flags |= I40E_AQ_NVM_LAST_CMD;
3492 cmd->module_pointer = module_pointer;
3493 cmd->offset = CPU_TO_LE32(offset);
3494 cmd->length = CPU_TO_LE16(length);
3495
3496 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
3497 if (length > I40E_AQ_LARGE_BUF)
3498 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
3499
3500 status = i40e_asq_send_command(hw, &desc, data, length, cmd_details);
3501
3502 i40e_aq_read_nvm_exit:
3503 return status;
3504 }
3505
3506 /**
3507 * i40e_aq_read_nvm_config - read an nvm config block
3508 * @hw: pointer to the hw struct
3509 * @cmd_flags: NVM access admin command bits
3510 * @field_id: field or feature id
3511 * @data: buffer for result
3512 * @buf_size: buffer size
3513 * @element_count: pointer to count of elements read by FW
3514 * @cmd_details: pointer to command details structure or NULL
3515 **/
i40e_aq_read_nvm_config(struct i40e_hw * hw,u8 cmd_flags,u32 field_id,void * data,u16 buf_size,u16 * element_count,struct i40e_asq_cmd_details * cmd_details)3516 enum i40e_status_code i40e_aq_read_nvm_config(struct i40e_hw *hw,
3517 u8 cmd_flags, u32 field_id, void *data,
3518 u16 buf_size, u16 *element_count,
3519 struct i40e_asq_cmd_details *cmd_details)
3520 {
3521 struct i40e_aq_desc desc;
3522 struct i40e_aqc_nvm_config_read *cmd =
3523 (struct i40e_aqc_nvm_config_read *)&desc.params.raw;
3524 enum i40e_status_code status;
3525
3526 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_nvm_config_read);
3527 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF));
3528 if (buf_size > I40E_AQ_LARGE_BUF)
3529 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
3530
3531 cmd->cmd_flags = CPU_TO_LE16(cmd_flags);
3532 cmd->element_id = CPU_TO_LE16((u16)(0xffff & field_id));
3533 if (cmd_flags & I40E_AQ_ANVM_FEATURE_OR_IMMEDIATE_MASK)
3534 cmd->element_id_msw = CPU_TO_LE16((u16)(field_id >> 16));
3535 else
3536 cmd->element_id_msw = 0;
3537
3538 status = i40e_asq_send_command(hw, &desc, data, buf_size, cmd_details);
3539
3540 if (!status && element_count)
3541 *element_count = LE16_TO_CPU(cmd->element_count);
3542
3543 return status;
3544 }
3545
3546 /**
3547 * i40e_aq_write_nvm_config - write an nvm config block
3548 * @hw: pointer to the hw struct
3549 * @cmd_flags: NVM access admin command bits
3550 * @data: buffer for result
3551 * @buf_size: buffer size
3552 * @element_count: count of elements to be written
3553 * @cmd_details: pointer to command details structure or NULL
3554 **/
i40e_aq_write_nvm_config(struct i40e_hw * hw,u8 cmd_flags,void * data,u16 buf_size,u16 element_count,struct i40e_asq_cmd_details * cmd_details)3555 enum i40e_status_code i40e_aq_write_nvm_config(struct i40e_hw *hw,
3556 u8 cmd_flags, void *data, u16 buf_size,
3557 u16 element_count,
3558 struct i40e_asq_cmd_details *cmd_details)
3559 {
3560 struct i40e_aq_desc desc;
3561 struct i40e_aqc_nvm_config_write *cmd =
3562 (struct i40e_aqc_nvm_config_write *)&desc.params.raw;
3563 enum i40e_status_code status;
3564
3565 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_nvm_config_write);
3566 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
3567 if (buf_size > I40E_AQ_LARGE_BUF)
3568 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
3569
3570 cmd->element_count = CPU_TO_LE16(element_count);
3571 cmd->cmd_flags = CPU_TO_LE16(cmd_flags);
3572 status = i40e_asq_send_command(hw, &desc, data, buf_size, cmd_details);
3573
3574 return status;
3575 }
3576
3577 /**
3578 * i40e_aq_oem_post_update - triggers an OEM specific flow after update
3579 * @hw: pointer to the hw struct
3580 * @buff: buffer for result
3581 * @buff_size: buffer size
3582 * @cmd_details: pointer to command details structure or NULL
3583 **/
i40e_aq_oem_post_update(struct i40e_hw * hw,void * buff,u16 buff_size,struct i40e_asq_cmd_details * cmd_details)3584 enum i40e_status_code i40e_aq_oem_post_update(struct i40e_hw *hw,
3585 void *buff, u16 buff_size,
3586 struct i40e_asq_cmd_details *cmd_details)
3587 {
3588 struct i40e_aq_desc desc;
3589 enum i40e_status_code status;
3590
3591
3592 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_oem_post_update);
3593 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
3594 if (status && LE16_TO_CPU(desc.retval) == I40E_AQ_RC_ESRCH)
3595 status = I40E_ERR_NOT_IMPLEMENTED;
3596
3597 return status;
3598 }
3599
3600 /**
3601 * i40e_aq_erase_nvm
3602 * @hw: pointer to the hw struct
3603 * @module_pointer: module pointer location in words from the NVM beginning
3604 * @offset: offset in the module (expressed in 4 KB from module's beginning)
3605 * @length: length of the section to be erased (expressed in 4 KB)
3606 * @last_command: tells if this is the last command in a series
3607 * @cmd_details: pointer to command details structure or NULL
3608 *
3609 * Erase the NVM sector using the admin queue commands
3610 **/
i40e_aq_erase_nvm(struct i40e_hw * hw,u8 module_pointer,u32 offset,u16 length,bool last_command,struct i40e_asq_cmd_details * cmd_details)3611 enum i40e_status_code i40e_aq_erase_nvm(struct i40e_hw *hw, u8 module_pointer,
3612 u32 offset, u16 length, bool last_command,
3613 struct i40e_asq_cmd_details *cmd_details)
3614 {
3615 struct i40e_aq_desc desc;
3616 struct i40e_aqc_nvm_update *cmd =
3617 (struct i40e_aqc_nvm_update *)&desc.params.raw;
3618 enum i40e_status_code status;
3619
3620 DEBUGFUNC("i40e_aq_erase_nvm");
3621
3622 /* In offset the highest byte must be zeroed. */
3623 if (offset & 0xFF000000) {
3624 status = I40E_ERR_PARAM;
3625 goto i40e_aq_erase_nvm_exit;
3626 }
3627
3628 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_nvm_erase);
3629
3630 /* If this is the last command in a series, set the proper flag. */
3631 if (last_command)
3632 cmd->command_flags |= I40E_AQ_NVM_LAST_CMD;
3633 cmd->module_pointer = module_pointer;
3634 cmd->offset = CPU_TO_LE32(offset);
3635 cmd->length = CPU_TO_LE16(length);
3636
3637 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
3638
3639 i40e_aq_erase_nvm_exit:
3640 return status;
3641 }
3642
3643 /**
3644 * i40e_parse_discover_capabilities
3645 * @hw: pointer to the hw struct
3646 * @buff: pointer to a buffer containing device/function capability records
3647 * @cap_count: number of capability records in the list
3648 * @list_type_opc: type of capabilities list to parse
3649 *
3650 * Parse the device/function capabilities list.
3651 **/
i40e_parse_discover_capabilities(struct i40e_hw * hw,void * buff,u32 cap_count,enum i40e_admin_queue_opc list_type_opc)3652 static void i40e_parse_discover_capabilities(struct i40e_hw *hw, void *buff,
3653 u32 cap_count,
3654 enum i40e_admin_queue_opc list_type_opc)
3655 {
3656 struct i40e_aqc_list_capabilities_element_resp *cap;
3657 u32 valid_functions, num_functions;
3658 u32 number, logical_id, phys_id;
3659 struct i40e_hw_capabilities *p;
3660 enum i40e_status_code status;
3661 u16 id, ocp_cfg_word0;
3662 u8 major_rev;
3663 u32 i = 0;
3664
3665 cap = (struct i40e_aqc_list_capabilities_element_resp *) buff;
3666
3667 if (list_type_opc == i40e_aqc_opc_list_dev_capabilities)
3668 p = (struct i40e_hw_capabilities *)&hw->dev_caps;
3669 else if (list_type_opc == i40e_aqc_opc_list_func_capabilities)
3670 p = (struct i40e_hw_capabilities *)&hw->func_caps;
3671 else
3672 return;
3673
3674 for (i = 0; i < cap_count; i++, cap++) {
3675 id = LE16_TO_CPU(cap->id);
3676 number = LE32_TO_CPU(cap->number);
3677 logical_id = LE32_TO_CPU(cap->logical_id);
3678 phys_id = LE32_TO_CPU(cap->phys_id);
3679 major_rev = cap->major_rev;
3680
3681 switch (id) {
3682 case I40E_AQ_CAP_ID_SWITCH_MODE:
3683 p->switch_mode = number;
3684 i40e_debug(hw, I40E_DEBUG_INIT,
3685 "HW Capability: Switch mode = %d\n",
3686 p->switch_mode);
3687 break;
3688 case I40E_AQ_CAP_ID_MNG_MODE:
3689 p->management_mode = number;
3690 if (major_rev > 1) {
3691 p->mng_protocols_over_mctp = logical_id;
3692 i40e_debug(hw, I40E_DEBUG_INIT,
3693 "HW Capability: Protocols over MCTP = %d\n",
3694 p->mng_protocols_over_mctp);
3695 } else {
3696 p->mng_protocols_over_mctp = 0;
3697 }
3698 i40e_debug(hw, I40E_DEBUG_INIT,
3699 "HW Capability: Management Mode = %d\n",
3700 p->management_mode);
3701 break;
3702 case I40E_AQ_CAP_ID_NPAR_ACTIVE:
3703 p->npar_enable = number;
3704 i40e_debug(hw, I40E_DEBUG_INIT,
3705 "HW Capability: NPAR enable = %d\n",
3706 p->npar_enable);
3707 break;
3708 case I40E_AQ_CAP_ID_OS2BMC_CAP:
3709 p->os2bmc = number;
3710 i40e_debug(hw, I40E_DEBUG_INIT,
3711 "HW Capability: OS2BMC = %d\n", p->os2bmc);
3712 break;
3713 case I40E_AQ_CAP_ID_FUNCTIONS_VALID:
3714 p->valid_functions = number;
3715 i40e_debug(hw, I40E_DEBUG_INIT,
3716 "HW Capability: Valid Functions = %d\n",
3717 p->valid_functions);
3718 break;
3719 case I40E_AQ_CAP_ID_SRIOV:
3720 if (number == 1)
3721 p->sr_iov_1_1 = TRUE;
3722 i40e_debug(hw, I40E_DEBUG_INIT,
3723 "HW Capability: SR-IOV = %d\n",
3724 p->sr_iov_1_1);
3725 break;
3726 case I40E_AQ_CAP_ID_VF:
3727 p->num_vfs = number;
3728 p->vf_base_id = logical_id;
3729 i40e_debug(hw, I40E_DEBUG_INIT,
3730 "HW Capability: VF count = %d\n",
3731 p->num_vfs);
3732 i40e_debug(hw, I40E_DEBUG_INIT,
3733 "HW Capability: VF base_id = %d\n",
3734 p->vf_base_id);
3735 break;
3736 case I40E_AQ_CAP_ID_VMDQ:
3737 if (number == 1)
3738 p->vmdq = TRUE;
3739 i40e_debug(hw, I40E_DEBUG_INIT,
3740 "HW Capability: VMDQ = %d\n", p->vmdq);
3741 break;
3742 case I40E_AQ_CAP_ID_8021QBG:
3743 if (number == 1)
3744 p->evb_802_1_qbg = TRUE;
3745 i40e_debug(hw, I40E_DEBUG_INIT,
3746 "HW Capability: 802.1Qbg = %d\n", number);
3747 break;
3748 case I40E_AQ_CAP_ID_8021QBR:
3749 if (number == 1)
3750 p->evb_802_1_qbh = TRUE;
3751 i40e_debug(hw, I40E_DEBUG_INIT,
3752 "HW Capability: 802.1Qbh = %d\n", number);
3753 break;
3754 case I40E_AQ_CAP_ID_VSI:
3755 p->num_vsis = number;
3756 i40e_debug(hw, I40E_DEBUG_INIT,
3757 "HW Capability: VSI count = %d\n",
3758 p->num_vsis);
3759 break;
3760 case I40E_AQ_CAP_ID_DCB:
3761 if (number == 1) {
3762 p->dcb = TRUE;
3763 p->enabled_tcmap = logical_id;
3764 p->maxtc = phys_id;
3765 }
3766 i40e_debug(hw, I40E_DEBUG_INIT,
3767 "HW Capability: DCB = %d\n", p->dcb);
3768 i40e_debug(hw, I40E_DEBUG_INIT,
3769 "HW Capability: TC Mapping = %d\n",
3770 logical_id);
3771 i40e_debug(hw, I40E_DEBUG_INIT,
3772 "HW Capability: TC Max = %d\n", p->maxtc);
3773 break;
3774 case I40E_AQ_CAP_ID_FCOE:
3775 if (number == 1)
3776 p->fcoe = TRUE;
3777 i40e_debug(hw, I40E_DEBUG_INIT,
3778 "HW Capability: FCOE = %d\n", p->fcoe);
3779 break;
3780 case I40E_AQ_CAP_ID_ISCSI:
3781 if (number == 1)
3782 p->iscsi = TRUE;
3783 i40e_debug(hw, I40E_DEBUG_INIT,
3784 "HW Capability: iSCSI = %d\n", p->iscsi);
3785 break;
3786 case I40E_AQ_CAP_ID_RSS:
3787 p->rss = TRUE;
3788 p->rss_table_size = number;
3789 p->rss_table_entry_width = logical_id;
3790 i40e_debug(hw, I40E_DEBUG_INIT,
3791 "HW Capability: RSS = %d\n", p->rss);
3792 i40e_debug(hw, I40E_DEBUG_INIT,
3793 "HW Capability: RSS table size = %d\n",
3794 p->rss_table_size);
3795 i40e_debug(hw, I40E_DEBUG_INIT,
3796 "HW Capability: RSS table width = %d\n",
3797 p->rss_table_entry_width);
3798 break;
3799 case I40E_AQ_CAP_ID_RXQ:
3800 p->num_rx_qp = number;
3801 p->base_queue = phys_id;
3802 i40e_debug(hw, I40E_DEBUG_INIT,
3803 "HW Capability: Rx QP = %d\n", number);
3804 i40e_debug(hw, I40E_DEBUG_INIT,
3805 "HW Capability: base_queue = %d\n",
3806 p->base_queue);
3807 break;
3808 case I40E_AQ_CAP_ID_TXQ:
3809 p->num_tx_qp = number;
3810 p->base_queue = phys_id;
3811 i40e_debug(hw, I40E_DEBUG_INIT,
3812 "HW Capability: Tx QP = %d\n", number);
3813 i40e_debug(hw, I40E_DEBUG_INIT,
3814 "HW Capability: base_queue = %d\n",
3815 p->base_queue);
3816 break;
3817 case I40E_AQ_CAP_ID_MSIX:
3818 p->num_msix_vectors = number;
3819 i40e_debug(hw, I40E_DEBUG_INIT,
3820 "HW Capability: MSIX vector count = %d\n",
3821 p->num_msix_vectors);
3822 break;
3823 case I40E_AQ_CAP_ID_VF_MSIX:
3824 p->num_msix_vectors_vf = number;
3825 i40e_debug(hw, I40E_DEBUG_INIT,
3826 "HW Capability: MSIX VF vector count = %d\n",
3827 p->num_msix_vectors_vf);
3828 break;
3829 case I40E_AQ_CAP_ID_FLEX10:
3830 if (major_rev == 1) {
3831 if (number == 1) {
3832 p->flex10_enable = TRUE;
3833 p->flex10_capable = TRUE;
3834 }
3835 } else {
3836 /* Capability revision >= 2 */
3837 if (number & 1)
3838 p->flex10_enable = TRUE;
3839 if (number & 2)
3840 p->flex10_capable = TRUE;
3841 }
3842 p->flex10_mode = logical_id;
3843 p->flex10_status = phys_id;
3844 i40e_debug(hw, I40E_DEBUG_INIT,
3845 "HW Capability: Flex10 mode = %d\n",
3846 p->flex10_mode);
3847 i40e_debug(hw, I40E_DEBUG_INIT,
3848 "HW Capability: Flex10 status = %d\n",
3849 p->flex10_status);
3850 break;
3851 case I40E_AQ_CAP_ID_CEM:
3852 if (number == 1)
3853 p->mgmt_cem = TRUE;
3854 i40e_debug(hw, I40E_DEBUG_INIT,
3855 "HW Capability: CEM = %d\n", p->mgmt_cem);
3856 break;
3857 case I40E_AQ_CAP_ID_IWARP:
3858 if (number == 1)
3859 p->iwarp = TRUE;
3860 i40e_debug(hw, I40E_DEBUG_INIT,
3861 "HW Capability: iWARP = %d\n", p->iwarp);
3862 break;
3863 case I40E_AQ_CAP_ID_LED:
3864 if (phys_id < I40E_HW_CAP_MAX_GPIO)
3865 p->led[phys_id] = TRUE;
3866 i40e_debug(hw, I40E_DEBUG_INIT,
3867 "HW Capability: LED - PIN %d\n", phys_id);
3868 break;
3869 case I40E_AQ_CAP_ID_SDP:
3870 if (phys_id < I40E_HW_CAP_MAX_GPIO)
3871 p->sdp[phys_id] = TRUE;
3872 i40e_debug(hw, I40E_DEBUG_INIT,
3873 "HW Capability: SDP - PIN %d\n", phys_id);
3874 break;
3875 case I40E_AQ_CAP_ID_MDIO:
3876 if (number == 1) {
3877 p->mdio_port_num = phys_id;
3878 p->mdio_port_mode = logical_id;
3879 }
3880 i40e_debug(hw, I40E_DEBUG_INIT,
3881 "HW Capability: MDIO port number = %d\n",
3882 p->mdio_port_num);
3883 i40e_debug(hw, I40E_DEBUG_INIT,
3884 "HW Capability: MDIO port mode = %d\n",
3885 p->mdio_port_mode);
3886 break;
3887 case I40E_AQ_CAP_ID_1588:
3888 if (number == 1)
3889 p->ieee_1588 = TRUE;
3890 i40e_debug(hw, I40E_DEBUG_INIT,
3891 "HW Capability: IEEE 1588 = %d\n",
3892 p->ieee_1588);
3893 break;
3894 case I40E_AQ_CAP_ID_FLOW_DIRECTOR:
3895 p->fd = TRUE;
3896 p->fd_filters_guaranteed = number;
3897 p->fd_filters_best_effort = logical_id;
3898 i40e_debug(hw, I40E_DEBUG_INIT,
3899 "HW Capability: Flow Director = 1\n");
3900 i40e_debug(hw, I40E_DEBUG_INIT,
3901 "HW Capability: Guaranteed FD filters = %d\n",
3902 p->fd_filters_guaranteed);
3903 break;
3904 case I40E_AQ_CAP_ID_WSR_PROT:
3905 p->wr_csr_prot = (u64)number;
3906 p->wr_csr_prot |= (u64)logical_id << 32;
3907 i40e_debug(hw, I40E_DEBUG_INIT,
3908 "HW Capability: wr_csr_prot = 0x%llX\n\n",
3909 (p->wr_csr_prot & 0xffff));
3910 break;
3911 case I40E_AQ_CAP_ID_NVM_MGMT:
3912 if (number & I40E_NVM_MGMT_SEC_REV_DISABLED)
3913 p->sec_rev_disabled = TRUE;
3914 if (number & I40E_NVM_MGMT_UPDATE_DISABLED)
3915 p->update_disabled = TRUE;
3916 break;
3917 case I40E_AQ_CAP_ID_WOL_AND_PROXY:
3918 hw->num_wol_proxy_filters = (u16)number;
3919 hw->wol_proxy_vsi_seid = (u16)logical_id;
3920 p->apm_wol_support = phys_id & I40E_WOL_SUPPORT_MASK;
3921 if (phys_id & I40E_ACPI_PROGRAMMING_METHOD_MASK)
3922 p->acpi_prog_method = I40E_ACPI_PROGRAMMING_METHOD_AQC_FPK;
3923 else
3924 p->acpi_prog_method = I40E_ACPI_PROGRAMMING_METHOD_HW_FVL;
3925 p->proxy_support = (phys_id & I40E_PROXY_SUPPORT_MASK) ? 1 : 0;
3926 i40e_debug(hw, I40E_DEBUG_INIT,
3927 "HW Capability: WOL proxy filters = %d\n",
3928 hw->num_wol_proxy_filters);
3929 break;
3930 default:
3931 break;
3932 }
3933 }
3934
3935 if (p->fcoe)
3936 i40e_debug(hw, I40E_DEBUG_ALL, "device is FCoE capable\n");
3937
3938 /* Always disable FCoE if compiled without the I40E_FCOE_ENA flag */
3939 p->fcoe = FALSE;
3940
3941 /* count the enabled ports (aka the "not disabled" ports) */
3942 hw->num_ports = 0;
3943 for (i = 0; i < 4; i++) {
3944 u32 port_cfg_reg = I40E_PRTGEN_CNF + (4 * i);
3945 u64 port_cfg = 0;
3946
3947 /* use AQ read to get the physical register offset instead
3948 * of the port relative offset
3949 */
3950 i40e_aq_debug_read_register(hw, port_cfg_reg, &port_cfg, NULL);
3951 if (!(port_cfg & I40E_PRTGEN_CNF_PORT_DIS_MASK))
3952 hw->num_ports++;
3953 }
3954
3955 /* OCP cards case: if a mezz is removed the ethernet port is at
3956 * disabled state in PRTGEN_CNF register. Additional NVM read is
3957 * needed in order to check if we are dealing with OCP card.
3958 * Those cards have 4 PFs at minimum, so using PRTGEN_CNF for counting
3959 * physical ports results in wrong partition id calculation and thus
3960 * not supporting WoL.
3961 */
3962 if (hw->mac.type == I40E_MAC_X722) {
3963 if (i40e_acquire_nvm(hw, I40E_RESOURCE_READ) == I40E_SUCCESS) {
3964 status = i40e_aq_read_nvm(hw, I40E_SR_EMP_MODULE_PTR,
3965 2 * I40E_SR_OCP_CFG_WORD0,
3966 sizeof(ocp_cfg_word0),
3967 &ocp_cfg_word0, TRUE, NULL);
3968 if (status == I40E_SUCCESS &&
3969 (ocp_cfg_word0 & I40E_SR_OCP_ENABLED))
3970 hw->num_ports = 4;
3971 i40e_release_nvm(hw);
3972 }
3973 }
3974
3975 valid_functions = p->valid_functions;
3976 num_functions = 0;
3977 while (valid_functions) {
3978 if (valid_functions & 1)
3979 num_functions++;
3980 valid_functions >>= 1;
3981 }
3982
3983 /* partition id is 1-based, and functions are evenly spread
3984 * across the ports as partitions
3985 */
3986 if (hw->num_ports != 0) {
3987 hw->partition_id = (hw->pf_id / hw->num_ports) + 1;
3988 hw->num_partitions = num_functions / hw->num_ports;
3989 }
3990
3991 /* additional HW specific goodies that might
3992 * someday be HW version specific
3993 */
3994 p->rx_buf_chain_len = I40E_MAX_CHAINED_RX_BUFFERS;
3995 }
3996
3997 /**
3998 * i40e_aq_discover_capabilities
3999 * @hw: pointer to the hw struct
4000 * @buff: a virtual buffer to hold the capabilities
4001 * @buff_size: Size of the virtual buffer
4002 * @data_size: Size of the returned data, or buff size needed if AQ err==ENOMEM
4003 * @list_type_opc: capabilities type to discover - pass in the command opcode
4004 * @cmd_details: pointer to command details structure or NULL
4005 *
4006 * Get the device capabilities descriptions from the firmware
4007 **/
i40e_aq_discover_capabilities(struct i40e_hw * hw,void * buff,u16 buff_size,u16 * data_size,enum i40e_admin_queue_opc list_type_opc,struct i40e_asq_cmd_details * cmd_details)4008 enum i40e_status_code i40e_aq_discover_capabilities(struct i40e_hw *hw,
4009 void *buff, u16 buff_size, u16 *data_size,
4010 enum i40e_admin_queue_opc list_type_opc,
4011 struct i40e_asq_cmd_details *cmd_details)
4012 {
4013 struct i40e_aqc_list_capabilites *cmd;
4014 struct i40e_aq_desc desc;
4015 enum i40e_status_code status = I40E_SUCCESS;
4016
4017 cmd = (struct i40e_aqc_list_capabilites *)&desc.params.raw;
4018
4019 if (list_type_opc != i40e_aqc_opc_list_func_capabilities &&
4020 list_type_opc != i40e_aqc_opc_list_dev_capabilities) {
4021 status = I40E_ERR_PARAM;
4022 goto exit;
4023 }
4024
4025 i40e_fill_default_direct_cmd_desc(&desc, list_type_opc);
4026
4027 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
4028 if (buff_size > I40E_AQ_LARGE_BUF)
4029 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
4030
4031 status = i40e_asq_send_command(hw, &desc, buff, buff_size, cmd_details);
4032 *data_size = LE16_TO_CPU(desc.datalen);
4033
4034 if (status)
4035 goto exit;
4036
4037 i40e_parse_discover_capabilities(hw, buff, LE32_TO_CPU(cmd->count),
4038 list_type_opc);
4039
4040 exit:
4041 return status;
4042 }
4043
4044 /**
4045 * i40e_aq_update_nvm
4046 * @hw: pointer to the hw struct
4047 * @module_pointer: module pointer location in words from the NVM beginning
4048 * @offset: byte offset from the module beginning
4049 * @length: length of the section to be written (in bytes from the offset)
4050 * @data: command buffer (size [bytes] = length)
4051 * @last_command: tells if this is the last command in a series
4052 * @preservation_flags: Preservation mode flags
4053 * @cmd_details: pointer to command details structure or NULL
4054 *
4055 * Update the NVM using the admin queue commands
4056 **/
i40e_aq_update_nvm(struct i40e_hw * hw,u8 module_pointer,u32 offset,u16 length,void * data,bool last_command,u8 preservation_flags,struct i40e_asq_cmd_details * cmd_details)4057 enum i40e_status_code i40e_aq_update_nvm(struct i40e_hw *hw, u8 module_pointer,
4058 u32 offset, u16 length, void *data,
4059 bool last_command, u8 preservation_flags,
4060 struct i40e_asq_cmd_details *cmd_details)
4061 {
4062 struct i40e_aq_desc desc;
4063 struct i40e_aqc_nvm_update *cmd =
4064 (struct i40e_aqc_nvm_update *)&desc.params.raw;
4065 enum i40e_status_code status;
4066
4067 DEBUGFUNC("i40e_aq_update_nvm");
4068
4069 /* In offset the highest byte must be zeroed. */
4070 if (offset & 0xFF000000) {
4071 status = I40E_ERR_PARAM;
4072 goto i40e_aq_update_nvm_exit;
4073 }
4074
4075 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_nvm_update);
4076
4077 /* If this is the last command in a series, set the proper flag. */
4078 if (last_command)
4079 cmd->command_flags |= I40E_AQ_NVM_LAST_CMD;
4080 if (hw->mac.type == I40E_MAC_X722) {
4081 if (preservation_flags == I40E_NVM_PRESERVATION_FLAGS_SELECTED)
4082 cmd->command_flags |=
4083 (I40E_AQ_NVM_PRESERVATION_FLAGS_SELECTED <<
4084 I40E_AQ_NVM_PRESERVATION_FLAGS_SHIFT);
4085 else if (preservation_flags == I40E_NVM_PRESERVATION_FLAGS_ALL)
4086 cmd->command_flags |=
4087 (I40E_AQ_NVM_PRESERVATION_FLAGS_ALL <<
4088 I40E_AQ_NVM_PRESERVATION_FLAGS_SHIFT);
4089 }
4090 cmd->module_pointer = module_pointer;
4091 cmd->offset = CPU_TO_LE32(offset);
4092 cmd->length = CPU_TO_LE16(length);
4093
4094 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
4095 if (length > I40E_AQ_LARGE_BUF)
4096 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
4097
4098 status = i40e_asq_send_command(hw, &desc, data, length, cmd_details);
4099
4100 i40e_aq_update_nvm_exit:
4101 return status;
4102 }
4103
4104 /**
4105 * i40e_aq_nvm_progress
4106 * @hw: pointer to the hw struct
4107 * @progress: pointer to progress returned from AQ
4108 * @cmd_details: pointer to command details structure or NULL
4109 *
4110 * Gets progress of flash rearrangement process
4111 **/
i40e_aq_nvm_progress(struct i40e_hw * hw,u8 * progress,struct i40e_asq_cmd_details * cmd_details)4112 enum i40e_status_code i40e_aq_nvm_progress(struct i40e_hw *hw, u8 *progress,
4113 struct i40e_asq_cmd_details *cmd_details)
4114 {
4115 enum i40e_status_code status;
4116 struct i40e_aq_desc desc;
4117
4118 DEBUGFUNC("i40e_aq_nvm_progress");
4119
4120 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_nvm_progress);
4121 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4122 *progress = desc.params.raw[0];
4123 return status;
4124 }
4125
4126 /**
4127 * i40e_aq_get_lldp_mib
4128 * @hw: pointer to the hw struct
4129 * @bridge_type: type of bridge requested
4130 * @mib_type: Local, Remote or both Local and Remote MIBs
4131 * @buff: pointer to a user supplied buffer to store the MIB block
4132 * @buff_size: size of the buffer (in bytes)
4133 * @local_len : length of the returned Local LLDP MIB
4134 * @remote_len: length of the returned Remote LLDP MIB
4135 * @cmd_details: pointer to command details structure or NULL
4136 *
4137 * Requests the complete LLDP MIB (entire packet).
4138 **/
i40e_aq_get_lldp_mib(struct i40e_hw * hw,u8 bridge_type,u8 mib_type,void * buff,u16 buff_size,u16 * local_len,u16 * remote_len,struct i40e_asq_cmd_details * cmd_details)4139 enum i40e_status_code i40e_aq_get_lldp_mib(struct i40e_hw *hw, u8 bridge_type,
4140 u8 mib_type, void *buff, u16 buff_size,
4141 u16 *local_len, u16 *remote_len,
4142 struct i40e_asq_cmd_details *cmd_details)
4143 {
4144 struct i40e_aq_desc desc;
4145 struct i40e_aqc_lldp_get_mib *cmd =
4146 (struct i40e_aqc_lldp_get_mib *)&desc.params.raw;
4147 struct i40e_aqc_lldp_get_mib *resp =
4148 (struct i40e_aqc_lldp_get_mib *)&desc.params.raw;
4149 enum i40e_status_code status;
4150
4151 if (buff_size == 0 || !buff)
4152 return I40E_ERR_PARAM;
4153
4154 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_lldp_get_mib);
4155 /* Indirect Command */
4156 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
4157
4158 cmd->type = mib_type & I40E_AQ_LLDP_MIB_TYPE_MASK;
4159 cmd->type |= ((bridge_type << I40E_AQ_LLDP_BRIDGE_TYPE_SHIFT) &
4160 I40E_AQ_LLDP_BRIDGE_TYPE_MASK);
4161
4162 desc.datalen = CPU_TO_LE16(buff_size);
4163
4164 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
4165 if (buff_size > I40E_AQ_LARGE_BUF)
4166 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
4167
4168 status = i40e_asq_send_command(hw, &desc, buff, buff_size, cmd_details);
4169 if (!status) {
4170 if (local_len != NULL)
4171 *local_len = LE16_TO_CPU(resp->local_len);
4172 if (remote_len != NULL)
4173 *remote_len = LE16_TO_CPU(resp->remote_len);
4174 }
4175
4176 return status;
4177 }
4178
4179 /**
4180 * i40e_aq_set_lldp_mib - Set the LLDP MIB
4181 * @hw: pointer to the hw struct
4182 * @mib_type: Local, Remote or both Local and Remote MIBs
4183 * @buff: pointer to a user supplied buffer to store the MIB block
4184 * @buff_size: size of the buffer (in bytes)
4185 * @cmd_details: pointer to command details structure or NULL
4186 *
4187 * Set the LLDP MIB.
4188 **/
i40e_aq_set_lldp_mib(struct i40e_hw * hw,u8 mib_type,void * buff,u16 buff_size,struct i40e_asq_cmd_details * cmd_details)4189 enum i40e_status_code i40e_aq_set_lldp_mib(struct i40e_hw *hw,
4190 u8 mib_type, void *buff, u16 buff_size,
4191 struct i40e_asq_cmd_details *cmd_details)
4192 {
4193 struct i40e_aq_desc desc;
4194 struct i40e_aqc_lldp_set_local_mib *cmd =
4195 (struct i40e_aqc_lldp_set_local_mib *)&desc.params.raw;
4196 enum i40e_status_code status;
4197
4198 if (buff_size == 0 || !buff)
4199 return I40E_ERR_PARAM;
4200
4201 i40e_fill_default_direct_cmd_desc(&desc,
4202 i40e_aqc_opc_lldp_set_local_mib);
4203 /* Indirect Command */
4204 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
4205 if (buff_size > I40E_AQ_LARGE_BUF)
4206 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
4207 desc.datalen = CPU_TO_LE16(buff_size);
4208
4209 cmd->type = mib_type;
4210 cmd->length = CPU_TO_LE16(buff_size);
4211 cmd->address_high = CPU_TO_LE32(I40E_HI_WORD((u64)buff));
4212 cmd->address_low = CPU_TO_LE32(I40E_LO_DWORD((u64)buff));
4213
4214 status = i40e_asq_send_command(hw, &desc, buff, buff_size, cmd_details);
4215 return status;
4216 }
4217
4218 /**
4219 * i40e_aq_cfg_lldp_mib_change_event
4220 * @hw: pointer to the hw struct
4221 * @enable_update: Enable or Disable event posting
4222 * @cmd_details: pointer to command details structure or NULL
4223 *
4224 * Enable or Disable posting of an event on ARQ when LLDP MIB
4225 * associated with the interface changes
4226 **/
i40e_aq_cfg_lldp_mib_change_event(struct i40e_hw * hw,bool enable_update,struct i40e_asq_cmd_details * cmd_details)4227 enum i40e_status_code i40e_aq_cfg_lldp_mib_change_event(struct i40e_hw *hw,
4228 bool enable_update,
4229 struct i40e_asq_cmd_details *cmd_details)
4230 {
4231 struct i40e_aq_desc desc;
4232 struct i40e_aqc_lldp_update_mib *cmd =
4233 (struct i40e_aqc_lldp_update_mib *)&desc.params.raw;
4234 enum i40e_status_code status;
4235
4236 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_lldp_update_mib);
4237
4238 if (!enable_update)
4239 cmd->command |= I40E_AQ_LLDP_MIB_UPDATE_DISABLE;
4240
4241 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4242
4243 return status;
4244 }
4245
4246 /**
4247 * i40e_aq_add_lldp_tlv
4248 * @hw: pointer to the hw struct
4249 * @bridge_type: type of bridge
4250 * @buff: buffer with TLV to add
4251 * @buff_size: length of the buffer
4252 * @tlv_len: length of the TLV to be added
4253 * @mib_len: length of the LLDP MIB returned in response
4254 * @cmd_details: pointer to command details structure or NULL
4255 *
4256 * Add the specified TLV to LLDP Local MIB for the given bridge type,
4257 * it is responsibility of the caller to make sure that the TLV is not
4258 * already present in the LLDPDU.
4259 * In return firmware will write the complete LLDP MIB with the newly
4260 * added TLV in the response buffer.
4261 **/
i40e_aq_add_lldp_tlv(struct i40e_hw * hw,u8 bridge_type,void * buff,u16 buff_size,u16 tlv_len,u16 * mib_len,struct i40e_asq_cmd_details * cmd_details)4262 enum i40e_status_code i40e_aq_add_lldp_tlv(struct i40e_hw *hw, u8 bridge_type,
4263 void *buff, u16 buff_size, u16 tlv_len,
4264 u16 *mib_len,
4265 struct i40e_asq_cmd_details *cmd_details)
4266 {
4267 struct i40e_aq_desc desc;
4268 struct i40e_aqc_lldp_add_tlv *cmd =
4269 (struct i40e_aqc_lldp_add_tlv *)&desc.params.raw;
4270 enum i40e_status_code status;
4271
4272 if (buff_size == 0 || !buff || tlv_len == 0)
4273 return I40E_ERR_PARAM;
4274
4275 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_lldp_add_tlv);
4276
4277 /* Indirect Command */
4278 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
4279 if (buff_size > I40E_AQ_LARGE_BUF)
4280 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
4281 desc.datalen = CPU_TO_LE16(buff_size);
4282
4283 cmd->type = ((bridge_type << I40E_AQ_LLDP_BRIDGE_TYPE_SHIFT) &
4284 I40E_AQ_LLDP_BRIDGE_TYPE_MASK);
4285 cmd->len = CPU_TO_LE16(tlv_len);
4286
4287 status = i40e_asq_send_command(hw, &desc, buff, buff_size, cmd_details);
4288 if (!status) {
4289 if (mib_len != NULL)
4290 *mib_len = LE16_TO_CPU(desc.datalen);
4291 }
4292
4293 return status;
4294 }
4295
4296 /**
4297 * i40e_aq_update_lldp_tlv
4298 * @hw: pointer to the hw struct
4299 * @bridge_type: type of bridge
4300 * @buff: buffer with TLV to update
4301 * @buff_size: size of the buffer holding original and updated TLVs
4302 * @old_len: Length of the Original TLV
4303 * @new_len: Length of the Updated TLV
4304 * @offset: offset of the updated TLV in the buff
4305 * @mib_len: length of the returned LLDP MIB
4306 * @cmd_details: pointer to command details structure or NULL
4307 *
4308 * Update the specified TLV to the LLDP Local MIB for the given bridge type.
4309 * Firmware will place the complete LLDP MIB in response buffer with the
4310 * updated TLV.
4311 **/
i40e_aq_update_lldp_tlv(struct i40e_hw * hw,u8 bridge_type,void * buff,u16 buff_size,u16 old_len,u16 new_len,u16 offset,u16 * mib_len,struct i40e_asq_cmd_details * cmd_details)4312 enum i40e_status_code i40e_aq_update_lldp_tlv(struct i40e_hw *hw,
4313 u8 bridge_type, void *buff, u16 buff_size,
4314 u16 old_len, u16 new_len, u16 offset,
4315 u16 *mib_len,
4316 struct i40e_asq_cmd_details *cmd_details)
4317 {
4318 struct i40e_aq_desc desc;
4319 struct i40e_aqc_lldp_update_tlv *cmd =
4320 (struct i40e_aqc_lldp_update_tlv *)&desc.params.raw;
4321 enum i40e_status_code status;
4322
4323 if (buff_size == 0 || !buff || offset == 0 ||
4324 old_len == 0 || new_len == 0)
4325 return I40E_ERR_PARAM;
4326
4327 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_lldp_update_tlv);
4328
4329 /* Indirect Command */
4330 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
4331 if (buff_size > I40E_AQ_LARGE_BUF)
4332 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
4333 desc.datalen = CPU_TO_LE16(buff_size);
4334
4335 cmd->type = ((bridge_type << I40E_AQ_LLDP_BRIDGE_TYPE_SHIFT) &
4336 I40E_AQ_LLDP_BRIDGE_TYPE_MASK);
4337 cmd->old_len = CPU_TO_LE16(old_len);
4338 cmd->new_offset = CPU_TO_LE16(offset);
4339 cmd->new_len = CPU_TO_LE16(new_len);
4340
4341 status = i40e_asq_send_command(hw, &desc, buff, buff_size, cmd_details);
4342 if (!status) {
4343 if (mib_len != NULL)
4344 *mib_len = LE16_TO_CPU(desc.datalen);
4345 }
4346
4347 return status;
4348 }
4349
4350 /**
4351 * i40e_aq_delete_lldp_tlv
4352 * @hw: pointer to the hw struct
4353 * @bridge_type: type of bridge
4354 * @buff: pointer to a user supplied buffer that has the TLV
4355 * @buff_size: length of the buffer
4356 * @tlv_len: length of the TLV to be deleted
4357 * @mib_len: length of the returned LLDP MIB
4358 * @cmd_details: pointer to command details structure or NULL
4359 *
4360 * Delete the specified TLV from LLDP Local MIB for the given bridge type.
4361 * The firmware places the entire LLDP MIB in the response buffer.
4362 **/
i40e_aq_delete_lldp_tlv(struct i40e_hw * hw,u8 bridge_type,void * buff,u16 buff_size,u16 tlv_len,u16 * mib_len,struct i40e_asq_cmd_details * cmd_details)4363 enum i40e_status_code i40e_aq_delete_lldp_tlv(struct i40e_hw *hw,
4364 u8 bridge_type, void *buff, u16 buff_size,
4365 u16 tlv_len, u16 *mib_len,
4366 struct i40e_asq_cmd_details *cmd_details)
4367 {
4368 struct i40e_aq_desc desc;
4369 struct i40e_aqc_lldp_add_tlv *cmd =
4370 (struct i40e_aqc_lldp_add_tlv *)&desc.params.raw;
4371 enum i40e_status_code status;
4372
4373 if (buff_size == 0 || !buff)
4374 return I40E_ERR_PARAM;
4375
4376 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_lldp_delete_tlv);
4377
4378 /* Indirect Command */
4379 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
4380 if (buff_size > I40E_AQ_LARGE_BUF)
4381 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
4382 desc.datalen = CPU_TO_LE16(buff_size);
4383 cmd->len = CPU_TO_LE16(tlv_len);
4384 cmd->type = ((bridge_type << I40E_AQ_LLDP_BRIDGE_TYPE_SHIFT) &
4385 I40E_AQ_LLDP_BRIDGE_TYPE_MASK);
4386
4387 status = i40e_asq_send_command(hw, &desc, buff, buff_size, cmd_details);
4388 if (!status) {
4389 if (mib_len != NULL)
4390 *mib_len = LE16_TO_CPU(desc.datalen);
4391 }
4392
4393 return status;
4394 }
4395
4396 /**
4397 * i40e_aq_stop_lldp
4398 * @hw: pointer to the hw struct
4399 * @shutdown_agent: True if LLDP Agent needs to be Shutdown
4400 * @cmd_details: pointer to command details structure or NULL
4401 *
4402 * Stop or Shutdown the embedded LLDP Agent
4403 **/
i40e_aq_stop_lldp(struct i40e_hw * hw,bool shutdown_agent,struct i40e_asq_cmd_details * cmd_details)4404 enum i40e_status_code i40e_aq_stop_lldp(struct i40e_hw *hw, bool shutdown_agent,
4405 struct i40e_asq_cmd_details *cmd_details)
4406 {
4407 struct i40e_aq_desc desc;
4408 struct i40e_aqc_lldp_stop *cmd =
4409 (struct i40e_aqc_lldp_stop *)&desc.params.raw;
4410 enum i40e_status_code status;
4411
4412 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_lldp_stop);
4413
4414 if (shutdown_agent)
4415 cmd->command |= I40E_AQ_LLDP_AGENT_SHUTDOWN;
4416
4417 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4418
4419 return status;
4420 }
4421
4422 /**
4423 * i40e_aq_start_lldp
4424 * @hw: pointer to the hw struct
4425 * @cmd_details: pointer to command details structure or NULL
4426 *
4427 * Start the embedded LLDP Agent on all ports.
4428 **/
i40e_aq_start_lldp(struct i40e_hw * hw,struct i40e_asq_cmd_details * cmd_details)4429 enum i40e_status_code i40e_aq_start_lldp(struct i40e_hw *hw,
4430 struct i40e_asq_cmd_details *cmd_details)
4431 {
4432 struct i40e_aq_desc desc;
4433 struct i40e_aqc_lldp_start *cmd =
4434 (struct i40e_aqc_lldp_start *)&desc.params.raw;
4435 enum i40e_status_code status;
4436
4437 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_lldp_start);
4438
4439 cmd->command = I40E_AQ_LLDP_AGENT_START;
4440 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4441
4442 return status;
4443 }
4444
4445 /**
4446 * i40e_aq_set_dcb_parameters
4447 * @hw: pointer to the hw struct
4448 * @cmd_details: pointer to command details structure or NULL
4449 * @dcb_enable: True if DCB configuration needs to be applied
4450 *
4451 **/
4452 enum i40e_status_code
i40e_aq_set_dcb_parameters(struct i40e_hw * hw,bool dcb_enable,struct i40e_asq_cmd_details * cmd_details)4453 i40e_aq_set_dcb_parameters(struct i40e_hw *hw, bool dcb_enable,
4454 struct i40e_asq_cmd_details *cmd_details)
4455 {
4456 struct i40e_aq_desc desc;
4457 struct i40e_aqc_set_dcb_parameters *cmd =
4458 (struct i40e_aqc_set_dcb_parameters *)&desc.params.raw;
4459 enum i40e_status_code status;
4460
4461 if ((hw->mac.type != I40E_MAC_XL710) ||
4462 ((hw->aq.api_maj_ver < 1) ||
4463 ((hw->aq.api_maj_ver == 1) && (hw->aq.api_min_ver < 6))))
4464 return I40E_ERR_DEVICE_NOT_SUPPORTED;
4465
4466 i40e_fill_default_direct_cmd_desc(&desc,
4467 i40e_aqc_opc_set_dcb_parameters);
4468
4469 if (dcb_enable) {
4470 cmd->valid_flags = I40E_DCB_VALID;
4471 cmd->command = I40E_AQ_DCB_SET_AGENT;
4472 }
4473 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4474
4475 return status;
4476 }
4477
4478 /**
4479 * i40e_aq_get_cee_dcb_config
4480 * @hw: pointer to the hw struct
4481 * @buff: response buffer that stores CEE operational configuration
4482 * @buff_size: size of the buffer passed
4483 * @cmd_details: pointer to command details structure or NULL
4484 *
4485 * Get CEE DCBX mode operational configuration from firmware
4486 **/
i40e_aq_get_cee_dcb_config(struct i40e_hw * hw,void * buff,u16 buff_size,struct i40e_asq_cmd_details * cmd_details)4487 enum i40e_status_code i40e_aq_get_cee_dcb_config(struct i40e_hw *hw,
4488 void *buff, u16 buff_size,
4489 struct i40e_asq_cmd_details *cmd_details)
4490 {
4491 struct i40e_aq_desc desc;
4492 enum i40e_status_code status;
4493
4494 if (buff_size == 0 || !buff)
4495 return I40E_ERR_PARAM;
4496
4497 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_get_cee_dcb_cfg);
4498
4499 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
4500 status = i40e_asq_send_command(hw, &desc, (void *)buff, buff_size,
4501 cmd_details);
4502
4503 return status;
4504 }
4505
4506 /**
4507 * i40e_aq_start_stop_dcbx - Start/Stop DCBx service in FW
4508 * @hw: pointer to the hw struct
4509 * @start_agent: True if DCBx Agent needs to be Started
4510 * False if DCBx Agent needs to be Stopped
4511 * @cmd_details: pointer to command details structure or NULL
4512 *
4513 * Start/Stop the embedded dcbx Agent
4514 **/
i40e_aq_start_stop_dcbx(struct i40e_hw * hw,bool start_agent,struct i40e_asq_cmd_details * cmd_details)4515 enum i40e_status_code i40e_aq_start_stop_dcbx(struct i40e_hw *hw,
4516 bool start_agent,
4517 struct i40e_asq_cmd_details *cmd_details)
4518 {
4519 struct i40e_aq_desc desc;
4520 struct i40e_aqc_lldp_stop_start_specific_agent *cmd =
4521 (struct i40e_aqc_lldp_stop_start_specific_agent *)
4522 &desc.params.raw;
4523 enum i40e_status_code status;
4524
4525 i40e_fill_default_direct_cmd_desc(&desc,
4526 i40e_aqc_opc_lldp_stop_start_spec_agent);
4527
4528 if (start_agent)
4529 cmd->command = I40E_AQC_START_SPECIFIC_AGENT_MASK;
4530
4531 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4532
4533 return status;
4534 }
4535
4536 /**
4537 * i40e_aq_add_udp_tunnel
4538 * @hw: pointer to the hw struct
4539 * @udp_port: the UDP port to add in Host byte order
4540 * @protocol_index: protocol index type
4541 * @filter_index: pointer to filter index
4542 * @cmd_details: pointer to command details structure or NULL
4543 *
4544 * Note: Firmware expects the udp_port value to be in Little Endian format,
4545 * and this function will call CPU_TO_LE16 to convert from Host byte order to
4546 * Little Endian order.
4547 **/
i40e_aq_add_udp_tunnel(struct i40e_hw * hw,u16 udp_port,u8 protocol_index,u8 * filter_index,struct i40e_asq_cmd_details * cmd_details)4548 enum i40e_status_code i40e_aq_add_udp_tunnel(struct i40e_hw *hw,
4549 u16 udp_port, u8 protocol_index,
4550 u8 *filter_index,
4551 struct i40e_asq_cmd_details *cmd_details)
4552 {
4553 struct i40e_aq_desc desc;
4554 struct i40e_aqc_add_udp_tunnel *cmd =
4555 (struct i40e_aqc_add_udp_tunnel *)&desc.params.raw;
4556 struct i40e_aqc_del_udp_tunnel_completion *resp =
4557 (struct i40e_aqc_del_udp_tunnel_completion *)&desc.params.raw;
4558 enum i40e_status_code status;
4559
4560 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_add_udp_tunnel);
4561
4562 cmd->udp_port = CPU_TO_LE16(udp_port);
4563 cmd->protocol_type = protocol_index;
4564
4565 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4566
4567 if (!status && filter_index)
4568 *filter_index = resp->index;
4569
4570 return status;
4571 }
4572
4573 /**
4574 * i40e_aq_del_udp_tunnel
4575 * @hw: pointer to the hw struct
4576 * @index: filter index
4577 * @cmd_details: pointer to command details structure or NULL
4578 **/
i40e_aq_del_udp_tunnel(struct i40e_hw * hw,u8 index,struct i40e_asq_cmd_details * cmd_details)4579 enum i40e_status_code i40e_aq_del_udp_tunnel(struct i40e_hw *hw, u8 index,
4580 struct i40e_asq_cmd_details *cmd_details)
4581 {
4582 struct i40e_aq_desc desc;
4583 struct i40e_aqc_remove_udp_tunnel *cmd =
4584 (struct i40e_aqc_remove_udp_tunnel *)&desc.params.raw;
4585 enum i40e_status_code status;
4586
4587 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_del_udp_tunnel);
4588
4589 cmd->index = index;
4590
4591 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4592
4593 return status;
4594 }
4595
4596 /**
4597 * i40e_aq_get_switch_resource_alloc (0x0204)
4598 * @hw: pointer to the hw struct
4599 * @num_entries: pointer to u8 to store the number of resource entries returned
4600 * @buf: pointer to a user supplied buffer. This buffer must be large enough
4601 * to store the resource information for all resource types. Each
4602 * resource type is a i40e_aqc_switch_resource_alloc_data structure.
4603 * @count: size, in bytes, of the buffer provided
4604 * @cmd_details: pointer to command details structure or NULL
4605 *
4606 * Query the resources allocated to a function.
4607 **/
i40e_aq_get_switch_resource_alloc(struct i40e_hw * hw,u8 * num_entries,struct i40e_aqc_switch_resource_alloc_element_resp * buf,u16 count,struct i40e_asq_cmd_details * cmd_details)4608 enum i40e_status_code i40e_aq_get_switch_resource_alloc(struct i40e_hw *hw,
4609 u8 *num_entries,
4610 struct i40e_aqc_switch_resource_alloc_element_resp *buf,
4611 u16 count,
4612 struct i40e_asq_cmd_details *cmd_details)
4613 {
4614 struct i40e_aq_desc desc;
4615 struct i40e_aqc_get_switch_resource_alloc *cmd_resp =
4616 (struct i40e_aqc_get_switch_resource_alloc *)&desc.params.raw;
4617 enum i40e_status_code status;
4618 u16 length = count * sizeof(*buf);
4619
4620 i40e_fill_default_direct_cmd_desc(&desc,
4621 i40e_aqc_opc_get_switch_resource_alloc);
4622
4623 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
4624 if (length > I40E_AQ_LARGE_BUF)
4625 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
4626
4627 status = i40e_asq_send_command(hw, &desc, buf, length, cmd_details);
4628
4629 if (!status && num_entries)
4630 *num_entries = cmd_resp->num_entries;
4631
4632 return status;
4633 }
4634
4635 /**
4636 * i40e_aq_delete_element - Delete switch element
4637 * @hw: pointer to the hw struct
4638 * @seid: the SEID to delete from the switch
4639 * @cmd_details: pointer to command details structure or NULL
4640 *
4641 * This deletes a switch element from the switch.
4642 **/
i40e_aq_delete_element(struct i40e_hw * hw,u16 seid,struct i40e_asq_cmd_details * cmd_details)4643 enum i40e_status_code i40e_aq_delete_element(struct i40e_hw *hw, u16 seid,
4644 struct i40e_asq_cmd_details *cmd_details)
4645 {
4646 struct i40e_aq_desc desc;
4647 struct i40e_aqc_switch_seid *cmd =
4648 (struct i40e_aqc_switch_seid *)&desc.params.raw;
4649 enum i40e_status_code status;
4650
4651 if (seid == 0)
4652 return I40E_ERR_PARAM;
4653
4654 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_delete_element);
4655
4656 cmd->seid = CPU_TO_LE16(seid);
4657
4658 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4659
4660 return status;
4661 }
4662
4663 /**
4664 * i40e_aq_add_pvirt - Instantiate a Port Virtualizer on a port
4665 * @hw: pointer to the hw struct
4666 * @flags: component flags
4667 * @mac_seid: uplink seid (MAC SEID)
4668 * @vsi_seid: connected vsi seid
4669 * @ret_seid: seid of create pv component
4670 *
4671 * This instantiates an i40e port virtualizer with specified flags.
4672 * Depending on specified flags the port virtualizer can act as a
4673 * 802.1Qbr port virtualizer or a 802.1Qbg S-component.
4674 */
i40e_aq_add_pvirt(struct i40e_hw * hw,u16 flags,u16 mac_seid,u16 vsi_seid,u16 * ret_seid)4675 enum i40e_status_code i40e_aq_add_pvirt(struct i40e_hw *hw, u16 flags,
4676 u16 mac_seid, u16 vsi_seid,
4677 u16 *ret_seid)
4678 {
4679 struct i40e_aq_desc desc;
4680 struct i40e_aqc_add_update_pv *cmd =
4681 (struct i40e_aqc_add_update_pv *)&desc.params.raw;
4682 struct i40e_aqc_add_update_pv_completion *resp =
4683 (struct i40e_aqc_add_update_pv_completion *)&desc.params.raw;
4684 enum i40e_status_code status;
4685
4686 if (vsi_seid == 0)
4687 return I40E_ERR_PARAM;
4688
4689 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_add_pv);
4690 cmd->command_flags = CPU_TO_LE16(flags);
4691 cmd->uplink_seid = CPU_TO_LE16(mac_seid);
4692 cmd->connected_seid = CPU_TO_LE16(vsi_seid);
4693
4694 status = i40e_asq_send_command(hw, &desc, NULL, 0, NULL);
4695 if (!status && ret_seid)
4696 *ret_seid = LE16_TO_CPU(resp->pv_seid);
4697
4698 return status;
4699 }
4700
4701 /**
4702 * i40e_aq_add_tag - Add an S/E-tag
4703 * @hw: pointer to the hw struct
4704 * @direct_to_queue: should s-tag direct flow to a specific queue
4705 * @vsi_seid: VSI SEID to use this tag
4706 * @tag: value of the tag
4707 * @queue_num: queue number, only valid is direct_to_queue is TRUE
4708 * @tags_used: return value, number of tags in use by this PF
4709 * @tags_free: return value, number of unallocated tags
4710 * @cmd_details: pointer to command details structure or NULL
4711 *
4712 * This associates an S- or E-tag to a VSI in the switch complex. It returns
4713 * the number of tags allocated by the PF, and the number of unallocated
4714 * tags available.
4715 **/
i40e_aq_add_tag(struct i40e_hw * hw,bool direct_to_queue,u16 vsi_seid,u16 tag,u16 queue_num,u16 * tags_used,u16 * tags_free,struct i40e_asq_cmd_details * cmd_details)4716 enum i40e_status_code i40e_aq_add_tag(struct i40e_hw *hw, bool direct_to_queue,
4717 u16 vsi_seid, u16 tag, u16 queue_num,
4718 u16 *tags_used, u16 *tags_free,
4719 struct i40e_asq_cmd_details *cmd_details)
4720 {
4721 struct i40e_aq_desc desc;
4722 struct i40e_aqc_add_tag *cmd =
4723 (struct i40e_aqc_add_tag *)&desc.params.raw;
4724 struct i40e_aqc_add_remove_tag_completion *resp =
4725 (struct i40e_aqc_add_remove_tag_completion *)&desc.params.raw;
4726 enum i40e_status_code status;
4727
4728 if (vsi_seid == 0)
4729 return I40E_ERR_PARAM;
4730
4731 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_add_tag);
4732
4733 cmd->seid = CPU_TO_LE16(vsi_seid);
4734 cmd->tag = CPU_TO_LE16(tag);
4735 if (direct_to_queue) {
4736 cmd->flags = CPU_TO_LE16(I40E_AQC_ADD_TAG_FLAG_TO_QUEUE);
4737 cmd->queue_number = CPU_TO_LE16(queue_num);
4738 }
4739
4740 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4741
4742 if (!status) {
4743 if (tags_used != NULL)
4744 *tags_used = LE16_TO_CPU(resp->tags_used);
4745 if (tags_free != NULL)
4746 *tags_free = LE16_TO_CPU(resp->tags_free);
4747 }
4748
4749 return status;
4750 }
4751
4752 /**
4753 * i40e_aq_remove_tag - Remove an S- or E-tag
4754 * @hw: pointer to the hw struct
4755 * @vsi_seid: VSI SEID this tag is associated with
4756 * @tag: value of the S-tag to delete
4757 * @tags_used: return value, number of tags in use by this PF
4758 * @tags_free: return value, number of unallocated tags
4759 * @cmd_details: pointer to command details structure or NULL
4760 *
4761 * This deletes an S- or E-tag from a VSI in the switch complex. It returns
4762 * the number of tags allocated by the PF, and the number of unallocated
4763 * tags available.
4764 **/
i40e_aq_remove_tag(struct i40e_hw * hw,u16 vsi_seid,u16 tag,u16 * tags_used,u16 * tags_free,struct i40e_asq_cmd_details * cmd_details)4765 enum i40e_status_code i40e_aq_remove_tag(struct i40e_hw *hw, u16 vsi_seid,
4766 u16 tag, u16 *tags_used, u16 *tags_free,
4767 struct i40e_asq_cmd_details *cmd_details)
4768 {
4769 struct i40e_aq_desc desc;
4770 struct i40e_aqc_remove_tag *cmd =
4771 (struct i40e_aqc_remove_tag *)&desc.params.raw;
4772 struct i40e_aqc_add_remove_tag_completion *resp =
4773 (struct i40e_aqc_add_remove_tag_completion *)&desc.params.raw;
4774 enum i40e_status_code status;
4775
4776 if (vsi_seid == 0)
4777 return I40E_ERR_PARAM;
4778
4779 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_remove_tag);
4780
4781 cmd->seid = CPU_TO_LE16(vsi_seid);
4782 cmd->tag = CPU_TO_LE16(tag);
4783
4784 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4785
4786 if (!status) {
4787 if (tags_used != NULL)
4788 *tags_used = LE16_TO_CPU(resp->tags_used);
4789 if (tags_free != NULL)
4790 *tags_free = LE16_TO_CPU(resp->tags_free);
4791 }
4792
4793 return status;
4794 }
4795
4796 /**
4797 * i40e_aq_add_mcast_etag - Add a multicast E-tag
4798 * @hw: pointer to the hw struct
4799 * @pv_seid: Port Virtualizer of this SEID to associate E-tag with
4800 * @etag: value of E-tag to add
4801 * @num_tags_in_buf: number of unicast E-tags in indirect buffer
4802 * @buf: address of indirect buffer
4803 * @tags_used: return value, number of E-tags in use by this port
4804 * @tags_free: return value, number of unallocated M-tags
4805 * @cmd_details: pointer to command details structure or NULL
4806 *
4807 * This associates a multicast E-tag to a port virtualizer. It will return
4808 * the number of tags allocated by the PF, and the number of unallocated
4809 * tags available.
4810 *
4811 * The indirect buffer pointed to by buf is a list of 2-byte E-tags,
4812 * num_tags_in_buf long.
4813 **/
i40e_aq_add_mcast_etag(struct i40e_hw * hw,u16 pv_seid,u16 etag,u8 num_tags_in_buf,void * buf,u16 * tags_used,u16 * tags_free,struct i40e_asq_cmd_details * cmd_details)4814 enum i40e_status_code i40e_aq_add_mcast_etag(struct i40e_hw *hw, u16 pv_seid,
4815 u16 etag, u8 num_tags_in_buf, void *buf,
4816 u16 *tags_used, u16 *tags_free,
4817 struct i40e_asq_cmd_details *cmd_details)
4818 {
4819 struct i40e_aq_desc desc;
4820 struct i40e_aqc_add_remove_mcast_etag *cmd =
4821 (struct i40e_aqc_add_remove_mcast_etag *)&desc.params.raw;
4822 struct i40e_aqc_add_remove_mcast_etag_completion *resp =
4823 (struct i40e_aqc_add_remove_mcast_etag_completion *)&desc.params.raw;
4824 enum i40e_status_code status;
4825 u16 length = sizeof(u16) * num_tags_in_buf;
4826
4827 if ((pv_seid == 0) || (buf == NULL) || (num_tags_in_buf == 0))
4828 return I40E_ERR_PARAM;
4829
4830 i40e_fill_default_direct_cmd_desc(&desc,
4831 i40e_aqc_opc_add_multicast_etag);
4832
4833 cmd->pv_seid = CPU_TO_LE16(pv_seid);
4834 cmd->etag = CPU_TO_LE16(etag);
4835 cmd->num_unicast_etags = num_tags_in_buf;
4836
4837 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
4838 if (length > I40E_AQ_LARGE_BUF)
4839 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
4840
4841 status = i40e_asq_send_command(hw, &desc, buf, length, cmd_details);
4842
4843 if (!status) {
4844 if (tags_used != NULL)
4845 *tags_used = LE16_TO_CPU(resp->mcast_etags_used);
4846 if (tags_free != NULL)
4847 *tags_free = LE16_TO_CPU(resp->mcast_etags_free);
4848 }
4849
4850 return status;
4851 }
4852
4853 /**
4854 * i40e_aq_remove_mcast_etag - Remove a multicast E-tag
4855 * @hw: pointer to the hw struct
4856 * @pv_seid: Port Virtualizer SEID this M-tag is associated with
4857 * @etag: value of the E-tag to remove
4858 * @tags_used: return value, number of tags in use by this port
4859 * @tags_free: return value, number of unallocated tags
4860 * @cmd_details: pointer to command details structure or NULL
4861 *
4862 * This deletes an E-tag from the port virtualizer. It will return
4863 * the number of tags allocated by the port, and the number of unallocated
4864 * tags available.
4865 **/
i40e_aq_remove_mcast_etag(struct i40e_hw * hw,u16 pv_seid,u16 etag,u16 * tags_used,u16 * tags_free,struct i40e_asq_cmd_details * cmd_details)4866 enum i40e_status_code i40e_aq_remove_mcast_etag(struct i40e_hw *hw, u16 pv_seid,
4867 u16 etag, u16 *tags_used, u16 *tags_free,
4868 struct i40e_asq_cmd_details *cmd_details)
4869 {
4870 struct i40e_aq_desc desc;
4871 struct i40e_aqc_add_remove_mcast_etag *cmd =
4872 (struct i40e_aqc_add_remove_mcast_etag *)&desc.params.raw;
4873 struct i40e_aqc_add_remove_mcast_etag_completion *resp =
4874 (struct i40e_aqc_add_remove_mcast_etag_completion *)&desc.params.raw;
4875 enum i40e_status_code status;
4876
4877
4878 if (pv_seid == 0)
4879 return I40E_ERR_PARAM;
4880
4881 i40e_fill_default_direct_cmd_desc(&desc,
4882 i40e_aqc_opc_remove_multicast_etag);
4883
4884 cmd->pv_seid = CPU_TO_LE16(pv_seid);
4885 cmd->etag = CPU_TO_LE16(etag);
4886
4887 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4888
4889 if (!status) {
4890 if (tags_used != NULL)
4891 *tags_used = LE16_TO_CPU(resp->mcast_etags_used);
4892 if (tags_free != NULL)
4893 *tags_free = LE16_TO_CPU(resp->mcast_etags_free);
4894 }
4895
4896 return status;
4897 }
4898
4899 /**
4900 * i40e_aq_update_tag - Update an S/E-tag
4901 * @hw: pointer to the hw struct
4902 * @vsi_seid: VSI SEID using this S-tag
4903 * @old_tag: old tag value
4904 * @new_tag: new tag value
4905 * @tags_used: return value, number of tags in use by this PF
4906 * @tags_free: return value, number of unallocated tags
4907 * @cmd_details: pointer to command details structure or NULL
4908 *
4909 * This updates the value of the tag currently attached to this VSI
4910 * in the switch complex. It will return the number of tags allocated
4911 * by the PF, and the number of unallocated tags available.
4912 **/
i40e_aq_update_tag(struct i40e_hw * hw,u16 vsi_seid,u16 old_tag,u16 new_tag,u16 * tags_used,u16 * tags_free,struct i40e_asq_cmd_details * cmd_details)4913 enum i40e_status_code i40e_aq_update_tag(struct i40e_hw *hw, u16 vsi_seid,
4914 u16 old_tag, u16 new_tag, u16 *tags_used,
4915 u16 *tags_free,
4916 struct i40e_asq_cmd_details *cmd_details)
4917 {
4918 struct i40e_aq_desc desc;
4919 struct i40e_aqc_update_tag *cmd =
4920 (struct i40e_aqc_update_tag *)&desc.params.raw;
4921 struct i40e_aqc_update_tag_completion *resp =
4922 (struct i40e_aqc_update_tag_completion *)&desc.params.raw;
4923 enum i40e_status_code status;
4924
4925 if (vsi_seid == 0)
4926 return I40E_ERR_PARAM;
4927
4928 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_update_tag);
4929
4930 cmd->seid = CPU_TO_LE16(vsi_seid);
4931 cmd->old_tag = CPU_TO_LE16(old_tag);
4932 cmd->new_tag = CPU_TO_LE16(new_tag);
4933
4934 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4935
4936 if (!status) {
4937 if (tags_used != NULL)
4938 *tags_used = LE16_TO_CPU(resp->tags_used);
4939 if (tags_free != NULL)
4940 *tags_free = LE16_TO_CPU(resp->tags_free);
4941 }
4942
4943 return status;
4944 }
4945
4946 /**
4947 * i40e_aq_dcb_ignore_pfc - Ignore PFC for given TCs
4948 * @hw: pointer to the hw struct
4949 * @tcmap: TC map for request/release any ignore PFC condition
4950 * @request: request or release ignore PFC condition
4951 * @tcmap_ret: return TCs for which PFC is currently ignored
4952 * @cmd_details: pointer to command details structure or NULL
4953 *
4954 * This sends out request/release to ignore PFC condition for a TC.
4955 * It will return the TCs for which PFC is currently ignored.
4956 **/
i40e_aq_dcb_ignore_pfc(struct i40e_hw * hw,u8 tcmap,bool request,u8 * tcmap_ret,struct i40e_asq_cmd_details * cmd_details)4957 enum i40e_status_code i40e_aq_dcb_ignore_pfc(struct i40e_hw *hw, u8 tcmap,
4958 bool request, u8 *tcmap_ret,
4959 struct i40e_asq_cmd_details *cmd_details)
4960 {
4961 struct i40e_aq_desc desc;
4962 struct i40e_aqc_pfc_ignore *cmd_resp =
4963 (struct i40e_aqc_pfc_ignore *)&desc.params.raw;
4964 enum i40e_status_code status;
4965
4966 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_dcb_ignore_pfc);
4967
4968 if (request)
4969 cmd_resp->command_flags = I40E_AQC_PFC_IGNORE_SET;
4970
4971 cmd_resp->tc_bitmap = tcmap;
4972
4973 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
4974
4975 if (!status) {
4976 if (tcmap_ret != NULL)
4977 *tcmap_ret = cmd_resp->tc_bitmap;
4978 }
4979
4980 return status;
4981 }
4982
4983 /**
4984 * i40e_aq_dcb_updated - DCB Updated Command
4985 * @hw: pointer to the hw struct
4986 * @cmd_details: pointer to command details structure or NULL
4987 *
4988 * When LLDP is handled in PF this command is used by the PF
4989 * to notify EMP that a DCB setting is modified.
4990 * When LLDP is handled in EMP this command is used by the PF
4991 * to notify EMP whenever one of the following parameters get
4992 * modified:
4993 * - PFCLinkDelayAllowance in PRTDCB_GENC.PFCLDA
4994 * - PCIRTT in PRTDCB_GENC.PCIRTT
4995 * - Maximum Frame Size for non-FCoE TCs set by PRTDCB_TDPUC.MAX_TXFRAME.
4996 * EMP will return when the shared RPB settings have been
4997 * recomputed and modified. The retval field in the descriptor
4998 * will be set to 0 when RPB is modified.
4999 **/
i40e_aq_dcb_updated(struct i40e_hw * hw,struct i40e_asq_cmd_details * cmd_details)5000 enum i40e_status_code i40e_aq_dcb_updated(struct i40e_hw *hw,
5001 struct i40e_asq_cmd_details *cmd_details)
5002 {
5003 struct i40e_aq_desc desc;
5004 enum i40e_status_code status;
5005
5006 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_dcb_updated);
5007
5008 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
5009
5010 return status;
5011 }
5012
5013 /**
5014 * i40e_aq_add_statistics - Add a statistics block to a VLAN in a switch.
5015 * @hw: pointer to the hw struct
5016 * @seid: defines the SEID of the switch for which the stats are requested
5017 * @vlan_id: the VLAN ID for which the statistics are requested
5018 * @stat_index: index of the statistics counters block assigned to this VLAN
5019 * @cmd_details: pointer to command details structure or NULL
5020 *
5021 * XL710 supports 128 smonVlanStats counters.This command is used to
5022 * allocate a set of smonVlanStats counters to a specific VLAN in a specific
5023 * switch.
5024 **/
i40e_aq_add_statistics(struct i40e_hw * hw,u16 seid,u16 vlan_id,u16 * stat_index,struct i40e_asq_cmd_details * cmd_details)5025 enum i40e_status_code i40e_aq_add_statistics(struct i40e_hw *hw, u16 seid,
5026 u16 vlan_id, u16 *stat_index,
5027 struct i40e_asq_cmd_details *cmd_details)
5028 {
5029 struct i40e_aq_desc desc;
5030 struct i40e_aqc_add_remove_statistics *cmd_resp =
5031 (struct i40e_aqc_add_remove_statistics *)&desc.params.raw;
5032 enum i40e_status_code status;
5033
5034 if ((seid == 0) || (stat_index == NULL))
5035 return I40E_ERR_PARAM;
5036
5037 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_add_statistics);
5038
5039 cmd_resp->seid = CPU_TO_LE16(seid);
5040 cmd_resp->vlan = CPU_TO_LE16(vlan_id);
5041
5042 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
5043
5044 if (!status && stat_index)
5045 *stat_index = LE16_TO_CPU(cmd_resp->stat_index);
5046
5047 return status;
5048 }
5049
5050 /**
5051 * i40e_aq_remove_statistics - Remove a statistics block to a VLAN in a switch.
5052 * @hw: pointer to the hw struct
5053 * @seid: defines the SEID of the switch for which the stats are requested
5054 * @vlan_id: the VLAN ID for which the statistics are requested
5055 * @stat_index: index of the statistics counters block assigned to this VLAN
5056 * @cmd_details: pointer to command details structure or NULL
5057 *
5058 * XL710 supports 128 smonVlanStats counters.This command is used to
5059 * deallocate a set of smonVlanStats counters to a specific VLAN in a specific
5060 * switch.
5061 **/
i40e_aq_remove_statistics(struct i40e_hw * hw,u16 seid,u16 vlan_id,u16 stat_index,struct i40e_asq_cmd_details * cmd_details)5062 enum i40e_status_code i40e_aq_remove_statistics(struct i40e_hw *hw, u16 seid,
5063 u16 vlan_id, u16 stat_index,
5064 struct i40e_asq_cmd_details *cmd_details)
5065 {
5066 struct i40e_aq_desc desc;
5067 struct i40e_aqc_add_remove_statistics *cmd =
5068 (struct i40e_aqc_add_remove_statistics *)&desc.params.raw;
5069 enum i40e_status_code status;
5070
5071 if (seid == 0)
5072 return I40E_ERR_PARAM;
5073
5074 i40e_fill_default_direct_cmd_desc(&desc,
5075 i40e_aqc_opc_remove_statistics);
5076
5077 cmd->seid = CPU_TO_LE16(seid);
5078 cmd->vlan = CPU_TO_LE16(vlan_id);
5079 cmd->stat_index = CPU_TO_LE16(stat_index);
5080
5081 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
5082
5083 return status;
5084 }
5085
5086 /**
5087 * i40e_aq_set_port_parameters - set physical port parameters.
5088 * @hw: pointer to the hw struct
5089 * @bad_frame_vsi: defines the VSI to which bad frames are forwarded
5090 * @save_bad_pac: if set packets with errors are forwarded to the bad frames VSI
5091 * @pad_short_pac: if set transmit packets smaller than 60 bytes are padded
5092 * @double_vlan: if set double VLAN is enabled
5093 * @cmd_details: pointer to command details structure or NULL
5094 **/
i40e_aq_set_port_parameters(struct i40e_hw * hw,u16 bad_frame_vsi,bool save_bad_pac,bool pad_short_pac,bool double_vlan,struct i40e_asq_cmd_details * cmd_details)5095 enum i40e_status_code i40e_aq_set_port_parameters(struct i40e_hw *hw,
5096 u16 bad_frame_vsi, bool save_bad_pac,
5097 bool pad_short_pac, bool double_vlan,
5098 struct i40e_asq_cmd_details *cmd_details)
5099 {
5100 struct i40e_aqc_set_port_parameters *cmd;
5101 enum i40e_status_code status;
5102 struct i40e_aq_desc desc;
5103 u16 command_flags = 0;
5104
5105 cmd = (struct i40e_aqc_set_port_parameters *)&desc.params.raw;
5106
5107 i40e_fill_default_direct_cmd_desc(&desc,
5108 i40e_aqc_opc_set_port_parameters);
5109
5110 cmd->bad_frame_vsi = CPU_TO_LE16(bad_frame_vsi);
5111 if (save_bad_pac)
5112 command_flags |= I40E_AQ_SET_P_PARAMS_SAVE_BAD_PACKETS;
5113 if (pad_short_pac)
5114 command_flags |= I40E_AQ_SET_P_PARAMS_PAD_SHORT_PACKETS;
5115 if (double_vlan)
5116 command_flags |= I40E_AQ_SET_P_PARAMS_DOUBLE_VLAN_ENA;
5117 cmd->command_flags = CPU_TO_LE16(command_flags);
5118
5119 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
5120
5121 return status;
5122 }
5123
5124 /**
5125 * i40e_aq_tx_sched_cmd - generic Tx scheduler AQ command handler
5126 * @hw: pointer to the hw struct
5127 * @seid: seid for the physical port/switching component/vsi
5128 * @buff: Indirect buffer to hold data parameters and response
5129 * @buff_size: Indirect buffer size
5130 * @opcode: Tx scheduler AQ command opcode
5131 * @cmd_details: pointer to command details structure or NULL
5132 *
5133 * Generic command handler for Tx scheduler AQ commands
5134 **/
i40e_aq_tx_sched_cmd(struct i40e_hw * hw,u16 seid,void * buff,u16 buff_size,enum i40e_admin_queue_opc opcode,struct i40e_asq_cmd_details * cmd_details)5135 static enum i40e_status_code i40e_aq_tx_sched_cmd(struct i40e_hw *hw, u16 seid,
5136 void *buff, u16 buff_size,
5137 enum i40e_admin_queue_opc opcode,
5138 struct i40e_asq_cmd_details *cmd_details)
5139 {
5140 struct i40e_aq_desc desc;
5141 struct i40e_aqc_tx_sched_ind *cmd =
5142 (struct i40e_aqc_tx_sched_ind *)&desc.params.raw;
5143 enum i40e_status_code status;
5144 bool cmd_param_flag = FALSE;
5145
5146 switch (opcode) {
5147 case i40e_aqc_opc_configure_vsi_ets_sla_bw_limit:
5148 case i40e_aqc_opc_configure_vsi_tc_bw:
5149 case i40e_aqc_opc_enable_switching_comp_ets:
5150 case i40e_aqc_opc_modify_switching_comp_ets:
5151 case i40e_aqc_opc_disable_switching_comp_ets:
5152 case i40e_aqc_opc_configure_switching_comp_ets_bw_limit:
5153 case i40e_aqc_opc_configure_switching_comp_bw_config:
5154 cmd_param_flag = TRUE;
5155 break;
5156 case i40e_aqc_opc_query_vsi_bw_config:
5157 case i40e_aqc_opc_query_vsi_ets_sla_config:
5158 case i40e_aqc_opc_query_switching_comp_ets_config:
5159 case i40e_aqc_opc_query_port_ets_config:
5160 case i40e_aqc_opc_query_switching_comp_bw_config:
5161 cmd_param_flag = FALSE;
5162 break;
5163 default:
5164 return I40E_ERR_PARAM;
5165 }
5166
5167 i40e_fill_default_direct_cmd_desc(&desc, opcode);
5168
5169 /* Indirect command */
5170 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
5171 if (cmd_param_flag)
5172 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_RD);
5173 if (buff_size > I40E_AQ_LARGE_BUF)
5174 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
5175
5176 desc.datalen = CPU_TO_LE16(buff_size);
5177
5178 cmd->vsi_seid = CPU_TO_LE16(seid);
5179
5180 status = i40e_asq_send_command(hw, &desc, buff, buff_size, cmd_details);
5181
5182 return status;
5183 }
5184
5185 /**
5186 * i40e_aq_config_vsi_bw_limit - Configure VSI BW Limit
5187 * @hw: pointer to the hw struct
5188 * @seid: VSI seid
5189 * @credit: BW limit credits (0 = disabled)
5190 * @max_credit: Max BW limit credits
5191 * @cmd_details: pointer to command details structure or NULL
5192 **/
i40e_aq_config_vsi_bw_limit(struct i40e_hw * hw,u16 seid,u16 credit,u8 max_credit,struct i40e_asq_cmd_details * cmd_details)5193 enum i40e_status_code i40e_aq_config_vsi_bw_limit(struct i40e_hw *hw,
5194 u16 seid, u16 credit, u8 max_credit,
5195 struct i40e_asq_cmd_details *cmd_details)
5196 {
5197 struct i40e_aq_desc desc;
5198 struct i40e_aqc_configure_vsi_bw_limit *cmd =
5199 (struct i40e_aqc_configure_vsi_bw_limit *)&desc.params.raw;
5200 enum i40e_status_code status;
5201
5202 i40e_fill_default_direct_cmd_desc(&desc,
5203 i40e_aqc_opc_configure_vsi_bw_limit);
5204
5205 cmd->vsi_seid = CPU_TO_LE16(seid);
5206 cmd->credit = CPU_TO_LE16(credit);
5207 cmd->max_credit = max_credit;
5208
5209 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
5210
5211 return status;
5212 }
5213
5214 /**
5215 * i40e_aq_config_switch_comp_bw_limit - Configure Switching component BW Limit
5216 * @hw: pointer to the hw struct
5217 * @seid: switching component seid
5218 * @credit: BW limit credits (0 = disabled)
5219 * @max_bw: Max BW limit credits
5220 * @cmd_details: pointer to command details structure or NULL
5221 **/
i40e_aq_config_switch_comp_bw_limit(struct i40e_hw * hw,u16 seid,u16 credit,u8 max_bw,struct i40e_asq_cmd_details * cmd_details)5222 enum i40e_status_code i40e_aq_config_switch_comp_bw_limit(struct i40e_hw *hw,
5223 u16 seid, u16 credit, u8 max_bw,
5224 struct i40e_asq_cmd_details *cmd_details)
5225 {
5226 struct i40e_aq_desc desc;
5227 struct i40e_aqc_configure_switching_comp_bw_limit *cmd =
5228 (struct i40e_aqc_configure_switching_comp_bw_limit *)&desc.params.raw;
5229 enum i40e_status_code status;
5230
5231 i40e_fill_default_direct_cmd_desc(&desc,
5232 i40e_aqc_opc_configure_switching_comp_bw_limit);
5233
5234 cmd->seid = CPU_TO_LE16(seid);
5235 cmd->credit = CPU_TO_LE16(credit);
5236 cmd->max_bw = max_bw;
5237
5238 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
5239
5240 return status;
5241 }
5242
5243 /**
5244 * i40e_aq_config_vsi_ets_sla_bw_limit - Config VSI BW Limit per TC
5245 * @hw: pointer to the hw struct
5246 * @seid: VSI seid
5247 * @bw_data: Buffer holding enabled TCs, per TC BW limit/credits
5248 * @cmd_details: pointer to command details structure or NULL
5249 **/
i40e_aq_config_vsi_ets_sla_bw_limit(struct i40e_hw * hw,u16 seid,struct i40e_aqc_configure_vsi_ets_sla_bw_data * bw_data,struct i40e_asq_cmd_details * cmd_details)5250 enum i40e_status_code i40e_aq_config_vsi_ets_sla_bw_limit(struct i40e_hw *hw,
5251 u16 seid,
5252 struct i40e_aqc_configure_vsi_ets_sla_bw_data *bw_data,
5253 struct i40e_asq_cmd_details *cmd_details)
5254 {
5255 return i40e_aq_tx_sched_cmd(hw, seid, (void *)bw_data, sizeof(*bw_data),
5256 i40e_aqc_opc_configure_vsi_ets_sla_bw_limit,
5257 cmd_details);
5258 }
5259
5260 /**
5261 * i40e_aq_config_vsi_tc_bw - Config VSI BW Allocation per TC
5262 * @hw: pointer to the hw struct
5263 * @seid: VSI seid
5264 * @bw_data: Buffer holding enabled TCs, relative TC BW limit/credits
5265 * @cmd_details: pointer to command details structure or NULL
5266 **/
i40e_aq_config_vsi_tc_bw(struct i40e_hw * hw,u16 seid,struct i40e_aqc_configure_vsi_tc_bw_data * bw_data,struct i40e_asq_cmd_details * cmd_details)5267 enum i40e_status_code i40e_aq_config_vsi_tc_bw(struct i40e_hw *hw,
5268 u16 seid,
5269 struct i40e_aqc_configure_vsi_tc_bw_data *bw_data,
5270 struct i40e_asq_cmd_details *cmd_details)
5271 {
5272 return i40e_aq_tx_sched_cmd(hw, seid, (void *)bw_data, sizeof(*bw_data),
5273 i40e_aqc_opc_configure_vsi_tc_bw,
5274 cmd_details);
5275 }
5276
5277 /**
5278 * i40e_aq_config_switch_comp_ets_bw_limit - Config Switch comp BW Limit per TC
5279 * @hw: pointer to the hw struct
5280 * @seid: seid of the switching component
5281 * @bw_data: Buffer holding enabled TCs, per TC BW limit/credits
5282 * @cmd_details: pointer to command details structure or NULL
5283 **/
i40e_aq_config_switch_comp_ets_bw_limit(struct i40e_hw * hw,u16 seid,struct i40e_aqc_configure_switching_comp_ets_bw_limit_data * bw_data,struct i40e_asq_cmd_details * cmd_details)5284 enum i40e_status_code i40e_aq_config_switch_comp_ets_bw_limit(
5285 struct i40e_hw *hw, u16 seid,
5286 struct i40e_aqc_configure_switching_comp_ets_bw_limit_data *bw_data,
5287 struct i40e_asq_cmd_details *cmd_details)
5288 {
5289 return i40e_aq_tx_sched_cmd(hw, seid, (void *)bw_data, sizeof(*bw_data),
5290 i40e_aqc_opc_configure_switching_comp_ets_bw_limit,
5291 cmd_details);
5292 }
5293
5294 /**
5295 * i40e_aq_query_vsi_bw_config - Query VSI BW configuration
5296 * @hw: pointer to the hw struct
5297 * @seid: seid of the VSI
5298 * @bw_data: Buffer to hold VSI BW configuration
5299 * @cmd_details: pointer to command details structure or NULL
5300 **/
i40e_aq_query_vsi_bw_config(struct i40e_hw * hw,u16 seid,struct i40e_aqc_query_vsi_bw_config_resp * bw_data,struct i40e_asq_cmd_details * cmd_details)5301 enum i40e_status_code i40e_aq_query_vsi_bw_config(struct i40e_hw *hw,
5302 u16 seid,
5303 struct i40e_aqc_query_vsi_bw_config_resp *bw_data,
5304 struct i40e_asq_cmd_details *cmd_details)
5305 {
5306 return i40e_aq_tx_sched_cmd(hw, seid, (void *)bw_data, sizeof(*bw_data),
5307 i40e_aqc_opc_query_vsi_bw_config,
5308 cmd_details);
5309 }
5310
5311 /**
5312 * i40e_aq_query_vsi_ets_sla_config - Query VSI BW configuration per TC
5313 * @hw: pointer to the hw struct
5314 * @seid: seid of the VSI
5315 * @bw_data: Buffer to hold VSI BW configuration per TC
5316 * @cmd_details: pointer to command details structure or NULL
5317 **/
i40e_aq_query_vsi_ets_sla_config(struct i40e_hw * hw,u16 seid,struct i40e_aqc_query_vsi_ets_sla_config_resp * bw_data,struct i40e_asq_cmd_details * cmd_details)5318 enum i40e_status_code i40e_aq_query_vsi_ets_sla_config(struct i40e_hw *hw,
5319 u16 seid,
5320 struct i40e_aqc_query_vsi_ets_sla_config_resp *bw_data,
5321 struct i40e_asq_cmd_details *cmd_details)
5322 {
5323 return i40e_aq_tx_sched_cmd(hw, seid, (void *)bw_data, sizeof(*bw_data),
5324 i40e_aqc_opc_query_vsi_ets_sla_config,
5325 cmd_details);
5326 }
5327
5328 /**
5329 * i40e_aq_query_switch_comp_ets_config - Query Switch comp BW config per TC
5330 * @hw: pointer to the hw struct
5331 * @seid: seid of the switching component
5332 * @bw_data: Buffer to hold switching component's per TC BW config
5333 * @cmd_details: pointer to command details structure or NULL
5334 **/
i40e_aq_query_switch_comp_ets_config(struct i40e_hw * hw,u16 seid,struct i40e_aqc_query_switching_comp_ets_config_resp * bw_data,struct i40e_asq_cmd_details * cmd_details)5335 enum i40e_status_code i40e_aq_query_switch_comp_ets_config(struct i40e_hw *hw,
5336 u16 seid,
5337 struct i40e_aqc_query_switching_comp_ets_config_resp *bw_data,
5338 struct i40e_asq_cmd_details *cmd_details)
5339 {
5340 return i40e_aq_tx_sched_cmd(hw, seid, (void *)bw_data, sizeof(*bw_data),
5341 i40e_aqc_opc_query_switching_comp_ets_config,
5342 cmd_details);
5343 }
5344
5345 /**
5346 * i40e_aq_query_port_ets_config - Query Physical Port ETS configuration
5347 * @hw: pointer to the hw struct
5348 * @seid: seid of the VSI or switching component connected to Physical Port
5349 * @bw_data: Buffer to hold current ETS configuration for the Physical Port
5350 * @cmd_details: pointer to command details structure or NULL
5351 **/
i40e_aq_query_port_ets_config(struct i40e_hw * hw,u16 seid,struct i40e_aqc_query_port_ets_config_resp * bw_data,struct i40e_asq_cmd_details * cmd_details)5352 enum i40e_status_code i40e_aq_query_port_ets_config(struct i40e_hw *hw,
5353 u16 seid,
5354 struct i40e_aqc_query_port_ets_config_resp *bw_data,
5355 struct i40e_asq_cmd_details *cmd_details)
5356 {
5357 return i40e_aq_tx_sched_cmd(hw, seid, (void *)bw_data, sizeof(*bw_data),
5358 i40e_aqc_opc_query_port_ets_config,
5359 cmd_details);
5360 }
5361
5362 /**
5363 * i40e_aq_query_switch_comp_bw_config - Query Switch comp BW configuration
5364 * @hw: pointer to the hw struct
5365 * @seid: seid of the switching component
5366 * @bw_data: Buffer to hold switching component's BW configuration
5367 * @cmd_details: pointer to command details structure or NULL
5368 **/
i40e_aq_query_switch_comp_bw_config(struct i40e_hw * hw,u16 seid,struct i40e_aqc_query_switching_comp_bw_config_resp * bw_data,struct i40e_asq_cmd_details * cmd_details)5369 enum i40e_status_code i40e_aq_query_switch_comp_bw_config(struct i40e_hw *hw,
5370 u16 seid,
5371 struct i40e_aqc_query_switching_comp_bw_config_resp *bw_data,
5372 struct i40e_asq_cmd_details *cmd_details)
5373 {
5374 return i40e_aq_tx_sched_cmd(hw, seid, (void *)bw_data, sizeof(*bw_data),
5375 i40e_aqc_opc_query_switching_comp_bw_config,
5376 cmd_details);
5377 }
5378
5379 /**
5380 * i40e_validate_filter_settings
5381 * @hw: pointer to the hardware structure
5382 * @settings: Filter control settings
5383 *
5384 * Check and validate the filter control settings passed.
5385 * The function checks for the valid filter/context sizes being
5386 * passed for FCoE and PE.
5387 *
5388 * Returns I40E_SUCCESS if the values passed are valid and within
5389 * range else returns an error.
5390 **/
i40e_validate_filter_settings(struct i40e_hw * hw,struct i40e_filter_control_settings * settings)5391 static enum i40e_status_code i40e_validate_filter_settings(struct i40e_hw *hw,
5392 struct i40e_filter_control_settings *settings)
5393 {
5394 u32 fcoe_cntx_size, fcoe_filt_size;
5395 u32 pe_cntx_size, pe_filt_size;
5396 u32 fcoe_fmax;
5397
5398 u32 val;
5399
5400 /* Validate FCoE settings passed */
5401 switch (settings->fcoe_filt_num) {
5402 case I40E_HASH_FILTER_SIZE_1K:
5403 case I40E_HASH_FILTER_SIZE_2K:
5404 case I40E_HASH_FILTER_SIZE_4K:
5405 case I40E_HASH_FILTER_SIZE_8K:
5406 case I40E_HASH_FILTER_SIZE_16K:
5407 case I40E_HASH_FILTER_SIZE_32K:
5408 fcoe_filt_size = I40E_HASH_FILTER_BASE_SIZE;
5409 fcoe_filt_size <<= (u32)settings->fcoe_filt_num;
5410 break;
5411 default:
5412 return I40E_ERR_PARAM;
5413 }
5414
5415 switch (settings->fcoe_cntx_num) {
5416 case I40E_DMA_CNTX_SIZE_512:
5417 case I40E_DMA_CNTX_SIZE_1K:
5418 case I40E_DMA_CNTX_SIZE_2K:
5419 case I40E_DMA_CNTX_SIZE_4K:
5420 fcoe_cntx_size = I40E_DMA_CNTX_BASE_SIZE;
5421 fcoe_cntx_size <<= (u32)settings->fcoe_cntx_num;
5422 break;
5423 default:
5424 return I40E_ERR_PARAM;
5425 }
5426
5427 /* Validate PE settings passed */
5428 switch (settings->pe_filt_num) {
5429 case I40E_HASH_FILTER_SIZE_1K:
5430 case I40E_HASH_FILTER_SIZE_2K:
5431 case I40E_HASH_FILTER_SIZE_4K:
5432 case I40E_HASH_FILTER_SIZE_8K:
5433 case I40E_HASH_FILTER_SIZE_16K:
5434 case I40E_HASH_FILTER_SIZE_32K:
5435 case I40E_HASH_FILTER_SIZE_64K:
5436 case I40E_HASH_FILTER_SIZE_128K:
5437 case I40E_HASH_FILTER_SIZE_256K:
5438 case I40E_HASH_FILTER_SIZE_512K:
5439 case I40E_HASH_FILTER_SIZE_1M:
5440 pe_filt_size = I40E_HASH_FILTER_BASE_SIZE;
5441 pe_filt_size <<= (u32)settings->pe_filt_num;
5442 break;
5443 default:
5444 return I40E_ERR_PARAM;
5445 }
5446
5447 switch (settings->pe_cntx_num) {
5448 case I40E_DMA_CNTX_SIZE_512:
5449 case I40E_DMA_CNTX_SIZE_1K:
5450 case I40E_DMA_CNTX_SIZE_2K:
5451 case I40E_DMA_CNTX_SIZE_4K:
5452 case I40E_DMA_CNTX_SIZE_8K:
5453 case I40E_DMA_CNTX_SIZE_16K:
5454 case I40E_DMA_CNTX_SIZE_32K:
5455 case I40E_DMA_CNTX_SIZE_64K:
5456 case I40E_DMA_CNTX_SIZE_128K:
5457 case I40E_DMA_CNTX_SIZE_256K:
5458 pe_cntx_size = I40E_DMA_CNTX_BASE_SIZE;
5459 pe_cntx_size <<= (u32)settings->pe_cntx_num;
5460 break;
5461 default:
5462 return I40E_ERR_PARAM;
5463 }
5464
5465 /* FCHSIZE + FCDSIZE should not be greater than PMFCOEFMAX */
5466 val = rd32(hw, I40E_GLHMC_FCOEFMAX);
5467 fcoe_fmax = (val & I40E_GLHMC_FCOEFMAX_PMFCOEFMAX_MASK)
5468 >> I40E_GLHMC_FCOEFMAX_PMFCOEFMAX_SHIFT;
5469 if (fcoe_filt_size + fcoe_cntx_size > fcoe_fmax)
5470 return I40E_ERR_INVALID_SIZE;
5471
5472 return I40E_SUCCESS;
5473 }
5474
5475 /**
5476 * i40e_set_filter_control
5477 * @hw: pointer to the hardware structure
5478 * @settings: Filter control settings
5479 *
5480 * Set the Queue Filters for PE/FCoE and enable filters required
5481 * for a single PF. It is expected that these settings are programmed
5482 * at the driver initialization time.
5483 **/
i40e_set_filter_control(struct i40e_hw * hw,struct i40e_filter_control_settings * settings)5484 enum i40e_status_code i40e_set_filter_control(struct i40e_hw *hw,
5485 struct i40e_filter_control_settings *settings)
5486 {
5487 enum i40e_status_code ret = I40E_SUCCESS;
5488 u32 hash_lut_size = 0;
5489 u32 val;
5490
5491 if (!settings)
5492 return I40E_ERR_PARAM;
5493
5494 /* Validate the input settings */
5495 ret = i40e_validate_filter_settings(hw, settings);
5496 if (ret)
5497 return ret;
5498
5499 /* Read the PF Queue Filter control register */
5500 val = i40e_read_rx_ctl(hw, I40E_PFQF_CTL_0);
5501
5502 /* Program required PE hash buckets for the PF */
5503 val &= ~I40E_PFQF_CTL_0_PEHSIZE_MASK;
5504 val |= ((u32)settings->pe_filt_num << I40E_PFQF_CTL_0_PEHSIZE_SHIFT) &
5505 I40E_PFQF_CTL_0_PEHSIZE_MASK;
5506 /* Program required PE contexts for the PF */
5507 val &= ~I40E_PFQF_CTL_0_PEDSIZE_MASK;
5508 val |= ((u32)settings->pe_cntx_num << I40E_PFQF_CTL_0_PEDSIZE_SHIFT) &
5509 I40E_PFQF_CTL_0_PEDSIZE_MASK;
5510
5511 /* Program required FCoE hash buckets for the PF */
5512 val &= ~I40E_PFQF_CTL_0_PFFCHSIZE_MASK;
5513 val |= ((u32)settings->fcoe_filt_num <<
5514 I40E_PFQF_CTL_0_PFFCHSIZE_SHIFT) &
5515 I40E_PFQF_CTL_0_PFFCHSIZE_MASK;
5516 /* Program required FCoE DDP contexts for the PF */
5517 val &= ~I40E_PFQF_CTL_0_PFFCDSIZE_MASK;
5518 val |= ((u32)settings->fcoe_cntx_num <<
5519 I40E_PFQF_CTL_0_PFFCDSIZE_SHIFT) &
5520 I40E_PFQF_CTL_0_PFFCDSIZE_MASK;
5521
5522 /* Program Hash LUT size for the PF */
5523 val &= ~I40E_PFQF_CTL_0_HASHLUTSIZE_MASK;
5524 if (settings->hash_lut_size == I40E_HASH_LUT_SIZE_512)
5525 hash_lut_size = 1;
5526 val |= (hash_lut_size << I40E_PFQF_CTL_0_HASHLUTSIZE_SHIFT) &
5527 I40E_PFQF_CTL_0_HASHLUTSIZE_MASK;
5528
5529 /* Enable FDIR, Ethertype and MACVLAN filters for PF and VFs */
5530 if (settings->enable_fdir)
5531 val |= I40E_PFQF_CTL_0_FD_ENA_MASK;
5532 if (settings->enable_ethtype)
5533 val |= I40E_PFQF_CTL_0_ETYPE_ENA_MASK;
5534 if (settings->enable_macvlan)
5535 val |= I40E_PFQF_CTL_0_MACVLAN_ENA_MASK;
5536
5537 i40e_write_rx_ctl(hw, I40E_PFQF_CTL_0, val);
5538
5539 return I40E_SUCCESS;
5540 }
5541
5542 /**
5543 * i40e_aq_add_rem_control_packet_filter - Add or Remove Control Packet Filter
5544 * @hw: pointer to the hw struct
5545 * @mac_addr: MAC address to use in the filter
5546 * @ethtype: Ethertype to use in the filter
5547 * @flags: Flags that needs to be applied to the filter
5548 * @vsi_seid: seid of the control VSI
5549 * @queue: VSI queue number to send the packet to
5550 * @is_add: Add control packet filter if True else remove
5551 * @stats: Structure to hold information on control filter counts
5552 * @cmd_details: pointer to command details structure or NULL
5553 *
5554 * This command will Add or Remove control packet filter for a control VSI.
5555 * In return it will update the total number of perfect filter count in
5556 * the stats member.
5557 **/
i40e_aq_add_rem_control_packet_filter(struct i40e_hw * hw,u8 * mac_addr,u16 ethtype,u16 flags,u16 vsi_seid,u16 queue,bool is_add,struct i40e_control_filter_stats * stats,struct i40e_asq_cmd_details * cmd_details)5558 enum i40e_status_code i40e_aq_add_rem_control_packet_filter(struct i40e_hw *hw,
5559 u8 *mac_addr, u16 ethtype, u16 flags,
5560 u16 vsi_seid, u16 queue, bool is_add,
5561 struct i40e_control_filter_stats *stats,
5562 struct i40e_asq_cmd_details *cmd_details)
5563 {
5564 struct i40e_aq_desc desc;
5565 struct i40e_aqc_add_remove_control_packet_filter *cmd =
5566 (struct i40e_aqc_add_remove_control_packet_filter *)
5567 &desc.params.raw;
5568 struct i40e_aqc_add_remove_control_packet_filter_completion *resp =
5569 (struct i40e_aqc_add_remove_control_packet_filter_completion *)
5570 &desc.params.raw;
5571 enum i40e_status_code status;
5572
5573 if (vsi_seid == 0)
5574 return I40E_ERR_PARAM;
5575
5576 if (is_add) {
5577 i40e_fill_default_direct_cmd_desc(&desc,
5578 i40e_aqc_opc_add_control_packet_filter);
5579 cmd->queue = CPU_TO_LE16(queue);
5580 } else {
5581 i40e_fill_default_direct_cmd_desc(&desc,
5582 i40e_aqc_opc_remove_control_packet_filter);
5583 }
5584
5585 if (mac_addr)
5586 i40e_memcpy(cmd->mac, mac_addr, ETH_ALEN,
5587 I40E_NONDMA_TO_NONDMA);
5588
5589 cmd->etype = CPU_TO_LE16(ethtype);
5590 cmd->flags = CPU_TO_LE16(flags);
5591 cmd->seid = CPU_TO_LE16(vsi_seid);
5592
5593 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
5594
5595 if (!status && stats) {
5596 stats->mac_etype_used = LE16_TO_CPU(resp->mac_etype_used);
5597 stats->etype_used = LE16_TO_CPU(resp->etype_used);
5598 stats->mac_etype_free = LE16_TO_CPU(resp->mac_etype_free);
5599 stats->etype_free = LE16_TO_CPU(resp->etype_free);
5600 }
5601
5602 return status;
5603 }
5604
5605 /**
5606 * i40e_add_filter_to_drop_tx_flow_control_frames- filter to drop flow control
5607 * @hw: pointer to the hw struct
5608 * @seid: VSI seid to add ethertype filter from
5609 **/
i40e_add_filter_to_drop_tx_flow_control_frames(struct i40e_hw * hw,u16 seid)5610 void i40e_add_filter_to_drop_tx_flow_control_frames(struct i40e_hw *hw,
5611 u16 seid)
5612 {
5613 #define I40E_FLOW_CONTROL_ETHTYPE 0x8808
5614 u16 flag = I40E_AQC_ADD_CONTROL_PACKET_FLAGS_IGNORE_MAC |
5615 I40E_AQC_ADD_CONTROL_PACKET_FLAGS_DROP |
5616 I40E_AQC_ADD_CONTROL_PACKET_FLAGS_TX;
5617 u16 ethtype = I40E_FLOW_CONTROL_ETHTYPE;
5618 enum i40e_status_code status;
5619
5620 status = i40e_aq_add_rem_control_packet_filter(hw, NULL, ethtype, flag,
5621 seid, 0, TRUE, NULL,
5622 NULL);
5623 if (status)
5624 DEBUGOUT("Ethtype Filter Add failed: Error pruning Tx flow control frames\n");
5625 }
5626
5627 /**
5628 * i40e_fix_up_geneve_vni - adjust Geneve VNI for HW issue
5629 * @filters: list of cloud filters
5630 * @filter_count: length of list
5631 *
5632 * There's an issue in the device where the Geneve VNI layout needs
5633 * to be shifted 1 byte over from the VxLAN VNI
5634 **/
i40e_fix_up_geneve_vni(struct i40e_aqc_add_remove_cloud_filters_element_data * filters,u8 filter_count)5635 static void i40e_fix_up_geneve_vni(
5636 struct i40e_aqc_add_remove_cloud_filters_element_data *filters,
5637 u8 filter_count)
5638 {
5639 struct i40e_aqc_add_remove_cloud_filters_element_data *f = filters;
5640 int i;
5641
5642 for (i = 0; i < filter_count; i++) {
5643 u16 tnl_type;
5644 u32 ti;
5645
5646 tnl_type = (LE16_TO_CPU(f[i].flags) &
5647 I40E_AQC_ADD_CLOUD_TNL_TYPE_MASK) >>
5648 I40E_AQC_ADD_CLOUD_TNL_TYPE_SHIFT;
5649 if (tnl_type == I40E_AQC_ADD_CLOUD_TNL_TYPE_GENEVE) {
5650 ti = LE32_TO_CPU(f[i].tenant_id);
5651 f[i].tenant_id = CPU_TO_LE32(ti << 8);
5652 }
5653 }
5654 }
5655
5656 /**
5657 * i40e_aq_add_cloud_filters
5658 * @hw: pointer to the hardware structure
5659 * @seid: VSI seid to add cloud filters from
5660 * @filters: Buffer which contains the filters to be added
5661 * @filter_count: number of filters contained in the buffer
5662 *
5663 * Set the cloud filters for a given VSI. The contents of the
5664 * i40e_aqc_add_remove_cloud_filters_element_data are filled
5665 * in by the caller of the function.
5666 *
5667 **/
i40e_aq_add_cloud_filters(struct i40e_hw * hw,u16 seid,struct i40e_aqc_add_remove_cloud_filters_element_data * filters,u8 filter_count)5668 enum i40e_status_code i40e_aq_add_cloud_filters(struct i40e_hw *hw,
5669 u16 seid,
5670 struct i40e_aqc_add_remove_cloud_filters_element_data *filters,
5671 u8 filter_count)
5672 {
5673 struct i40e_aq_desc desc;
5674 struct i40e_aqc_add_remove_cloud_filters *cmd =
5675 (struct i40e_aqc_add_remove_cloud_filters *)&desc.params.raw;
5676 enum i40e_status_code status;
5677 u16 buff_len;
5678
5679 i40e_fill_default_direct_cmd_desc(&desc,
5680 i40e_aqc_opc_add_cloud_filters);
5681
5682 buff_len = filter_count * sizeof(*filters);
5683 desc.datalen = CPU_TO_LE16(buff_len);
5684 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
5685 cmd->num_filters = filter_count;
5686 cmd->seid = CPU_TO_LE16(seid);
5687
5688 i40e_fix_up_geneve_vni(filters, filter_count);
5689
5690 status = i40e_asq_send_command(hw, &desc, filters, buff_len, NULL);
5691
5692 return status;
5693 }
5694
5695 /**
5696 * i40e_aq_remove_cloud_filters
5697 * @hw: pointer to the hardware structure
5698 * @seid: VSI seid to remove cloud filters from
5699 * @filters: Buffer which contains the filters to be removed
5700 * @filter_count: number of filters contained in the buffer
5701 *
5702 * Remove the cloud filters for a given VSI. The contents of the
5703 * i40e_aqc_add_remove_cloud_filters_element_data are filled
5704 * in by the caller of the function.
5705 *
5706 **/
i40e_aq_remove_cloud_filters(struct i40e_hw * hw,u16 seid,struct i40e_aqc_add_remove_cloud_filters_element_data * filters,u8 filter_count)5707 enum i40e_status_code i40e_aq_remove_cloud_filters(struct i40e_hw *hw,
5708 u16 seid,
5709 struct i40e_aqc_add_remove_cloud_filters_element_data *filters,
5710 u8 filter_count)
5711 {
5712 struct i40e_aq_desc desc;
5713 struct i40e_aqc_add_remove_cloud_filters *cmd =
5714 (struct i40e_aqc_add_remove_cloud_filters *)&desc.params.raw;
5715 enum i40e_status_code status;
5716 u16 buff_len;
5717
5718 i40e_fill_default_direct_cmd_desc(&desc,
5719 i40e_aqc_opc_remove_cloud_filters);
5720
5721 buff_len = filter_count * sizeof(*filters);
5722 desc.datalen = CPU_TO_LE16(buff_len);
5723 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF | I40E_AQ_FLAG_RD));
5724 cmd->num_filters = filter_count;
5725 cmd->seid = CPU_TO_LE16(seid);
5726
5727 i40e_fix_up_geneve_vni(filters, filter_count);
5728
5729 status = i40e_asq_send_command(hw, &desc, filters, buff_len, NULL);
5730
5731 return status;
5732 }
5733
5734 /**
5735 * i40e_aq_alternate_write
5736 * @hw: pointer to the hardware structure
5737 * @reg_addr0: address of first dword to be read
5738 * @reg_val0: value to be written under 'reg_addr0'
5739 * @reg_addr1: address of second dword to be read
5740 * @reg_val1: value to be written under 'reg_addr1'
5741 *
5742 * Write one or two dwords to alternate structure. Fields are indicated
5743 * by 'reg_addr0' and 'reg_addr1' register numbers.
5744 *
5745 **/
i40e_aq_alternate_write(struct i40e_hw * hw,u32 reg_addr0,u32 reg_val0,u32 reg_addr1,u32 reg_val1)5746 enum i40e_status_code i40e_aq_alternate_write(struct i40e_hw *hw,
5747 u32 reg_addr0, u32 reg_val0,
5748 u32 reg_addr1, u32 reg_val1)
5749 {
5750 struct i40e_aq_desc desc;
5751 struct i40e_aqc_alternate_write *cmd_resp =
5752 (struct i40e_aqc_alternate_write *)&desc.params.raw;
5753 enum i40e_status_code status;
5754
5755 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_alternate_write);
5756 cmd_resp->address0 = CPU_TO_LE32(reg_addr0);
5757 cmd_resp->address1 = CPU_TO_LE32(reg_addr1);
5758 cmd_resp->data0 = CPU_TO_LE32(reg_val0);
5759 cmd_resp->data1 = CPU_TO_LE32(reg_val1);
5760
5761 status = i40e_asq_send_command(hw, &desc, NULL, 0, NULL);
5762
5763 return status;
5764 }
5765
5766 /**
5767 * i40e_aq_alternate_write_indirect
5768 * @hw: pointer to the hardware structure
5769 * @addr: address of a first register to be modified
5770 * @dw_count: number of alternate structure fields to write
5771 * @buffer: pointer to the command buffer
5772 *
5773 * Write 'dw_count' dwords from 'buffer' to alternate structure
5774 * starting at 'addr'.
5775 *
5776 **/
i40e_aq_alternate_write_indirect(struct i40e_hw * hw,u32 addr,u32 dw_count,void * buffer)5777 enum i40e_status_code i40e_aq_alternate_write_indirect(struct i40e_hw *hw,
5778 u32 addr, u32 dw_count, void *buffer)
5779 {
5780 struct i40e_aq_desc desc;
5781 struct i40e_aqc_alternate_ind_write *cmd_resp =
5782 (struct i40e_aqc_alternate_ind_write *)&desc.params.raw;
5783 enum i40e_status_code status;
5784
5785 if (buffer == NULL)
5786 return I40E_ERR_PARAM;
5787
5788 /* Indirect command */
5789 i40e_fill_default_direct_cmd_desc(&desc,
5790 i40e_aqc_opc_alternate_write_indirect);
5791
5792 desc.flags |= CPU_TO_LE16(I40E_AQ_FLAG_RD);
5793 desc.flags |= CPU_TO_LE16(I40E_AQ_FLAG_BUF);
5794 if (dw_count > (I40E_AQ_LARGE_BUF/4))
5795 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
5796
5797 cmd_resp->address = CPU_TO_LE32(addr);
5798 cmd_resp->length = CPU_TO_LE32(dw_count);
5799
5800 status = i40e_asq_send_command(hw, &desc, buffer,
5801 I40E_LO_DWORD(4*dw_count), NULL);
5802
5803 return status;
5804 }
5805
5806 /**
5807 * i40e_aq_alternate_read
5808 * @hw: pointer to the hardware structure
5809 * @reg_addr0: address of first dword to be read
5810 * @reg_val0: pointer for data read from 'reg_addr0'
5811 * @reg_addr1: address of second dword to be read
5812 * @reg_val1: pointer for data read from 'reg_addr1'
5813 *
5814 * Read one or two dwords from alternate structure. Fields are indicated
5815 * by 'reg_addr0' and 'reg_addr1' register numbers. If 'reg_val1' pointer
5816 * is not passed then only register at 'reg_addr0' is read.
5817 *
5818 **/
i40e_aq_alternate_read(struct i40e_hw * hw,u32 reg_addr0,u32 * reg_val0,u32 reg_addr1,u32 * reg_val1)5819 enum i40e_status_code i40e_aq_alternate_read(struct i40e_hw *hw,
5820 u32 reg_addr0, u32 *reg_val0,
5821 u32 reg_addr1, u32 *reg_val1)
5822 {
5823 struct i40e_aq_desc desc;
5824 struct i40e_aqc_alternate_write *cmd_resp =
5825 (struct i40e_aqc_alternate_write *)&desc.params.raw;
5826 enum i40e_status_code status;
5827
5828 if (reg_val0 == NULL)
5829 return I40E_ERR_PARAM;
5830
5831 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_alternate_read);
5832 cmd_resp->address0 = CPU_TO_LE32(reg_addr0);
5833 cmd_resp->address1 = CPU_TO_LE32(reg_addr1);
5834
5835 status = i40e_asq_send_command(hw, &desc, NULL, 0, NULL);
5836
5837 if (status == I40E_SUCCESS) {
5838 *reg_val0 = LE32_TO_CPU(cmd_resp->data0);
5839
5840 if (reg_val1 != NULL)
5841 *reg_val1 = LE32_TO_CPU(cmd_resp->data1);
5842 }
5843
5844 return status;
5845 }
5846
5847 /**
5848 * i40e_aq_alternate_read_indirect
5849 * @hw: pointer to the hardware structure
5850 * @addr: address of the alternate structure field
5851 * @dw_count: number of alternate structure fields to read
5852 * @buffer: pointer to the command buffer
5853 *
5854 * Read 'dw_count' dwords from alternate structure starting at 'addr' and
5855 * place them in 'buffer'. The buffer should be allocated by caller.
5856 *
5857 **/
i40e_aq_alternate_read_indirect(struct i40e_hw * hw,u32 addr,u32 dw_count,void * buffer)5858 enum i40e_status_code i40e_aq_alternate_read_indirect(struct i40e_hw *hw,
5859 u32 addr, u32 dw_count, void *buffer)
5860 {
5861 struct i40e_aq_desc desc;
5862 struct i40e_aqc_alternate_ind_write *cmd_resp =
5863 (struct i40e_aqc_alternate_ind_write *)&desc.params.raw;
5864 enum i40e_status_code status;
5865
5866 if (buffer == NULL)
5867 return I40E_ERR_PARAM;
5868
5869 /* Indirect command */
5870 i40e_fill_default_direct_cmd_desc(&desc,
5871 i40e_aqc_opc_alternate_read_indirect);
5872
5873 desc.flags |= CPU_TO_LE16(I40E_AQ_FLAG_RD);
5874 desc.flags |= CPU_TO_LE16(I40E_AQ_FLAG_BUF);
5875 if (dw_count > (I40E_AQ_LARGE_BUF/4))
5876 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
5877
5878 cmd_resp->address = CPU_TO_LE32(addr);
5879 cmd_resp->length = CPU_TO_LE32(dw_count);
5880
5881 status = i40e_asq_send_command(hw, &desc, buffer,
5882 I40E_LO_DWORD(4*dw_count), NULL);
5883
5884 return status;
5885 }
5886
5887 /**
5888 * i40e_aq_alternate_clear
5889 * @hw: pointer to the HW structure.
5890 *
5891 * Clear the alternate structures of the port from which the function
5892 * is called.
5893 *
5894 **/
i40e_aq_alternate_clear(struct i40e_hw * hw)5895 enum i40e_status_code i40e_aq_alternate_clear(struct i40e_hw *hw)
5896 {
5897 struct i40e_aq_desc desc;
5898 enum i40e_status_code status;
5899
5900 i40e_fill_default_direct_cmd_desc(&desc,
5901 i40e_aqc_opc_alternate_clear_port);
5902
5903 status = i40e_asq_send_command(hw, &desc, NULL, 0, NULL);
5904
5905 return status;
5906 }
5907
5908 /**
5909 * i40e_aq_alternate_write_done
5910 * @hw: pointer to the HW structure.
5911 * @bios_mode: indicates whether the command is executed by UEFI or legacy BIOS
5912 * @reset_needed: indicates the SW should trigger GLOBAL reset
5913 *
5914 * Indicates to the FW that alternate structures have been changed.
5915 *
5916 **/
i40e_aq_alternate_write_done(struct i40e_hw * hw,u8 bios_mode,bool * reset_needed)5917 enum i40e_status_code i40e_aq_alternate_write_done(struct i40e_hw *hw,
5918 u8 bios_mode, bool *reset_needed)
5919 {
5920 struct i40e_aq_desc desc;
5921 struct i40e_aqc_alternate_write_done *cmd =
5922 (struct i40e_aqc_alternate_write_done *)&desc.params.raw;
5923 enum i40e_status_code status;
5924
5925 if (reset_needed == NULL)
5926 return I40E_ERR_PARAM;
5927
5928 i40e_fill_default_direct_cmd_desc(&desc,
5929 i40e_aqc_opc_alternate_write_done);
5930
5931 cmd->cmd_flags = CPU_TO_LE16(bios_mode);
5932
5933 status = i40e_asq_send_command(hw, &desc, NULL, 0, NULL);
5934 if (!status && reset_needed)
5935 *reset_needed = ((LE16_TO_CPU(cmd->cmd_flags) &
5936 I40E_AQ_ALTERNATE_RESET_NEEDED) != 0);
5937
5938 return status;
5939 }
5940
5941 /**
5942 * i40e_aq_set_oem_mode
5943 * @hw: pointer to the HW structure.
5944 * @oem_mode: the OEM mode to be used
5945 *
5946 * Sets the device to a specific operating mode. Currently the only supported
5947 * mode is no_clp, which causes FW to refrain from using Alternate RAM.
5948 *
5949 **/
i40e_aq_set_oem_mode(struct i40e_hw * hw,u8 oem_mode)5950 enum i40e_status_code i40e_aq_set_oem_mode(struct i40e_hw *hw,
5951 u8 oem_mode)
5952 {
5953 struct i40e_aq_desc desc;
5954 struct i40e_aqc_alternate_write_done *cmd =
5955 (struct i40e_aqc_alternate_write_done *)&desc.params.raw;
5956 enum i40e_status_code status;
5957
5958 i40e_fill_default_direct_cmd_desc(&desc,
5959 i40e_aqc_opc_alternate_set_mode);
5960
5961 cmd->cmd_flags = CPU_TO_LE16(oem_mode);
5962
5963 status = i40e_asq_send_command(hw, &desc, NULL, 0, NULL);
5964
5965 return status;
5966 }
5967
5968 /**
5969 * i40e_aq_resume_port_tx
5970 * @hw: pointer to the hardware structure
5971 * @cmd_details: pointer to command details structure or NULL
5972 *
5973 * Resume port's Tx traffic
5974 **/
i40e_aq_resume_port_tx(struct i40e_hw * hw,struct i40e_asq_cmd_details * cmd_details)5975 enum i40e_status_code i40e_aq_resume_port_tx(struct i40e_hw *hw,
5976 struct i40e_asq_cmd_details *cmd_details)
5977 {
5978 struct i40e_aq_desc desc;
5979 enum i40e_status_code status;
5980
5981 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_resume_port_tx);
5982
5983 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
5984
5985 return status;
5986 }
5987
5988 /**
5989 * i40e_set_pci_config_data - store PCI bus info
5990 * @hw: pointer to hardware structure
5991 * @link_status: the link status word from PCI config space
5992 *
5993 * Stores the PCI bus info (speed, width, type) within the i40e_hw structure
5994 **/
i40e_set_pci_config_data(struct i40e_hw * hw,u16 link_status)5995 void i40e_set_pci_config_data(struct i40e_hw *hw, u16 link_status)
5996 {
5997 hw->bus.type = i40e_bus_type_pci_express;
5998
5999 switch (link_status & I40E_PCI_LINK_WIDTH) {
6000 case I40E_PCI_LINK_WIDTH_1:
6001 hw->bus.width = i40e_bus_width_pcie_x1;
6002 break;
6003 case I40E_PCI_LINK_WIDTH_2:
6004 hw->bus.width = i40e_bus_width_pcie_x2;
6005 break;
6006 case I40E_PCI_LINK_WIDTH_4:
6007 hw->bus.width = i40e_bus_width_pcie_x4;
6008 break;
6009 case I40E_PCI_LINK_WIDTH_8:
6010 hw->bus.width = i40e_bus_width_pcie_x8;
6011 break;
6012 default:
6013 hw->bus.width = i40e_bus_width_unknown;
6014 break;
6015 }
6016
6017 switch (link_status & I40E_PCI_LINK_SPEED) {
6018 case I40E_PCI_LINK_SPEED_2500:
6019 hw->bus.speed = i40e_bus_speed_2500;
6020 break;
6021 case I40E_PCI_LINK_SPEED_5000:
6022 hw->bus.speed = i40e_bus_speed_5000;
6023 break;
6024 case I40E_PCI_LINK_SPEED_8000:
6025 hw->bus.speed = i40e_bus_speed_8000;
6026 break;
6027 default:
6028 hw->bus.speed = i40e_bus_speed_unknown;
6029 break;
6030 }
6031 }
6032
6033 /**
6034 * i40e_aq_debug_dump
6035 * @hw: pointer to the hardware structure
6036 * @cluster_id: specific cluster to dump
6037 * @table_id: table id within cluster
6038 * @start_index: index of line in the block to read
6039 * @buff_size: dump buffer size
6040 * @buff: dump buffer
6041 * @ret_buff_size: actual buffer size returned
6042 * @ret_next_table: next block to read
6043 * @ret_next_index: next index to read
6044 * @cmd_details: pointer to command details structure or NULL
6045 *
6046 * Dump internal FW/HW data for debug purposes.
6047 *
6048 **/
i40e_aq_debug_dump(struct i40e_hw * hw,u8 cluster_id,u8 table_id,u32 start_index,u16 buff_size,void * buff,u16 * ret_buff_size,u8 * ret_next_table,u32 * ret_next_index,struct i40e_asq_cmd_details * cmd_details)6049 enum i40e_status_code i40e_aq_debug_dump(struct i40e_hw *hw, u8 cluster_id,
6050 u8 table_id, u32 start_index, u16 buff_size,
6051 void *buff, u16 *ret_buff_size,
6052 u8 *ret_next_table, u32 *ret_next_index,
6053 struct i40e_asq_cmd_details *cmd_details)
6054 {
6055 struct i40e_aq_desc desc;
6056 struct i40e_aqc_debug_dump_internals *cmd =
6057 (struct i40e_aqc_debug_dump_internals *)&desc.params.raw;
6058 struct i40e_aqc_debug_dump_internals *resp =
6059 (struct i40e_aqc_debug_dump_internals *)&desc.params.raw;
6060 enum i40e_status_code status;
6061
6062 if (buff_size == 0 || !buff)
6063 return I40E_ERR_PARAM;
6064
6065 i40e_fill_default_direct_cmd_desc(&desc,
6066 i40e_aqc_opc_debug_dump_internals);
6067 /* Indirect Command */
6068 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
6069 if (buff_size > I40E_AQ_LARGE_BUF)
6070 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
6071
6072 cmd->cluster_id = cluster_id;
6073 cmd->table_id = table_id;
6074 cmd->idx = CPU_TO_LE32(start_index);
6075
6076 desc.datalen = CPU_TO_LE16(buff_size);
6077
6078 status = i40e_asq_send_command(hw, &desc, buff, buff_size, cmd_details);
6079 if (!status) {
6080 if (ret_buff_size != NULL)
6081 *ret_buff_size = LE16_TO_CPU(desc.datalen);
6082 if (ret_next_table != NULL)
6083 *ret_next_table = resp->table_id;
6084 if (ret_next_index != NULL)
6085 *ret_next_index = LE32_TO_CPU(resp->idx);
6086 }
6087
6088 return status;
6089 }
6090
6091 /**
6092 * i40e_read_bw_from_alt_ram
6093 * @hw: pointer to the hardware structure
6094 * @max_bw: pointer for max_bw read
6095 * @min_bw: pointer for min_bw read
6096 * @min_valid: pointer for bool that is TRUE if min_bw is a valid value
6097 * @max_valid: pointer for bool that is TRUE if max_bw is a valid value
6098 *
6099 * Read bw from the alternate ram for the given pf
6100 **/
i40e_read_bw_from_alt_ram(struct i40e_hw * hw,u32 * max_bw,u32 * min_bw,bool * min_valid,bool * max_valid)6101 enum i40e_status_code i40e_read_bw_from_alt_ram(struct i40e_hw *hw,
6102 u32 *max_bw, u32 *min_bw,
6103 bool *min_valid, bool *max_valid)
6104 {
6105 enum i40e_status_code status;
6106 u32 max_bw_addr, min_bw_addr;
6107
6108 /* Calculate the address of the min/max bw registers */
6109 max_bw_addr = I40E_ALT_STRUCT_FIRST_PF_OFFSET +
6110 I40E_ALT_STRUCT_MAX_BW_OFFSET +
6111 (I40E_ALT_STRUCT_DWORDS_PER_PF * hw->pf_id);
6112 min_bw_addr = I40E_ALT_STRUCT_FIRST_PF_OFFSET +
6113 I40E_ALT_STRUCT_MIN_BW_OFFSET +
6114 (I40E_ALT_STRUCT_DWORDS_PER_PF * hw->pf_id);
6115
6116 /* Read the bandwidths from alt ram */
6117 status = i40e_aq_alternate_read(hw, max_bw_addr, max_bw,
6118 min_bw_addr, min_bw);
6119
6120 if (*min_bw & I40E_ALT_BW_VALID_MASK)
6121 *min_valid = TRUE;
6122 else
6123 *min_valid = FALSE;
6124
6125 if (*max_bw & I40E_ALT_BW_VALID_MASK)
6126 *max_valid = TRUE;
6127 else
6128 *max_valid = FALSE;
6129
6130 return status;
6131 }
6132
6133 /**
6134 * i40e_aq_configure_partition_bw
6135 * @hw: pointer to the hardware structure
6136 * @bw_data: Buffer holding valid pfs and bw limits
6137 * @cmd_details: pointer to command details
6138 *
6139 * Configure partitions guaranteed/max bw
6140 **/
i40e_aq_configure_partition_bw(struct i40e_hw * hw,struct i40e_aqc_configure_partition_bw_data * bw_data,struct i40e_asq_cmd_details * cmd_details)6141 enum i40e_status_code i40e_aq_configure_partition_bw(struct i40e_hw *hw,
6142 struct i40e_aqc_configure_partition_bw_data *bw_data,
6143 struct i40e_asq_cmd_details *cmd_details)
6144 {
6145 enum i40e_status_code status;
6146 struct i40e_aq_desc desc;
6147 u16 bwd_size = sizeof(*bw_data);
6148
6149 i40e_fill_default_direct_cmd_desc(&desc,
6150 i40e_aqc_opc_configure_partition_bw);
6151
6152 /* Indirect command */
6153 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
6154 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_RD);
6155
6156 desc.datalen = CPU_TO_LE16(bwd_size);
6157
6158 status = i40e_asq_send_command(hw, &desc, bw_data, bwd_size, cmd_details);
6159
6160 return status;
6161 }
6162
6163 /**
6164 * i40e_read_phy_register_clause22
6165 * @hw: pointer to the HW structure
6166 * @reg: register address in the page
6167 * @phy_addr: PHY address on MDIO interface
6168 * @value: PHY register value
6169 *
6170 * Reads specified PHY register value
6171 **/
i40e_read_phy_register_clause22(struct i40e_hw * hw,u16 reg,u8 phy_addr,u16 * value)6172 enum i40e_status_code i40e_read_phy_register_clause22(struct i40e_hw *hw,
6173 u16 reg, u8 phy_addr, u16 *value)
6174 {
6175 enum i40e_status_code status = I40E_ERR_TIMEOUT;
6176 u8 port_num = (u8)hw->func_caps.mdio_port_num;
6177 u32 command = 0;
6178 u16 retry = 1000;
6179
6180 command = (reg << I40E_GLGEN_MSCA_DEVADD_SHIFT) |
6181 (phy_addr << I40E_GLGEN_MSCA_PHYADD_SHIFT) |
6182 (I40E_MDIO_CLAUSE22_OPCODE_READ_MASK) |
6183 (I40E_MDIO_CLAUSE22_STCODE_MASK) |
6184 (I40E_GLGEN_MSCA_MDICMD_MASK);
6185 wr32(hw, I40E_GLGEN_MSCA(port_num), command);
6186 do {
6187 command = rd32(hw, I40E_GLGEN_MSCA(port_num));
6188 if (!(command & I40E_GLGEN_MSCA_MDICMD_MASK)) {
6189 status = I40E_SUCCESS;
6190 break;
6191 }
6192 i40e_usec_delay(10);
6193 retry--;
6194 } while (retry);
6195
6196 if (status) {
6197 i40e_debug(hw, I40E_DEBUG_PHY,
6198 "PHY: Can't write command to external PHY.\n");
6199 } else {
6200 command = rd32(hw, I40E_GLGEN_MSRWD(port_num));
6201 *value = (command & I40E_GLGEN_MSRWD_MDIRDDATA_MASK) >>
6202 I40E_GLGEN_MSRWD_MDIRDDATA_SHIFT;
6203 }
6204
6205 return status;
6206 }
6207
6208 /**
6209 * i40e_write_phy_register_clause22
6210 * @hw: pointer to the HW structure
6211 * @reg: register address in the page
6212 * @phy_addr: PHY address on MDIO interface
6213 * @value: PHY register value
6214 *
6215 * Writes specified PHY register value
6216 **/
i40e_write_phy_register_clause22(struct i40e_hw * hw,u16 reg,u8 phy_addr,u16 value)6217 enum i40e_status_code i40e_write_phy_register_clause22(struct i40e_hw *hw,
6218 u16 reg, u8 phy_addr, u16 value)
6219 {
6220 enum i40e_status_code status = I40E_ERR_TIMEOUT;
6221 u8 port_num = (u8)hw->func_caps.mdio_port_num;
6222 u32 command = 0;
6223 u16 retry = 1000;
6224
6225 command = value << I40E_GLGEN_MSRWD_MDIWRDATA_SHIFT;
6226 wr32(hw, I40E_GLGEN_MSRWD(port_num), command);
6227
6228 command = (reg << I40E_GLGEN_MSCA_DEVADD_SHIFT) |
6229 (phy_addr << I40E_GLGEN_MSCA_PHYADD_SHIFT) |
6230 (I40E_MDIO_CLAUSE22_OPCODE_WRITE_MASK) |
6231 (I40E_MDIO_CLAUSE22_STCODE_MASK) |
6232 (I40E_GLGEN_MSCA_MDICMD_MASK);
6233
6234 wr32(hw, I40E_GLGEN_MSCA(port_num), command);
6235 do {
6236 command = rd32(hw, I40E_GLGEN_MSCA(port_num));
6237 if (!(command & I40E_GLGEN_MSCA_MDICMD_MASK)) {
6238 status = I40E_SUCCESS;
6239 break;
6240 }
6241 i40e_usec_delay(10);
6242 retry--;
6243 } while (retry);
6244
6245 return status;
6246 }
6247
6248 /**
6249 * i40e_read_phy_register_clause45
6250 * @hw: pointer to the HW structure
6251 * @page: registers page number
6252 * @reg: register address in the page
6253 * @phy_addr: PHY address on MDIO interface
6254 * @value: PHY register value
6255 *
6256 * Reads specified PHY register value
6257 **/
i40e_read_phy_register_clause45(struct i40e_hw * hw,u8 page,u16 reg,u8 phy_addr,u16 * value)6258 enum i40e_status_code i40e_read_phy_register_clause45(struct i40e_hw *hw,
6259 u8 page, u16 reg, u8 phy_addr, u16 *value)
6260 {
6261 enum i40e_status_code status = I40E_ERR_TIMEOUT;
6262 u32 command = 0;
6263 u16 retry = 1000;
6264 u8 port_num = (u8)hw->func_caps.mdio_port_num;
6265
6266 command = (reg << I40E_GLGEN_MSCA_MDIADD_SHIFT) |
6267 (page << I40E_GLGEN_MSCA_DEVADD_SHIFT) |
6268 (phy_addr << I40E_GLGEN_MSCA_PHYADD_SHIFT) |
6269 (I40E_MDIO_CLAUSE45_OPCODE_ADDRESS_MASK) |
6270 (I40E_MDIO_CLAUSE45_STCODE_MASK) |
6271 (I40E_GLGEN_MSCA_MDICMD_MASK) |
6272 (I40E_GLGEN_MSCA_MDIINPROGEN_MASK);
6273 wr32(hw, I40E_GLGEN_MSCA(port_num), command);
6274 do {
6275 command = rd32(hw, I40E_GLGEN_MSCA(port_num));
6276 if (!(command & I40E_GLGEN_MSCA_MDICMD_MASK)) {
6277 status = I40E_SUCCESS;
6278 break;
6279 }
6280 i40e_usec_delay(10);
6281 retry--;
6282 } while (retry);
6283
6284 if (status) {
6285 i40e_debug(hw, I40E_DEBUG_PHY,
6286 "PHY: Can't write command to external PHY.\n");
6287 goto phy_read_end;
6288 }
6289
6290 command = (page << I40E_GLGEN_MSCA_DEVADD_SHIFT) |
6291 (phy_addr << I40E_GLGEN_MSCA_PHYADD_SHIFT) |
6292 (I40E_MDIO_CLAUSE45_OPCODE_READ_MASK) |
6293 (I40E_MDIO_CLAUSE45_STCODE_MASK) |
6294 (I40E_GLGEN_MSCA_MDICMD_MASK) |
6295 (I40E_GLGEN_MSCA_MDIINPROGEN_MASK);
6296 status = I40E_ERR_TIMEOUT;
6297 retry = 1000;
6298 wr32(hw, I40E_GLGEN_MSCA(port_num), command);
6299 do {
6300 command = rd32(hw, I40E_GLGEN_MSCA(port_num));
6301 if (!(command & I40E_GLGEN_MSCA_MDICMD_MASK)) {
6302 status = I40E_SUCCESS;
6303 break;
6304 }
6305 i40e_usec_delay(10);
6306 retry--;
6307 } while (retry);
6308
6309 if (!status) {
6310 command = rd32(hw, I40E_GLGEN_MSRWD(port_num));
6311 *value = (command & I40E_GLGEN_MSRWD_MDIRDDATA_MASK) >>
6312 I40E_GLGEN_MSRWD_MDIRDDATA_SHIFT;
6313 } else {
6314 i40e_debug(hw, I40E_DEBUG_PHY,
6315 "PHY: Can't read register value from external PHY.\n");
6316 }
6317
6318 phy_read_end:
6319 return status;
6320 }
6321
6322 /**
6323 * i40e_write_phy_register_clause45
6324 * @hw: pointer to the HW structure
6325 * @page: registers page number
6326 * @reg: register address in the page
6327 * @phy_addr: PHY address on MDIO interface
6328 * @value: PHY register value
6329 *
6330 * Writes value to specified PHY register
6331 **/
i40e_write_phy_register_clause45(struct i40e_hw * hw,u8 page,u16 reg,u8 phy_addr,u16 value)6332 enum i40e_status_code i40e_write_phy_register_clause45(struct i40e_hw *hw,
6333 u8 page, u16 reg, u8 phy_addr, u16 value)
6334 {
6335 enum i40e_status_code status = I40E_ERR_TIMEOUT;
6336 u32 command = 0;
6337 u16 retry = 1000;
6338 u8 port_num = (u8)hw->func_caps.mdio_port_num;
6339
6340 command = (reg << I40E_GLGEN_MSCA_MDIADD_SHIFT) |
6341 (page << I40E_GLGEN_MSCA_DEVADD_SHIFT) |
6342 (phy_addr << I40E_GLGEN_MSCA_PHYADD_SHIFT) |
6343 (I40E_MDIO_CLAUSE45_OPCODE_ADDRESS_MASK) |
6344 (I40E_MDIO_CLAUSE45_STCODE_MASK) |
6345 (I40E_GLGEN_MSCA_MDICMD_MASK) |
6346 (I40E_GLGEN_MSCA_MDIINPROGEN_MASK);
6347 wr32(hw, I40E_GLGEN_MSCA(port_num), command);
6348 do {
6349 command = rd32(hw, I40E_GLGEN_MSCA(port_num));
6350 if (!(command & I40E_GLGEN_MSCA_MDICMD_MASK)) {
6351 status = I40E_SUCCESS;
6352 break;
6353 }
6354 i40e_usec_delay(10);
6355 retry--;
6356 } while (retry);
6357 if (status) {
6358 i40e_debug(hw, I40E_DEBUG_PHY,
6359 "PHY: Can't write command to external PHY.\n");
6360 goto phy_write_end;
6361 }
6362
6363 command = value << I40E_GLGEN_MSRWD_MDIWRDATA_SHIFT;
6364 wr32(hw, I40E_GLGEN_MSRWD(port_num), command);
6365
6366 command = (page << I40E_GLGEN_MSCA_DEVADD_SHIFT) |
6367 (phy_addr << I40E_GLGEN_MSCA_PHYADD_SHIFT) |
6368 (I40E_MDIO_CLAUSE45_OPCODE_WRITE_MASK) |
6369 (I40E_MDIO_CLAUSE45_STCODE_MASK) |
6370 (I40E_GLGEN_MSCA_MDICMD_MASK) |
6371 (I40E_GLGEN_MSCA_MDIINPROGEN_MASK);
6372 status = I40E_ERR_TIMEOUT;
6373 retry = 1000;
6374 wr32(hw, I40E_GLGEN_MSCA(port_num), command);
6375 do {
6376 command = rd32(hw, I40E_GLGEN_MSCA(port_num));
6377 if (!(command & I40E_GLGEN_MSCA_MDICMD_MASK)) {
6378 status = I40E_SUCCESS;
6379 break;
6380 }
6381 i40e_usec_delay(10);
6382 retry--;
6383 } while (retry);
6384
6385 phy_write_end:
6386 return status;
6387 }
6388
6389 /**
6390 * i40e_write_phy_register
6391 * @hw: pointer to the HW structure
6392 * @page: registers page number
6393 * @reg: register address in the page
6394 * @phy_addr: PHY address on MDIO interface
6395 * @value: PHY register value
6396 *
6397 * Writes value to specified PHY register
6398 **/
i40e_write_phy_register(struct i40e_hw * hw,u8 page,u16 reg,u8 phy_addr,u16 value)6399 enum i40e_status_code i40e_write_phy_register(struct i40e_hw *hw,
6400 u8 page, u16 reg, u8 phy_addr, u16 value)
6401 {
6402 enum i40e_status_code status;
6403
6404 switch (hw->device_id) {
6405 case I40E_DEV_ID_1G_BASE_T_X722:
6406 status = i40e_write_phy_register_clause22(hw,
6407 reg, phy_addr, value);
6408 break;
6409 case I40E_DEV_ID_10G_BASE_T:
6410 case I40E_DEV_ID_10G_BASE_T4:
6411 case I40E_DEV_ID_10G_BASE_T_X722:
6412 case I40E_DEV_ID_25G_B:
6413 case I40E_DEV_ID_25G_SFP28:
6414 status = i40e_write_phy_register_clause45(hw,
6415 page, reg, phy_addr, value);
6416 break;
6417 default:
6418 status = I40E_ERR_UNKNOWN_PHY;
6419 break;
6420 }
6421
6422 return status;
6423 }
6424
6425 /**
6426 * i40e_read_phy_register
6427 * @hw: pointer to the HW structure
6428 * @page: registers page number
6429 * @reg: register address in the page
6430 * @phy_addr: PHY address on MDIO interface
6431 * @value: PHY register value
6432 *
6433 * Reads specified PHY register value
6434 **/
i40e_read_phy_register(struct i40e_hw * hw,u8 page,u16 reg,u8 phy_addr,u16 * value)6435 enum i40e_status_code i40e_read_phy_register(struct i40e_hw *hw,
6436 u8 page, u16 reg, u8 phy_addr, u16 *value)
6437 {
6438 enum i40e_status_code status;
6439
6440 switch (hw->device_id) {
6441 case I40E_DEV_ID_1G_BASE_T_X722:
6442 status = i40e_read_phy_register_clause22(hw, reg, phy_addr,
6443 value);
6444 break;
6445 case I40E_DEV_ID_10G_BASE_T:
6446 case I40E_DEV_ID_10G_BASE_T4:
6447 case I40E_DEV_ID_10G_BASE_T_X722:
6448 case I40E_DEV_ID_25G_B:
6449 case I40E_DEV_ID_25G_SFP28:
6450 status = i40e_read_phy_register_clause45(hw, page, reg,
6451 phy_addr, value);
6452 break;
6453 default:
6454 status = I40E_ERR_UNKNOWN_PHY;
6455 break;
6456 }
6457
6458 return status;
6459 }
6460
6461 /**
6462 * i40e_get_phy_address
6463 * @hw: pointer to the HW structure
6464 * @dev_num: PHY port num that address we want
6465 *
6466 * Gets PHY address for current port
6467 **/
i40e_get_phy_address(struct i40e_hw * hw,u8 dev_num)6468 u8 i40e_get_phy_address(struct i40e_hw *hw, u8 dev_num)
6469 {
6470 u8 port_num = (u8)hw->func_caps.mdio_port_num;
6471 u32 reg_val = rd32(hw, I40E_GLGEN_MDIO_I2C_SEL(port_num));
6472
6473 return (u8)(reg_val >> ((dev_num + 1) * 5)) & 0x1f;
6474 }
6475
6476 /**
6477 * i40e_blink_phy_led
6478 * @hw: pointer to the HW structure
6479 * @time: time how long led will blinks in secs
6480 * @interval: gap between LED on and off in msecs
6481 *
6482 * Blinks PHY link LED
6483 **/
i40e_blink_phy_link_led(struct i40e_hw * hw,u32 time,u32 interval)6484 enum i40e_status_code i40e_blink_phy_link_led(struct i40e_hw *hw,
6485 u32 time, u32 interval)
6486 {
6487 enum i40e_status_code status = I40E_SUCCESS;
6488 u32 i;
6489 u16 led_ctl = 0;
6490 u16 gpio_led_port;
6491 u16 led_reg;
6492 u16 led_addr = I40E_PHY_LED_PROV_REG_1;
6493 u8 phy_addr = 0;
6494 u8 port_num;
6495
6496 i = rd32(hw, I40E_PFGEN_PORTNUM);
6497 port_num = (u8)(i & I40E_PFGEN_PORTNUM_PORT_NUM_MASK);
6498 phy_addr = i40e_get_phy_address(hw, port_num);
6499
6500 for (gpio_led_port = 0; gpio_led_port < 3; gpio_led_port++,
6501 led_addr++) {
6502 status = i40e_read_phy_register_clause45(hw,
6503 I40E_PHY_COM_REG_PAGE,
6504 led_addr, phy_addr,
6505 &led_reg);
6506 if (status)
6507 goto phy_blinking_end;
6508 led_ctl = led_reg;
6509 if (led_reg & I40E_PHY_LED_LINK_MODE_MASK) {
6510 led_reg = 0;
6511 status = i40e_write_phy_register_clause45(hw,
6512 I40E_PHY_COM_REG_PAGE,
6513 led_addr, phy_addr,
6514 led_reg);
6515 if (status)
6516 goto phy_blinking_end;
6517 break;
6518 }
6519 }
6520
6521 if (time > 0 && interval > 0) {
6522 for (i = 0; i < time * 1000; i += interval) {
6523 status = i40e_read_phy_register_clause45(hw,
6524 I40E_PHY_COM_REG_PAGE,
6525 led_addr, phy_addr, &led_reg);
6526 if (status)
6527 goto restore_config;
6528 if (led_reg & I40E_PHY_LED_MANUAL_ON)
6529 led_reg = 0;
6530 else
6531 led_reg = I40E_PHY_LED_MANUAL_ON;
6532 status = i40e_write_phy_register_clause45(hw,
6533 I40E_PHY_COM_REG_PAGE,
6534 led_addr, phy_addr, led_reg);
6535 if (status)
6536 goto restore_config;
6537 i40e_msec_delay(interval);
6538 }
6539 }
6540
6541 restore_config:
6542 status = i40e_write_phy_register_clause45(hw,
6543 I40E_PHY_COM_REG_PAGE,
6544 led_addr, phy_addr, led_ctl);
6545
6546 phy_blinking_end:
6547 return status;
6548 }
6549
6550 /**
6551 * i40e_led_get_reg - read LED register
6552 * @hw: pointer to the HW structure
6553 * @led_addr: LED register address
6554 * @reg_val: read register value
6555 **/
i40e_led_get_reg(struct i40e_hw * hw,u16 led_addr,u32 * reg_val)6556 static enum i40e_status_code i40e_led_get_reg(struct i40e_hw *hw, u16 led_addr,
6557 u32 *reg_val)
6558 {
6559 enum i40e_status_code status;
6560 u8 phy_addr = 0;
6561
6562 *reg_val = 0;
6563 if (hw->flags & I40E_HW_FLAG_AQ_PHY_ACCESS_CAPABLE) {
6564 status = i40e_aq_get_phy_register(hw,
6565 I40E_AQ_PHY_REG_ACCESS_EXTERNAL,
6566 I40E_PHY_COM_REG_PAGE,
6567 I40E_PHY_LED_PROV_REG_1,
6568 reg_val, NULL);
6569 } else {
6570 phy_addr = i40e_get_phy_address(hw, hw->port);
6571 status = i40e_read_phy_register_clause45(hw,
6572 I40E_PHY_COM_REG_PAGE,
6573 led_addr, phy_addr,
6574 (u16 *)reg_val);
6575 }
6576 return status;
6577 }
6578
6579 /**
6580 * i40e_led_set_reg - write LED register
6581 * @hw: pointer to the HW structure
6582 * @led_addr: LED register address
6583 * @reg_val: register value to write
6584 **/
i40e_led_set_reg(struct i40e_hw * hw,u16 led_addr,u32 reg_val)6585 static enum i40e_status_code i40e_led_set_reg(struct i40e_hw *hw, u16 led_addr,
6586 u32 reg_val)
6587 {
6588 enum i40e_status_code status;
6589 u8 phy_addr = 0;
6590
6591 if (hw->flags & I40E_HW_FLAG_AQ_PHY_ACCESS_CAPABLE) {
6592 status = i40e_aq_set_phy_register(hw,
6593 I40E_AQ_PHY_REG_ACCESS_EXTERNAL,
6594 I40E_PHY_COM_REG_PAGE,
6595 I40E_PHY_LED_PROV_REG_1,
6596 reg_val, NULL);
6597 } else {
6598 phy_addr = i40e_get_phy_address(hw, hw->port);
6599 status = i40e_write_phy_register_clause45(hw,
6600 I40E_PHY_COM_REG_PAGE,
6601 led_addr, phy_addr,
6602 (u16)reg_val);
6603 }
6604
6605 return status;
6606 }
6607
6608 /**
6609 * i40e_led_get_phy - return current on/off mode
6610 * @hw: pointer to the hw struct
6611 * @led_addr: address of led register to use
6612 * @val: original value of register to use
6613 *
6614 **/
i40e_led_get_phy(struct i40e_hw * hw,u16 * led_addr,u16 * val)6615 enum i40e_status_code i40e_led_get_phy(struct i40e_hw *hw, u16 *led_addr,
6616 u16 *val)
6617 {
6618 enum i40e_status_code status = I40E_SUCCESS;
6619 u16 gpio_led_port;
6620 u32 reg_val_aq;
6621 u16 temp_addr;
6622 u8 phy_addr = 0;
6623 u16 reg_val;
6624
6625 if (hw->flags & I40E_HW_FLAG_AQ_PHY_ACCESS_CAPABLE) {
6626 status = i40e_aq_get_phy_register(hw,
6627 I40E_AQ_PHY_REG_ACCESS_EXTERNAL,
6628 I40E_PHY_COM_REG_PAGE,
6629 I40E_PHY_LED_PROV_REG_1,
6630 ®_val_aq, NULL);
6631 if (status == I40E_SUCCESS)
6632 *val = (u16)reg_val_aq;
6633 return status;
6634 }
6635 temp_addr = I40E_PHY_LED_PROV_REG_1;
6636 phy_addr = i40e_get_phy_address(hw, hw->port);
6637 for (gpio_led_port = 0; gpio_led_port < 3; gpio_led_port++,
6638 temp_addr++) {
6639 status = i40e_read_phy_register_clause45(hw,
6640 I40E_PHY_COM_REG_PAGE,
6641 temp_addr, phy_addr,
6642 ®_val);
6643 if (status)
6644 return status;
6645 *val = reg_val;
6646 if (reg_val & I40E_PHY_LED_LINK_MODE_MASK) {
6647 *led_addr = temp_addr;
6648 break;
6649 }
6650 }
6651 return status;
6652 }
6653
6654 /**
6655 * i40e_led_set_phy
6656 * @hw: pointer to the HW structure
6657 * @on: TRUE or FALSE
6658 * @led_addr: address of led register to use
6659 * @mode: original val plus bit for set or ignore
6660 *
6661 * Set led's on or off when controlled by the PHY
6662 *
6663 **/
i40e_led_set_phy(struct i40e_hw * hw,bool on,u16 led_addr,u32 mode)6664 enum i40e_status_code i40e_led_set_phy(struct i40e_hw *hw, bool on,
6665 u16 led_addr, u32 mode)
6666 {
6667 enum i40e_status_code status = I40E_SUCCESS;
6668 u32 led_ctl = 0;
6669 u32 led_reg = 0;
6670
6671 status = i40e_led_get_reg(hw, led_addr, &led_reg);
6672 if (status)
6673 return status;
6674 led_ctl = led_reg;
6675 if (led_reg & I40E_PHY_LED_LINK_MODE_MASK) {
6676 led_reg = 0;
6677 status = i40e_led_set_reg(hw, led_addr, led_reg);
6678 if (status)
6679 return status;
6680 }
6681 status = i40e_led_get_reg(hw, led_addr, &led_reg);
6682 if (status)
6683 goto restore_config;
6684 if (on)
6685 led_reg = I40E_PHY_LED_MANUAL_ON;
6686 else
6687 led_reg = 0;
6688 status = i40e_led_set_reg(hw, led_addr, led_reg);
6689 if (status)
6690 goto restore_config;
6691 if (mode & I40E_PHY_LED_MODE_ORIG) {
6692 led_ctl = (mode & I40E_PHY_LED_MODE_MASK);
6693 status = i40e_led_set_reg(hw, led_addr, led_ctl);
6694 }
6695 return status;
6696
6697 restore_config:
6698 status = i40e_led_set_reg(hw, led_addr, led_ctl);
6699 return status;
6700 }
6701
6702 /**
6703 * i40e_aq_rx_ctl_read_register - use FW to read from an Rx control register
6704 * @hw: pointer to the hw struct
6705 * @reg_addr: register address
6706 * @reg_val: ptr to register value
6707 * @cmd_details: pointer to command details structure or NULL
6708 *
6709 * Use the firmware to read the Rx control register,
6710 * especially useful if the Rx unit is under heavy pressure
6711 **/
i40e_aq_rx_ctl_read_register(struct i40e_hw * hw,u32 reg_addr,u32 * reg_val,struct i40e_asq_cmd_details * cmd_details)6712 enum i40e_status_code i40e_aq_rx_ctl_read_register(struct i40e_hw *hw,
6713 u32 reg_addr, u32 *reg_val,
6714 struct i40e_asq_cmd_details *cmd_details)
6715 {
6716 struct i40e_aq_desc desc;
6717 struct i40e_aqc_rx_ctl_reg_read_write *cmd_resp =
6718 (struct i40e_aqc_rx_ctl_reg_read_write *)&desc.params.raw;
6719 enum i40e_status_code status;
6720
6721 if (reg_val == NULL)
6722 return I40E_ERR_PARAM;
6723
6724 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_rx_ctl_reg_read);
6725
6726 cmd_resp->address = CPU_TO_LE32(reg_addr);
6727
6728 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
6729
6730 if (status == I40E_SUCCESS)
6731 *reg_val = LE32_TO_CPU(cmd_resp->value);
6732
6733 return status;
6734 }
6735
6736 /**
6737 * i40e_read_rx_ctl - read from an Rx control register
6738 * @hw: pointer to the hw struct
6739 * @reg_addr: register address
6740 **/
i40e_read_rx_ctl(struct i40e_hw * hw,u32 reg_addr)6741 u32 i40e_read_rx_ctl(struct i40e_hw *hw, u32 reg_addr)
6742 {
6743 enum i40e_status_code status = I40E_SUCCESS;
6744 bool use_register;
6745 int retry = 5;
6746 u32 val = 0;
6747
6748 use_register = (((hw->aq.api_maj_ver == 1) &&
6749 (hw->aq.api_min_ver < 5)) ||
6750 (hw->mac.type == I40E_MAC_X722));
6751 if (!use_register) {
6752 do_retry:
6753 status = i40e_aq_rx_ctl_read_register(hw, reg_addr, &val, NULL);
6754 if (hw->aq.asq_last_status == I40E_AQ_RC_EAGAIN && retry) {
6755 i40e_msec_delay(1);
6756 retry--;
6757 goto do_retry;
6758 }
6759 }
6760
6761 /* if the AQ access failed, try the old-fashioned way */
6762 if (status || use_register)
6763 val = rd32(hw, reg_addr);
6764
6765 return val;
6766 }
6767
6768 /**
6769 * i40e_aq_rx_ctl_write_register
6770 * @hw: pointer to the hw struct
6771 * @reg_addr: register address
6772 * @reg_val: register value
6773 * @cmd_details: pointer to command details structure or NULL
6774 *
6775 * Use the firmware to write to an Rx control register,
6776 * especially useful if the Rx unit is under heavy pressure
6777 **/
i40e_aq_rx_ctl_write_register(struct i40e_hw * hw,u32 reg_addr,u32 reg_val,struct i40e_asq_cmd_details * cmd_details)6778 enum i40e_status_code i40e_aq_rx_ctl_write_register(struct i40e_hw *hw,
6779 u32 reg_addr, u32 reg_val,
6780 struct i40e_asq_cmd_details *cmd_details)
6781 {
6782 struct i40e_aq_desc desc;
6783 struct i40e_aqc_rx_ctl_reg_read_write *cmd =
6784 (struct i40e_aqc_rx_ctl_reg_read_write *)&desc.params.raw;
6785 enum i40e_status_code status;
6786
6787 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_rx_ctl_reg_write);
6788
6789 cmd->address = CPU_TO_LE32(reg_addr);
6790 cmd->value = CPU_TO_LE32(reg_val);
6791
6792 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
6793
6794 return status;
6795 }
6796
6797 /**
6798 * i40e_write_rx_ctl - write to an Rx control register
6799 * @hw: pointer to the hw struct
6800 * @reg_addr: register address
6801 * @reg_val: register value
6802 **/
i40e_write_rx_ctl(struct i40e_hw * hw,u32 reg_addr,u32 reg_val)6803 void i40e_write_rx_ctl(struct i40e_hw *hw, u32 reg_addr, u32 reg_val)
6804 {
6805 enum i40e_status_code status = I40E_SUCCESS;
6806 bool use_register;
6807 int retry = 5;
6808
6809 use_register = (((hw->aq.api_maj_ver == 1) &&
6810 (hw->aq.api_min_ver < 5)) ||
6811 (hw->mac.type == I40E_MAC_X722));
6812 if (!use_register) {
6813 do_retry:
6814 status = i40e_aq_rx_ctl_write_register(hw, reg_addr,
6815 reg_val, NULL);
6816 if (hw->aq.asq_last_status == I40E_AQ_RC_EAGAIN && retry) {
6817 i40e_msec_delay(1);
6818 retry--;
6819 goto do_retry;
6820 }
6821 }
6822
6823 /* if the AQ access failed, try the old-fashioned way */
6824 if (status || use_register)
6825 wr32(hw, reg_addr, reg_val);
6826 }
6827
6828 /**
6829 * i40e_aq_set_phy_register
6830 * @hw: pointer to the hw struct
6831 * @phy_select: select which phy should be accessed
6832 * @dev_addr: PHY device address
6833 * @reg_addr: PHY register address
6834 * @reg_val: new register value
6835 * @cmd_details: pointer to command details structure or NULL
6836 *
6837 * Write the external PHY register.
6838 **/
i40e_aq_set_phy_register(struct i40e_hw * hw,u8 phy_select,u8 dev_addr,u32 reg_addr,u32 reg_val,struct i40e_asq_cmd_details * cmd_details)6839 enum i40e_status_code i40e_aq_set_phy_register(struct i40e_hw *hw,
6840 u8 phy_select, u8 dev_addr,
6841 u32 reg_addr, u32 reg_val,
6842 struct i40e_asq_cmd_details *cmd_details)
6843 {
6844 struct i40e_aq_desc desc;
6845 struct i40e_aqc_phy_register_access *cmd =
6846 (struct i40e_aqc_phy_register_access *)&desc.params.raw;
6847 enum i40e_status_code status;
6848
6849 i40e_fill_default_direct_cmd_desc(&desc,
6850 i40e_aqc_opc_set_phy_register);
6851
6852 cmd->phy_interface = phy_select;
6853 cmd->dev_addres = dev_addr;
6854 cmd->reg_address = CPU_TO_LE32(reg_addr);
6855 cmd->reg_value = CPU_TO_LE32(reg_val);
6856
6857 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
6858
6859 return status;
6860 }
6861
6862 /**
6863 * i40e_aq_get_phy_register
6864 * @hw: pointer to the hw struct
6865 * @phy_select: select which phy should be accessed
6866 * @dev_addr: PHY device address
6867 * @reg_addr: PHY register address
6868 * @reg_val: read register value
6869 * @cmd_details: pointer to command details structure or NULL
6870 *
6871 * Read the external PHY register.
6872 **/
i40e_aq_get_phy_register(struct i40e_hw * hw,u8 phy_select,u8 dev_addr,u32 reg_addr,u32 * reg_val,struct i40e_asq_cmd_details * cmd_details)6873 enum i40e_status_code i40e_aq_get_phy_register(struct i40e_hw *hw,
6874 u8 phy_select, u8 dev_addr,
6875 u32 reg_addr, u32 *reg_val,
6876 struct i40e_asq_cmd_details *cmd_details)
6877 {
6878 struct i40e_aq_desc desc;
6879 struct i40e_aqc_phy_register_access *cmd =
6880 (struct i40e_aqc_phy_register_access *)&desc.params.raw;
6881 enum i40e_status_code status;
6882
6883 i40e_fill_default_direct_cmd_desc(&desc,
6884 i40e_aqc_opc_get_phy_register);
6885
6886 cmd->phy_interface = phy_select;
6887 cmd->dev_addres = dev_addr;
6888 cmd->reg_address = CPU_TO_LE32(reg_addr);
6889
6890 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
6891 if (!status)
6892 *reg_val = LE32_TO_CPU(cmd->reg_value);
6893
6894 return status;
6895 }
6896
6897
6898 /**
6899 * i40e_aq_send_msg_to_pf
6900 * @hw: pointer to the hardware structure
6901 * @v_opcode: opcodes for VF-PF communication
6902 * @v_retval: return error code
6903 * @msg: pointer to the msg buffer
6904 * @msglen: msg length
6905 * @cmd_details: pointer to command details
6906 *
6907 * Send message to PF driver using admin queue. By default, this message
6908 * is sent asynchronously, i.e. i40e_asq_send_command() does not wait for
6909 * completion before returning.
6910 **/
i40e_aq_send_msg_to_pf(struct i40e_hw * hw,enum virtchnl_ops v_opcode,enum i40e_status_code v_retval,u8 * msg,u16 msglen,struct i40e_asq_cmd_details * cmd_details)6911 enum i40e_status_code i40e_aq_send_msg_to_pf(struct i40e_hw *hw,
6912 enum virtchnl_ops v_opcode,
6913 enum i40e_status_code v_retval,
6914 u8 *msg, u16 msglen,
6915 struct i40e_asq_cmd_details *cmd_details)
6916 {
6917 struct i40e_aq_desc desc;
6918 struct i40e_asq_cmd_details details;
6919 enum i40e_status_code status;
6920
6921 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_send_msg_to_pf);
6922 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_SI);
6923 desc.cookie_high = CPU_TO_LE32(v_opcode);
6924 desc.cookie_low = CPU_TO_LE32(v_retval);
6925 if (msglen) {
6926 desc.flags |= CPU_TO_LE16((u16)(I40E_AQ_FLAG_BUF
6927 | I40E_AQ_FLAG_RD));
6928 if (msglen > I40E_AQ_LARGE_BUF)
6929 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_LB);
6930 desc.datalen = CPU_TO_LE16(msglen);
6931 }
6932 if (!cmd_details) {
6933 i40e_memset(&details, 0, sizeof(details), I40E_NONDMA_MEM);
6934 details.async = TRUE;
6935 cmd_details = &details;
6936 }
6937 status = i40e_asq_send_command(hw, (struct i40e_aq_desc *)&desc, msg,
6938 msglen, cmd_details);
6939 return status;
6940 }
6941
6942 /**
6943 * i40e_vf_parse_hw_config
6944 * @hw: pointer to the hardware structure
6945 * @msg: pointer to the virtual channel VF resource structure
6946 *
6947 * Given a VF resource message from the PF, populate the hw struct
6948 * with appropriate information.
6949 **/
i40e_vf_parse_hw_config(struct i40e_hw * hw,struct virtchnl_vf_resource * msg)6950 void i40e_vf_parse_hw_config(struct i40e_hw *hw,
6951 struct virtchnl_vf_resource *msg)
6952 {
6953 struct virtchnl_vsi_resource *vsi_res;
6954 int i;
6955
6956 vsi_res = &msg->vsi_res[0];
6957
6958 hw->dev_caps.num_vsis = msg->num_vsis;
6959 hw->dev_caps.num_rx_qp = msg->num_queue_pairs;
6960 hw->dev_caps.num_tx_qp = msg->num_queue_pairs;
6961 hw->dev_caps.num_msix_vectors_vf = msg->max_vectors;
6962 hw->dev_caps.dcb = msg->vf_cap_flags &
6963 VIRTCHNL_VF_OFFLOAD_L2;
6964 hw->dev_caps.iwarp = (msg->vf_cap_flags &
6965 VIRTCHNL_VF_OFFLOAD_IWARP) ? 1 : 0;
6966 for (i = 0; i < msg->num_vsis; i++) {
6967 if (vsi_res->vsi_type == VIRTCHNL_VSI_SRIOV) {
6968 i40e_memcpy(hw->mac.perm_addr,
6969 vsi_res->default_mac_addr,
6970 ETH_ALEN,
6971 I40E_NONDMA_TO_NONDMA);
6972 i40e_memcpy(hw->mac.addr, vsi_res->default_mac_addr,
6973 ETH_ALEN,
6974 I40E_NONDMA_TO_NONDMA);
6975 }
6976 vsi_res++;
6977 }
6978 }
6979
6980 /**
6981 * i40e_vf_reset
6982 * @hw: pointer to the hardware structure
6983 *
6984 * Send a VF_RESET message to the PF. Does not wait for response from PF
6985 * as none will be forthcoming. Immediately after calling this function,
6986 * the admin queue should be shut down and (optionally) reinitialized.
6987 **/
i40e_vf_reset(struct i40e_hw * hw)6988 enum i40e_status_code i40e_vf_reset(struct i40e_hw *hw)
6989 {
6990 return i40e_aq_send_msg_to_pf(hw, VIRTCHNL_OP_RESET_VF,
6991 I40E_SUCCESS, NULL, 0, NULL);
6992 }
6993
6994 /**
6995 * i40e_aq_set_arp_proxy_config
6996 * @hw: pointer to the HW structure
6997 * @proxy_config: pointer to proxy config command table struct
6998 * @cmd_details: pointer to command details
6999 *
7000 * Set ARP offload parameters from pre-populated
7001 * i40e_aqc_arp_proxy_data struct
7002 **/
i40e_aq_set_arp_proxy_config(struct i40e_hw * hw,struct i40e_aqc_arp_proxy_data * proxy_config,struct i40e_asq_cmd_details * cmd_details)7003 enum i40e_status_code i40e_aq_set_arp_proxy_config(struct i40e_hw *hw,
7004 struct i40e_aqc_arp_proxy_data *proxy_config,
7005 struct i40e_asq_cmd_details *cmd_details)
7006 {
7007 struct i40e_aq_desc desc;
7008 enum i40e_status_code status;
7009
7010 if (!proxy_config)
7011 return I40E_ERR_PARAM;
7012
7013 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_set_proxy_config);
7014
7015 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
7016 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_RD);
7017 desc.params.external.addr_high =
7018 CPU_TO_LE32(I40E_HI_DWORD((u64)proxy_config));
7019 desc.params.external.addr_low =
7020 CPU_TO_LE32(I40E_LO_DWORD((u64)proxy_config));
7021 desc.datalen = CPU_TO_LE16(sizeof(struct i40e_aqc_arp_proxy_data));
7022
7023 status = i40e_asq_send_command(hw, &desc, proxy_config,
7024 sizeof(struct i40e_aqc_arp_proxy_data),
7025 cmd_details);
7026
7027 return status;
7028 }
7029
7030 /**
7031 * i40e_aq_opc_set_ns_proxy_table_entry
7032 * @hw: pointer to the HW structure
7033 * @ns_proxy_table_entry: pointer to NS table entry command struct
7034 * @cmd_details: pointer to command details
7035 *
7036 * Set IPv6 Neighbor Solicitation (NS) protocol offload parameters
7037 * from pre-populated i40e_aqc_ns_proxy_data struct
7038 **/
i40e_aq_set_ns_proxy_table_entry(struct i40e_hw * hw,struct i40e_aqc_ns_proxy_data * ns_proxy_table_entry,struct i40e_asq_cmd_details * cmd_details)7039 enum i40e_status_code i40e_aq_set_ns_proxy_table_entry(struct i40e_hw *hw,
7040 struct i40e_aqc_ns_proxy_data *ns_proxy_table_entry,
7041 struct i40e_asq_cmd_details *cmd_details)
7042 {
7043 struct i40e_aq_desc desc;
7044 enum i40e_status_code status;
7045
7046 if (!ns_proxy_table_entry)
7047 return I40E_ERR_PARAM;
7048
7049 i40e_fill_default_direct_cmd_desc(&desc,
7050 i40e_aqc_opc_set_ns_proxy_table_entry);
7051
7052 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
7053 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_RD);
7054 desc.params.external.addr_high =
7055 CPU_TO_LE32(I40E_HI_DWORD((u64)ns_proxy_table_entry));
7056 desc.params.external.addr_low =
7057 CPU_TO_LE32(I40E_LO_DWORD((u64)ns_proxy_table_entry));
7058 desc.datalen = CPU_TO_LE16(sizeof(struct i40e_aqc_ns_proxy_data));
7059
7060 status = i40e_asq_send_command(hw, &desc, ns_proxy_table_entry,
7061 sizeof(struct i40e_aqc_ns_proxy_data),
7062 cmd_details);
7063
7064 return status;
7065 }
7066
7067 /**
7068 * i40e_aq_set_clear_wol_filter
7069 * @hw: pointer to the hw struct
7070 * @filter_index: index of filter to modify (0-7)
7071 * @filter: buffer containing filter to be set
7072 * @set_filter: TRUE to set filter, FALSE to clear filter
7073 * @no_wol_tco: if TRUE, pass through packets cannot cause wake-up
7074 * if FALSE, pass through packets may cause wake-up
7075 * @filter_valid: TRUE if filter action is valid
7076 * @no_wol_tco_valid: TRUE if no WoL in TCO traffic action valid
7077 * @cmd_details: pointer to command details structure or NULL
7078 *
7079 * Set or clear WoL filter for port attached to the PF
7080 **/
i40e_aq_set_clear_wol_filter(struct i40e_hw * hw,u8 filter_index,struct i40e_aqc_set_wol_filter_data * filter,bool set_filter,bool no_wol_tco,bool filter_valid,bool no_wol_tco_valid,struct i40e_asq_cmd_details * cmd_details)7081 enum i40e_status_code i40e_aq_set_clear_wol_filter(struct i40e_hw *hw,
7082 u8 filter_index,
7083 struct i40e_aqc_set_wol_filter_data *filter,
7084 bool set_filter, bool no_wol_tco,
7085 bool filter_valid, bool no_wol_tco_valid,
7086 struct i40e_asq_cmd_details *cmd_details)
7087 {
7088 struct i40e_aq_desc desc;
7089 struct i40e_aqc_set_wol_filter *cmd =
7090 (struct i40e_aqc_set_wol_filter *)&desc.params.raw;
7091 enum i40e_status_code status;
7092 u16 cmd_flags = 0;
7093 u16 valid_flags = 0;
7094 u16 buff_len = 0;
7095
7096 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_set_wol_filter);
7097
7098 if (filter_index >= I40E_AQC_MAX_NUM_WOL_FILTERS)
7099 return I40E_ERR_PARAM;
7100 cmd->filter_index = CPU_TO_LE16(filter_index);
7101
7102 if (set_filter) {
7103 if (!filter)
7104 return I40E_ERR_PARAM;
7105
7106 cmd_flags |= I40E_AQC_SET_WOL_FILTER;
7107 cmd_flags |= I40E_AQC_SET_WOL_FILTER_WOL_PRESERVE_ON_PFR;
7108 }
7109
7110 if (no_wol_tco)
7111 cmd_flags |= I40E_AQC_SET_WOL_FILTER_NO_TCO_WOL;
7112 cmd->cmd_flags = CPU_TO_LE16(cmd_flags);
7113
7114 if (filter_valid)
7115 valid_flags |= I40E_AQC_SET_WOL_FILTER_ACTION_VALID;
7116 if (no_wol_tco_valid)
7117 valid_flags |= I40E_AQC_SET_WOL_FILTER_NO_TCO_ACTION_VALID;
7118 cmd->valid_flags = CPU_TO_LE16(valid_flags);
7119
7120 buff_len = sizeof(*filter);
7121 desc.datalen = CPU_TO_LE16(buff_len);
7122
7123 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_BUF);
7124 desc.flags |= CPU_TO_LE16((u16)I40E_AQ_FLAG_RD);
7125
7126 cmd->address_high = CPU_TO_LE32(I40E_HI_DWORD((u64)filter));
7127 cmd->address_low = CPU_TO_LE32(I40E_LO_DWORD((u64)filter));
7128
7129 status = i40e_asq_send_command(hw, &desc, filter,
7130 buff_len, cmd_details);
7131
7132 return status;
7133 }
7134
7135 /**
7136 * i40e_aq_get_wake_event_reason
7137 * @hw: pointer to the hw struct
7138 * @wake_reason: return value, index of matching filter
7139 * @cmd_details: pointer to command details structure or NULL
7140 *
7141 * Get information for the reason of a Wake Up event
7142 **/
i40e_aq_get_wake_event_reason(struct i40e_hw * hw,u16 * wake_reason,struct i40e_asq_cmd_details * cmd_details)7143 enum i40e_status_code i40e_aq_get_wake_event_reason(struct i40e_hw *hw,
7144 u16 *wake_reason,
7145 struct i40e_asq_cmd_details *cmd_details)
7146 {
7147 struct i40e_aq_desc desc;
7148 struct i40e_aqc_get_wake_reason_completion *resp =
7149 (struct i40e_aqc_get_wake_reason_completion *)&desc.params.raw;
7150 enum i40e_status_code status;
7151
7152 i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_get_wake_reason);
7153
7154 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
7155
7156 if (status == I40E_SUCCESS)
7157 *wake_reason = LE16_TO_CPU(resp->wake_reason);
7158
7159 return status;
7160 }
7161
7162 /**
7163 * i40e_aq_clear_all_wol_filters
7164 * @hw: pointer to the hw struct
7165 * @cmd_details: pointer to command details structure or NULL
7166 *
7167 * Get information for the reason of a Wake Up event
7168 **/
i40e_aq_clear_all_wol_filters(struct i40e_hw * hw,struct i40e_asq_cmd_details * cmd_details)7169 enum i40e_status_code i40e_aq_clear_all_wol_filters(struct i40e_hw *hw,
7170 struct i40e_asq_cmd_details *cmd_details)
7171 {
7172 struct i40e_aq_desc desc;
7173 enum i40e_status_code status;
7174
7175 i40e_fill_default_direct_cmd_desc(&desc,
7176 i40e_aqc_opc_clear_all_wol_filters);
7177
7178 status = i40e_asq_send_command(hw, &desc, NULL, 0, cmd_details);
7179
7180 return status;
7181 }
7182
7183