blob: 832da609d9a7d463462ae97d3143fe17153c6192 [file] [log] [blame]
Sasha Neftin13b5b7f2018-10-11 10:17:19 +03001// SPDX-License-Identifier: GPL-2.0
2/* Copyright (c) 2018 Intel Corporation */
3
4#include <linux/delay.h>
5
6#include "igc_hw.h"
7#include "igc_i225.h"
Sasha Neftinc0071c72018-10-11 10:17:26 +03008#include "igc_mac.h"
9#include "igc_base.h"
10#include "igc.h"
11
12/**
13 * igc_set_pcie_completion_timeout - set pci-e completion timeout
14 * @hw: pointer to the HW structure
15 */
16static s32 igc_set_pcie_completion_timeout(struct igc_hw *hw)
17{
18 u32 gcr = rd32(IGC_GCR);
19 u16 pcie_devctl2;
20 s32 ret_val = 0;
21
22 /* only take action if timeout value is defaulted to 0 */
23 if (gcr & IGC_GCR_CMPL_TMOUT_MASK)
24 goto out;
25
26 /* if capabilities version is type 1 we can write the
27 * timeout of 10ms to 200ms through the GCR register
28 */
29 if (!(gcr & IGC_GCR_CAP_VER2)) {
30 gcr |= IGC_GCR_CMPL_TMOUT_10ms;
31 goto out;
32 }
33
34 /* for version 2 capabilities we need to write the config space
35 * directly in order to set the completion timeout value for
36 * 16ms to 55ms
37 */
38 ret_val = igc_read_pcie_cap_reg(hw, PCIE_DEVICE_CONTROL2,
39 &pcie_devctl2);
40 if (ret_val)
41 goto out;
42
43 pcie_devctl2 |= PCIE_DEVICE_CONTROL2_16ms;
44
45 ret_val = igc_write_pcie_cap_reg(hw, PCIE_DEVICE_CONTROL2,
46 &pcie_devctl2);
47out:
48 /* disable completion timeout resend */
49 gcr &= ~IGC_GCR_CMPL_TMOUT_RESEND;
50
51 wr32(IGC_GCR, gcr);
52
53 return ret_val;
54}
55
56/**
Sasha Neftinab405612018-10-11 10:17:28 +030057 * igc_check_for_link_base - Check for link
58 * @hw: pointer to the HW structure
59 *
60 * If sgmii is enabled, then use the pcs register to determine link, otherwise
61 * use the generic interface for determining link.
62 */
63static s32 igc_check_for_link_base(struct igc_hw *hw)
64{
65 s32 ret_val = 0;
66
67 ret_val = igc_check_for_copper_link(hw);
68
69 return ret_val;
70}
71
72/**
Sasha Neftinc0071c72018-10-11 10:17:26 +030073 * igc_reset_hw_base - Reset hardware
74 * @hw: pointer to the HW structure
75 *
76 * This resets the hardware into a known state. This is a
77 * function pointer entry point called by the api module.
78 */
79static s32 igc_reset_hw_base(struct igc_hw *hw)
80{
81 s32 ret_val;
82 u32 ctrl;
83
84 /* Prevent the PCI-E bus from sticking if there is no TLP connection
85 * on the last TLP read/write transaction when MAC is reset.
86 */
87 ret_val = igc_disable_pcie_master(hw);
88 if (ret_val)
89 hw_dbg("PCI-E Master disable polling has failed.\n");
90
91 /* set the completion timeout for interface */
92 ret_val = igc_set_pcie_completion_timeout(hw);
93 if (ret_val)
94 hw_dbg("PCI-E Set completion timeout has failed.\n");
95
96 hw_dbg("Masking off all interrupts\n");
97 wr32(IGC_IMC, 0xffffffff);
98
99 wr32(IGC_RCTL, 0);
100 wr32(IGC_TCTL, IGC_TCTL_PSP);
101 wrfl();
102
103 usleep_range(10000, 20000);
104
105 ctrl = rd32(IGC_CTRL);
106
107 hw_dbg("Issuing a global reset to MAC\n");
108 wr32(IGC_CTRL, ctrl | IGC_CTRL_RST);
109
110 ret_val = igc_get_auto_rd_done(hw);
111 if (ret_val) {
112 /* When auto config read does not complete, do not
113 * return with an error. This can happen in situations
114 * where there is no eeprom and prevents getting link.
115 */
116 hw_dbg("Auto Read Done did not complete\n");
117 }
118
119 /* Clear any pending interrupt events. */
120 wr32(IGC_IMC, 0xffffffff);
121 rd32(IGC_ICR);
122
123 return ret_val;
124}
125
126/**
Sasha Neftin55868382018-10-11 10:17:31 +0300127 * igc_get_phy_id_base - Retrieve PHY addr and id
128 * @hw: pointer to the HW structure
129 *
130 * Retrieves the PHY address and ID for both PHY's which do and do not use
131 * sgmi interface.
132 */
133static s32 igc_get_phy_id_base(struct igc_hw *hw)
134{
135 s32 ret_val = 0;
136
137 ret_val = igc_get_phy_id(hw);
138
139 return ret_val;
140}
141
142/**
Sasha Neftinab405612018-10-11 10:17:28 +0300143 * igc_init_nvm_params_base - Init NVM func ptrs.
144 * @hw: pointer to the HW structure
145 */
146static s32 igc_init_nvm_params_base(struct igc_hw *hw)
147{
148 struct igc_nvm_info *nvm = &hw->nvm;
149 u32 eecd = rd32(IGC_EECD);
150 u16 size;
151
152 size = (u16)((eecd & IGC_EECD_SIZE_EX_MASK) >>
153 IGC_EECD_SIZE_EX_SHIFT);
154
155 /* Added to a constant, "size" becomes the left-shift value
156 * for setting word_size.
157 */
158 size += NVM_WORD_SIZE_BASE_SHIFT;
159
160 /* Just in case size is out of range, cap it to the largest
161 * EEPROM size supported
162 */
163 if (size > 15)
164 size = 15;
165
166 nvm->word_size = BIT(size);
167 nvm->opcode_bits = 8;
168 nvm->delay_usec = 1;
169
170 nvm->page_size = eecd & IGC_EECD_ADDR_BITS ? 32 : 8;
171 nvm->address_bits = eecd & IGC_EECD_ADDR_BITS ?
172 16 : 8;
173
174 if (nvm->word_size == BIT(15))
175 nvm->page_size = 128;
176
177 return 0;
178}
179
180/**
Sasha Neftin4eb80802018-10-11 10:17:34 +0300181 * igc_setup_copper_link_base - Configure copper link settings
182 * @hw: pointer to the HW structure
183 *
184 * Configures the link for auto-neg or forced speed and duplex. Then we check
185 * for link, once link is established calls to configure collision distance
186 * and flow control are called.
187 */
188static s32 igc_setup_copper_link_base(struct igc_hw *hw)
189{
190 s32 ret_val = 0;
191 u32 ctrl;
192
193 ctrl = rd32(IGC_CTRL);
194 ctrl |= IGC_CTRL_SLU;
195 ctrl &= ~(IGC_CTRL_FRCSPD | IGC_CTRL_FRCDPX);
196 wr32(IGC_CTRL, ctrl);
197
198 ret_val = igc_setup_copper_link(hw);
199
200 return ret_val;
201}
202
203/**
Sasha Neftinc0071c72018-10-11 10:17:26 +0300204 * igc_init_mac_params_base - Init MAC func ptrs.
205 * @hw: pointer to the HW structure
206 */
207static s32 igc_init_mac_params_base(struct igc_hw *hw)
208{
Sasha Neftinab405612018-10-11 10:17:28 +0300209 struct igc_dev_spec_base *dev_spec = &hw->dev_spec._base;
Sasha Neftinc0071c72018-10-11 10:17:26 +0300210 struct igc_mac_info *mac = &hw->mac;
211
212 /* Set mta register count */
213 mac->mta_reg_count = 128;
214 mac->rar_entry_count = IGC_RAR_ENTRIES;
215
216 /* reset */
217 mac->ops.reset_hw = igc_reset_hw_base;
218
219 mac->ops.acquire_swfw_sync = igc_acquire_swfw_sync_i225;
220 mac->ops.release_swfw_sync = igc_release_swfw_sync_i225;
221
Sasha Neftinab405612018-10-11 10:17:28 +0300222 /* Allow a single clear of the SW semaphore on I225 */
223 if (mac->type == igc_i225)
224 dev_spec->clear_semaphore_once = true;
225
Sasha Neftin4eb80802018-10-11 10:17:34 +0300226 /* physical interface link setup */
227 mac->ops.setup_physical_interface = igc_setup_copper_link_base;
228
Sasha Neftinc0071c72018-10-11 10:17:26 +0300229 return 0;
230}
231
Sasha Neftin55868382018-10-11 10:17:31 +0300232/**
233 * igc_init_phy_params_base - Init PHY func ptrs.
234 * @hw: pointer to the HW structure
235 */
236static s32 igc_init_phy_params_base(struct igc_hw *hw)
237{
238 struct igc_phy_info *phy = &hw->phy;
239 s32 ret_val = 0;
240 u32 ctrl_ext;
241
242 if (hw->phy.media_type != igc_media_type_copper) {
243 phy->type = igc_phy_none;
244 goto out;
245 }
246
247 phy->autoneg_mask = AUTONEG_ADVERTISE_SPEED_DEFAULT_2500;
248 phy->reset_delay_us = 100;
249
250 ctrl_ext = rd32(IGC_CTRL_EXT);
251
252 /* set lan id */
253 hw->bus.func = (rd32(IGC_STATUS) & IGC_STATUS_FUNC_MASK) >>
254 IGC_STATUS_FUNC_SHIFT;
255
256 /* Make sure the PHY is in a good state. Several people have reported
257 * firmware leaving the PHY's page select register set to something
258 * other than the default of zero, which causes the PHY ID read to
259 * access something other than the intended register.
260 */
261 ret_val = hw->phy.ops.reset(hw);
262 if (ret_val) {
263 hw_dbg("Error resetting the PHY.\n");
264 goto out;
265 }
266
267 ret_val = igc_get_phy_id_base(hw);
268 if (ret_val)
269 return ret_val;
270
Sasha Neftin4eb80802018-10-11 10:17:34 +0300271 igc_check_for_link_base(hw);
272
Sasha Neftin55868382018-10-11 10:17:31 +0300273 /* Verify phy id and set remaining function pointers */
274 switch (phy->id) {
275 case I225_I_PHY_ID:
276 phy->type = igc_phy_i225;
277 break;
278 default:
279 ret_val = -IGC_ERR_PHY;
280 goto out;
281 }
282
283out:
284 return ret_val;
285}
286
Sasha Neftinc0071c72018-10-11 10:17:26 +0300287static s32 igc_get_invariants_base(struct igc_hw *hw)
288{
Sasha Neftin4eb80802018-10-11 10:17:34 +0300289 struct igc_mac_info *mac = &hw->mac;
Sasha Neftinc0071c72018-10-11 10:17:26 +0300290 u32 link_mode = 0;
291 u32 ctrl_ext = 0;
292 s32 ret_val = 0;
293
Sasha Neftin4eb80802018-10-11 10:17:34 +0300294 switch (hw->device_id) {
295 case IGC_DEV_ID_I225_LM:
296 case IGC_DEV_ID_I225_V:
297 mac->type = igc_i225;
298 break;
299 default:
300 return -IGC_ERR_MAC_INIT;
301 }
302
303 hw->phy.media_type = igc_media_type_copper;
304
Sasha Neftinc0071c72018-10-11 10:17:26 +0300305 ctrl_ext = rd32(IGC_CTRL_EXT);
306 link_mode = ctrl_ext & IGC_CTRL_EXT_LINK_MODE_MASK;
307
308 /* mac initialization and operations */
309 ret_val = igc_init_mac_params_base(hw);
310 if (ret_val)
311 goto out;
312
Sasha Neftinab405612018-10-11 10:17:28 +0300313 /* NVM initialization */
314 ret_val = igc_init_nvm_params_base(hw);
315 switch (hw->mac.type) {
316 case igc_i225:
317 ret_val = igc_init_nvm_params_i225(hw);
318 break;
319 default:
320 break;
321 }
322
Sasha Neftin55868382018-10-11 10:17:31 +0300323 /* setup PHY parameters */
324 ret_val = igc_init_phy_params_base(hw);
Sasha Neftinab405612018-10-11 10:17:28 +0300325 if (ret_val)
326 goto out;
327
Sasha Neftinc0071c72018-10-11 10:17:26 +0300328out:
329 return ret_val;
330}
331
332/**
Sasha Neftin55868382018-10-11 10:17:31 +0300333 * igc_acquire_phy_base - Acquire rights to access PHY
334 * @hw: pointer to the HW structure
335 *
336 * Acquire access rights to the correct PHY. This is a
337 * function pointer entry point called by the api module.
338 */
339static s32 igc_acquire_phy_base(struct igc_hw *hw)
340{
341 u16 mask = IGC_SWFW_PHY0_SM;
342
343 return hw->mac.ops.acquire_swfw_sync(hw, mask);
344}
345
346/**
347 * igc_release_phy_base - Release rights to access PHY
348 * @hw: pointer to the HW structure
349 *
350 * A wrapper to release access rights to the correct PHY. This is a
351 * function pointer entry point called by the api module.
352 */
353static void igc_release_phy_base(struct igc_hw *hw)
354{
355 u16 mask = IGC_SWFW_PHY0_SM;
356
357 hw->mac.ops.release_swfw_sync(hw, mask);
358}
359
360/**
Sasha Neftinab405612018-10-11 10:17:28 +0300361 * igc_get_link_up_info_base - Get link speed/duplex info
362 * @hw: pointer to the HW structure
363 * @speed: stores the current speed
364 * @duplex: stores the current duplex
365 *
366 * This is a wrapper function, if using the serial gigabit media independent
367 * interface, use PCS to retrieve the link speed and duplex information.
368 * Otherwise, use the generic function to get the link speed and duplex info.
369 */
370static s32 igc_get_link_up_info_base(struct igc_hw *hw, u16 *speed,
371 u16 *duplex)
372{
373 s32 ret_val;
374
375 ret_val = igc_get_speed_and_duplex_copper(hw, speed, duplex);
376
377 return ret_val;
378}
379
380/**
Sasha Neftinc0071c72018-10-11 10:17:26 +0300381 * igc_init_hw_base - Initialize hardware
382 * @hw: pointer to the HW structure
383 *
384 * This inits the hardware readying it for operation.
385 */
386static s32 igc_init_hw_base(struct igc_hw *hw)
387{
388 struct igc_mac_info *mac = &hw->mac;
389 u16 i, rar_count = mac->rar_entry_count;
390 s32 ret_val = 0;
391
392 /* Setup the receive address */
393 igc_init_rx_addrs(hw, rar_count);
394
395 /* Zero out the Multicast HASH table */
396 hw_dbg("Zeroing the MTA\n");
397 for (i = 0; i < mac->mta_reg_count; i++)
398 array_wr32(IGC_MTA, i, 0);
399
400 /* Zero out the Unicast HASH table */
401 hw_dbg("Zeroing the UTA\n");
402 for (i = 0; i < mac->uta_reg_count; i++)
403 array_wr32(IGC_UTA, i, 0);
404
405 /* Setup link and flow control */
406 ret_val = igc_setup_link(hw);
407
408 /* Clear all of the statistics registers (clear on read). It is
409 * important that we do this after we have tried to establish link
410 * because the symbol error count will increment wildly if there
411 * is no link.
412 */
413 igc_clear_hw_cntrs_base(hw);
414
415 return ret_val;
416}
Sasha Neftin13b5b7f2018-10-11 10:17:19 +0300417
418/**
Sasha Neftinab405612018-10-11 10:17:28 +0300419 * igc_read_mac_addr_base - Read device MAC address
420 * @hw: pointer to the HW structure
421 */
422static s32 igc_read_mac_addr_base(struct igc_hw *hw)
423{
424 s32 ret_val = 0;
425
426 ret_val = igc_read_mac_addr(hw);
427
428 return ret_val;
429}
430
431/**
Sasha Neftin55868382018-10-11 10:17:31 +0300432 * igc_power_down_phy_copper_base - Remove link during PHY power down
433 * @hw: pointer to the HW structure
434 *
435 * In the case of a PHY power down to save power, or to turn off link during a
436 * driver unload, or wake on lan is not enabled, remove the link.
437 */
438void igc_power_down_phy_copper_base(struct igc_hw *hw)
439{
440 /* If the management interface is not enabled, then power down */
441 if (!(igc_enable_mng_pass_thru(hw) || igc_check_reset_block(hw)))
442 igc_power_down_phy_copper(hw);
443}
444
445/**
Sasha Neftin13b5b7f2018-10-11 10:17:19 +0300446 * igc_rx_fifo_flush_base - Clean rx fifo after Rx enable
447 * @hw: pointer to the HW structure
448 *
449 * After Rx enable, if manageability is enabled then there is likely some
450 * bad data at the start of the fifo and possibly in the DMA fifo. This
451 * function clears the fifos and flushes any packets that came in as rx was
452 * being enabled.
453 */
454void igc_rx_fifo_flush_base(struct igc_hw *hw)
455{
456 u32 rctl, rlpml, rxdctl[4], rfctl, temp_rctl, rx_enabled;
457 int i, ms_wait;
458
459 /* disable IPv6 options as per hardware errata */
460 rfctl = rd32(IGC_RFCTL);
461 rfctl |= IGC_RFCTL_IPV6_EX_DIS;
462 wr32(IGC_RFCTL, rfctl);
463
464 if (!(rd32(IGC_MANC) & IGC_MANC_RCV_TCO_EN))
465 return;
466
467 /* Disable all Rx queues */
468 for (i = 0; i < 4; i++) {
469 rxdctl[i] = rd32(IGC_RXDCTL(i));
470 wr32(IGC_RXDCTL(i),
471 rxdctl[i] & ~IGC_RXDCTL_QUEUE_ENABLE);
472 }
473 /* Poll all queues to verify they have shut down */
474 for (ms_wait = 0; ms_wait < 10; ms_wait++) {
475 usleep_range(1000, 2000);
476 rx_enabled = 0;
477 for (i = 0; i < 4; i++)
478 rx_enabled |= rd32(IGC_RXDCTL(i));
479 if (!(rx_enabled & IGC_RXDCTL_QUEUE_ENABLE))
480 break;
481 }
482
483 if (ms_wait == 10)
484 pr_debug("Queue disable timed out after 10ms\n");
485
486 /* Clear RLPML, RCTL.SBP, RFCTL.LEF, and set RCTL.LPE so that all
487 * incoming packets are rejected. Set enable and wait 2ms so that
488 * any packet that was coming in as RCTL.EN was set is flushed
489 */
490 wr32(IGC_RFCTL, rfctl & ~IGC_RFCTL_LEF);
491
492 rlpml = rd32(IGC_RLPML);
493 wr32(IGC_RLPML, 0);
494
495 rctl = rd32(IGC_RCTL);
496 temp_rctl = rctl & ~(IGC_RCTL_EN | IGC_RCTL_SBP);
497 temp_rctl |= IGC_RCTL_LPE;
498
499 wr32(IGC_RCTL, temp_rctl);
500 wr32(IGC_RCTL, temp_rctl | IGC_RCTL_EN);
501 wrfl();
502 usleep_range(2000, 3000);
503
504 /* Enable Rx queues that were previously enabled and restore our
505 * previous state
506 */
507 for (i = 0; i < 4; i++)
508 wr32(IGC_RXDCTL(i), rxdctl[i]);
509 wr32(IGC_RCTL, rctl);
510 wrfl();
511
512 wr32(IGC_RLPML, rlpml);
513 wr32(IGC_RFCTL, rfctl);
514
515 /* Flush receive errors generated by workaround */
516 rd32(IGC_ROC);
517 rd32(IGC_RNBC);
518 rd32(IGC_MPC);
519}
Sasha Neftinc0071c72018-10-11 10:17:26 +0300520
521static struct igc_mac_operations igc_mac_ops_base = {
522 .init_hw = igc_init_hw_base,
Sasha Neftinab405612018-10-11 10:17:28 +0300523 .check_for_link = igc_check_for_link_base,
524 .rar_set = igc_rar_set,
525 .read_mac_addr = igc_read_mac_addr_base,
526 .get_speed_and_duplex = igc_get_link_up_info_base,
Sasha Neftinc0071c72018-10-11 10:17:26 +0300527};
528
Sasha Neftin55868382018-10-11 10:17:31 +0300529static const struct igc_phy_operations igc_phy_ops_base = {
530 .acquire = igc_acquire_phy_base,
531 .release = igc_release_phy_base,
532 .reset = igc_phy_hw_reset,
533 .read_reg = igc_read_phy_reg_gpy,
534 .write_reg = igc_write_phy_reg_gpy,
535};
536
Sasha Neftinc0071c72018-10-11 10:17:26 +0300537const struct igc_info igc_base_info = {
538 .get_invariants = igc_get_invariants_base,
539 .mac_ops = &igc_mac_ops_base,
Sasha Neftin55868382018-10-11 10:17:31 +0300540 .phy_ops = &igc_phy_ops_base,
Sasha Neftinc0071c72018-10-11 10:17:26 +0300541};