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