xref: /openbsd/sys/dev/pci/igc_phy.c (revision 73471bf0)
1 /*	$OpenBSD: igc_phy.c,v 1.1 2021/10/31 14:52:57 patrick Exp $	*/
2 /*-
3  * Copyright 2021 Intel Corp
4  * Copyright 2021 Rubicon Communications, LLC (Netgate)
5  * SPDX-License-Identifier: BSD-3-Clause
6  */
7 
8 #include <dev/pci/igc_api.h>
9 
10 /**
11  *  igc_init_phy_ops_generic - Initialize PHY function pointers
12  *  @hw: pointer to the HW structure
13  *
14  *  Setups up the function pointers to no-op functions
15  **/
16 void
17 igc_init_phy_ops_generic(struct igc_hw *hw)
18 {
19 	struct igc_phy_info *phy = &hw->phy;
20 	DEBUGFUNC("igc_init_phy_ops_generic");
21 
22 	/* Initialize function pointers */
23 	phy->ops.init_params = igc_null_ops_generic;
24 	phy->ops.acquire = igc_null_ops_generic;
25 	phy->ops.check_reset_block = igc_null_ops_generic;
26 	phy->ops.commit = igc_null_ops_generic;
27 	phy->ops.force_speed_duplex = igc_null_ops_generic;
28 	phy->ops.get_info = igc_null_ops_generic;
29 	phy->ops.set_page = igc_null_set_page;
30 	phy->ops.read_reg = igc_null_read_reg;
31 	phy->ops.read_reg_locked = igc_null_read_reg;
32 	phy->ops.read_reg_page = igc_null_read_reg;
33 	phy->ops.release = igc_null_phy_generic;
34 	phy->ops.reset = igc_null_ops_generic;
35 	phy->ops.set_d0_lplu_state = igc_null_lplu_state;
36 	phy->ops.set_d3_lplu_state = igc_null_lplu_state;
37 	phy->ops.write_reg = igc_null_write_reg;
38 	phy->ops.write_reg_locked = igc_null_write_reg;
39 	phy->ops.write_reg_page = igc_null_write_reg;
40 	phy->ops.power_up = igc_null_phy_generic;
41 	phy->ops.power_down = igc_null_phy_generic;
42 }
43 
44 /**
45  *  igc_null_set_page - No-op function, return 0
46  *  @hw: pointer to the HW structure
47  *  @data: dummy variable
48  **/
49 int
50 igc_null_set_page(struct igc_hw IGC_UNUSEDARG *hw, uint16_t IGC_UNUSEDARG data)
51 {
52 	DEBUGFUNC("igc_null_set_page");
53 	return IGC_SUCCESS;
54 }
55 
56 /**
57  *  igc_null_read_reg - No-op function, return 0
58  *  @hw: pointer to the HW structure
59  *  @offset: dummy variable
60  *  @data: dummy variable
61  **/
62 int
63 igc_null_read_reg(struct igc_hw IGC_UNUSEDARG *hw,
64     uint32_t IGC_UNUSEDARG offset, uint16_t IGC_UNUSEDARG *data)
65 {
66 	DEBUGFUNC("igc_null_read_reg");
67 	return IGC_SUCCESS;
68 }
69 
70 /**
71  *  igc_null_phy_generic - No-op function, return void
72  *  @hw: pointer to the HW structure
73  **/
74 void
75 igc_null_phy_generic(struct igc_hw IGC_UNUSEDARG *hw)
76 {
77 	DEBUGFUNC("igc_null_phy_generic");
78 	return;
79 }
80 
81 /**
82  *  igc_null_lplu_state - No-op function, return 0
83  *  @hw: pointer to the HW structure
84  *  @active: dummy variable
85  **/
86 int
87 igc_null_lplu_state(struct igc_hw IGC_UNUSEDARG *hw, bool IGC_UNUSEDARG active)
88 {
89 	DEBUGFUNC("igc_null_lplu_state");
90 	return IGC_SUCCESS;
91 }
92 
93 /**
94  *  igc_null_write_reg - No-op function, return 0
95  *  @hw: pointer to the HW structure
96  *  @offset: dummy variable
97  *  @data: dummy variable
98  **/
99 int
100 igc_null_write_reg(struct igc_hw IGC_UNUSEDARG *hw,
101     uint32_t IGC_UNUSEDARG offset, uint16_t IGC_UNUSEDARG data)
102 {
103 	DEBUGFUNC("igc_null_write_reg");
104 	return IGC_SUCCESS;
105 }
106 
107 /**
108  *  igc_check_reset_block_generic - Check if PHY reset is blocked
109  *  @hw: pointer to the HW structure
110  *
111  *  Read the PHY management control register and check whether a PHY reset
112  *  is blocked.  If a reset is not blocked return IGC_SUCCESS, otherwise
113  *  return IGC_BLK_PHY_RESET (12).
114  **/
115 int
116 igc_check_reset_block_generic(struct igc_hw *hw)
117 {
118 	uint32_t manc;
119 
120 	DEBUGFUNC("igc_check_reset_block");
121 
122 	manc = IGC_READ_REG(hw, IGC_MANC);
123 
124 	return (manc & IGC_MANC_BLK_PHY_RST_ON_IDE) ?
125 	    IGC_BLK_PHY_RESET : IGC_SUCCESS;
126 }
127 
128 /**
129  *  igc_get_phy_id - Retrieve the PHY ID and revision
130  *  @hw: pointer to the HW structure
131  *
132  *  Reads the PHY registers and stores the PHY ID and possibly the PHY
133  *  revision in the hardware structure.
134  **/
135 int
136 igc_get_phy_id(struct igc_hw *hw)
137 {
138 	struct igc_phy_info *phy = &hw->phy;
139 	uint16_t phy_id;
140 	int ret_val = IGC_SUCCESS;
141 
142 	DEBUGFUNC("igc_get_phy_id");
143 
144 	if (!phy->ops.read_reg)
145 		return IGC_SUCCESS;
146 
147 	ret_val = phy->ops.read_reg(hw, PHY_ID1, &phy_id);
148 	if (ret_val)
149 		return ret_val;
150 
151 	phy->id = (uint32_t)(phy_id << 16);
152 	DELAY(20);
153 	ret_val = phy->ops.read_reg(hw, PHY_ID2, &phy_id);
154 	if (ret_val)
155 		return ret_val;
156 
157 	phy->id |= (uint32_t)(phy_id & PHY_REVISION_MASK);
158 	phy->revision = (uint32_t)(phy_id & ~PHY_REVISION_MASK);
159 
160 
161 	return IGC_SUCCESS;
162 }
163 
164 /**
165  *  igc_read_phy_reg_mdic - Read MDI control register
166  *  @hw: pointer to the HW structure
167  *  @offset: register offset to be read
168  *  @data: pointer to the read data
169  *
170  *  Reads the MDI control register in the PHY at offset and stores the
171  *  information read to data.
172  **/
173 int
174 igc_read_phy_reg_mdic(struct igc_hw *hw, uint32_t offset, uint16_t *data)
175 {
176 	struct igc_phy_info *phy = &hw->phy;
177 	uint32_t i, mdic = 0;
178 
179 	DEBUGFUNC("igc_read_phy_reg_mdic");
180 
181 	if (offset > MAX_PHY_REG_ADDRESS) {
182 		DEBUGOUT1("PHY Address %d is out of range\n", offset);
183 		return -IGC_ERR_PARAM;
184 	}
185 
186 	/* Set up Op-code, Phy Address, and register offset in the MDI
187 	 * Control register.  The MAC will take care of interfacing with the
188 	 * PHY to retrieve the desired data.
189 	 */
190 	mdic = ((offset << IGC_MDIC_REG_SHIFT) |
191 	    (phy->addr << IGC_MDIC_PHY_SHIFT) | (IGC_MDIC_OP_READ));
192 
193 	IGC_WRITE_REG(hw, IGC_MDIC, mdic);
194 
195 	/* Poll the ready bit to see if the MDI read completed
196 	 * Increasing the time out as testing showed failures with
197 	 * the lower time out
198 	 */
199 	for (i = 0; i < (IGC_GEN_POLL_TIMEOUT * 3); i++) {
200 		DELAY(50);
201 		mdic = IGC_READ_REG(hw, IGC_MDIC);
202 		if (mdic & IGC_MDIC_READY)
203 			break;
204 	}
205 	if (!(mdic & IGC_MDIC_READY)) {
206 		DEBUGOUT("MDI Read did not complete\n");
207 		return -IGC_ERR_PHY;
208 	}
209 	if (mdic & IGC_MDIC_ERROR) {
210 		DEBUGOUT("MDI Error\n");
211 		return -IGC_ERR_PHY;
212 	}
213 	if (((mdic & IGC_MDIC_REG_MASK) >> IGC_MDIC_REG_SHIFT) != offset) {
214 		DEBUGOUT2("MDI Read offset error - requested %d, returned %d\n",
215 		    offset, (mdic & IGC_MDIC_REG_MASK) >> IGC_MDIC_REG_SHIFT);
216 		return -IGC_ERR_PHY;
217 	}
218 	*data = (uint16_t)mdic;
219 
220 	return IGC_SUCCESS;
221 }
222 
223 /**
224  *  igc_write_phy_reg_mdic - Write MDI control register
225  *  @hw: pointer to the HW structure
226  *  @offset: register offset to write to
227  *  @data: data to write to register at offset
228  *
229  *  Writes data to MDI control register in the PHY at offset.
230  **/
231 int
232 igc_write_phy_reg_mdic(struct igc_hw *hw, uint32_t offset, uint16_t data)
233 {
234 	struct igc_phy_info *phy = &hw->phy;
235 	uint32_t i, mdic = 0;
236 
237 	DEBUGFUNC("igc_write_phy_reg_mdic");
238 
239 	if (offset > MAX_PHY_REG_ADDRESS) {
240 		DEBUGOUT1("PHY Address %d is out of range\n", offset);
241 		return -IGC_ERR_PARAM;
242 	}
243 
244 	/* Set up Op-code, Phy Address, and register offset in the MDI
245 	 * Control register.  The MAC will take care of interfacing with the
246 	 * PHY to retrieve the desired data.
247 	 */
248 	mdic = (((uint32_t)data) | (offset << IGC_MDIC_REG_SHIFT) |
249 	    (phy->addr << IGC_MDIC_PHY_SHIFT) | (IGC_MDIC_OP_WRITE));
250 
251 	IGC_WRITE_REG(hw, IGC_MDIC, mdic);
252 
253 	/* Poll the ready bit to see if the MDI read completed
254 	 * Increasing the time out as testing showed failures with
255 	 * the lower time out
256 	 */
257 	for (i = 0; i < (IGC_GEN_POLL_TIMEOUT * 3); i++) {
258 		DELAY(50);
259 		mdic = IGC_READ_REG(hw, IGC_MDIC);
260 		if (mdic & IGC_MDIC_READY)
261 			break;
262 	}
263 	if (!(mdic & IGC_MDIC_READY)) {
264 		DEBUGOUT("MDI Write did not complete\n");
265 		return -IGC_ERR_PHY;
266 	}
267 	if (mdic & IGC_MDIC_ERROR) {
268 		DEBUGOUT("MDI Error\n");
269 		return -IGC_ERR_PHY;
270 	}
271 	if (((mdic & IGC_MDIC_REG_MASK) >> IGC_MDIC_REG_SHIFT) != offset)
272 		return -IGC_ERR_PHY;
273 
274 	return IGC_SUCCESS;
275 }
276 
277 /**
278  *  igc_phy_setup_autoneg - Configure PHY for auto-negotiation
279  *  @hw: pointer to the HW structure
280  *
281  *  Reads the MII auto-neg advertisement register and/or the 1000T control
282  *  register and if the PHY is already setup for auto-negotiation, then
283  *  return successful.  Otherwise, setup advertisement and flow control to
284  *  the appropriate values for the wanted auto-negotiation.
285  **/
286 int
287 igc_phy_setup_autoneg(struct igc_hw *hw)
288 {
289 	struct igc_phy_info *phy = &hw->phy;
290 	uint16_t mii_autoneg_adv_reg;
291 	uint16_t mii_1000t_ctrl_reg = 0;
292 	uint16_t aneg_multigbt_an_ctrl = 0;
293 	int ret_val;
294 
295 	DEBUGFUNC("igc_phy_setup_autoneg");
296 
297 	phy->autoneg_advertised &= phy->autoneg_mask;
298 
299 	/* Read the MII Auto-Neg Advertisement Register (Address 4). */
300 	ret_val = phy->ops.read_reg(hw, PHY_AUTONEG_ADV, &mii_autoneg_adv_reg);
301 	if (ret_val)
302 		return ret_val;
303 
304 	if (phy->autoneg_mask & ADVERTISE_1000_FULL) {
305 		/* Read the MII 1000Base-T Control Register (Address 9). */
306 		ret_val = phy->ops.read_reg(hw, PHY_1000T_CTRL,
307 		    &mii_1000t_ctrl_reg);
308 		if (ret_val)
309 			return ret_val;
310 	}
311 
312 	if ((phy->autoneg_mask & ADVERTISE_2500_FULL) &&
313 	    hw->phy.id == I225_I_PHY_ID) {
314 	/* Read the MULTI GBT AN Control Register - reg 7.32 */
315 		ret_val = phy->ops.read_reg(hw, (STANDARD_AN_REG_MASK <<
316 		    MMD_DEVADDR_SHIFT) | ANEG_MULTIGBT_AN_CTRL,
317 		    &aneg_multigbt_an_ctrl);
318 		if (ret_val)
319 			return ret_val;
320 	}
321 
322 	/* Need to parse both autoneg_advertised and fc and set up
323 	 * the appropriate PHY registers.  First we will parse for
324 	 * autoneg_advertised software override.  Since we can advertise
325 	 * a plethora of combinations, we need to check each bit
326 	 * individually.
327 	 */
328 
329 	/* First we clear all the 10/100 mb speed bits in the Auto-Neg
330 	 * Advertisement Register (Address 4) and the 1000 mb speed bits in
331 	 * the  1000Base-T Control Register (Address 9).
332 	 */
333 	mii_autoneg_adv_reg &= ~(NWAY_AR_100TX_FD_CAPS | NWAY_AR_100TX_HD_CAPS |
334 	    NWAY_AR_10T_FD_CAPS | NWAY_AR_10T_HD_CAPS);
335 	mii_1000t_ctrl_reg &= ~(CR_1000T_HD_CAPS | CR_1000T_FD_CAPS);
336 
337 	DEBUGOUT1("autoneg_advertised %x\n", phy->autoneg_advertised);
338 
339 	/* Do we want to advertise 10 Mb Half Duplex? */
340 	if (phy->autoneg_advertised & ADVERTISE_10_HALF) {
341 		DEBUGOUT("Advertise 10mb Half duplex\n");
342 		mii_autoneg_adv_reg |= NWAY_AR_10T_HD_CAPS;
343 	}
344 
345 	/* Do we want to advertise 10 Mb Full Duplex? */
346 	if (phy->autoneg_advertised & ADVERTISE_10_FULL) {
347 		DEBUGOUT("Advertise 10mb Full duplex\n");
348 		mii_autoneg_adv_reg |= NWAY_AR_10T_FD_CAPS;
349 	}
350 
351 	/* Do we want to advertise 100 Mb Half Duplex? */
352 	if (phy->autoneg_advertised & ADVERTISE_100_HALF) {
353 		DEBUGOUT("Advertise 100mb Half duplex\n");
354 		mii_autoneg_adv_reg |= NWAY_AR_100TX_HD_CAPS;
355 	}
356 
357 	/* Do we want to advertise 100 Mb Full Duplex? */
358 	if (phy->autoneg_advertised & ADVERTISE_100_FULL) {
359 		DEBUGOUT("Advertise 100mb Full duplex\n");
360 		mii_autoneg_adv_reg |= NWAY_AR_100TX_FD_CAPS;
361 	}
362 
363 	/* We do not allow the Phy to advertise 1000 Mb Half Duplex */
364 	if (phy->autoneg_advertised & ADVERTISE_1000_HALF)
365 		DEBUGOUT("Advertise 1000mb Half duplex request denied!\n");
366 
367 	/* Do we want to advertise 1000 Mb Full Duplex? */
368 	if (phy->autoneg_advertised & ADVERTISE_1000_FULL) {
369 		DEBUGOUT("Advertise 1000mb Full duplex\n");
370 		mii_1000t_ctrl_reg |= CR_1000T_FD_CAPS;
371 	}
372 
373 	/* We do not allow the Phy to advertise 2500 Mb Half Duplex */
374 	if (phy->autoneg_advertised & ADVERTISE_2500_HALF)
375 		DEBUGOUT("Advertise 2500mb Half duplex request denied!\n");
376 
377 	/* Do we want to advertise 2500 Mb Full Duplex? */
378 	if (phy->autoneg_advertised & ADVERTISE_2500_FULL) {
379 		DEBUGOUT("Advertise 2500mb Full duplex\n");
380 		aneg_multigbt_an_ctrl |= CR_2500T_FD_CAPS;
381 	} else
382 		aneg_multigbt_an_ctrl &= ~CR_2500T_FD_CAPS;
383 
384 	/* Check for a software override of the flow control settings, and
385 	 * setup the PHY advertisement registers accordingly.  If
386 	 * auto-negotiation is enabled, then software will have to set the
387 	 * "PAUSE" bits to the correct value in the Auto-Negotiation
388 	 * Advertisement Register (PHY_AUTONEG_ADV) and re-start auto-
389 	 * negotiation.
390 	 *
391 	 * The possible values of the "fc" parameter are:
392 	 *      0:  Flow control is completely disabled
393 	 *      1:  Rx flow control is enabled (we can receive pause frames
394 	 *          but not send pause frames).
395 	 *      2:  Tx flow control is enabled (we can send pause frames
396 	 *          but we do not support receiving pause frames).
397 	 *      3:  Both Rx and Tx flow control (symmetric) are enabled.
398 	 *  other:  No software override.  The flow control configuration
399 	 *          in the EEPROM is used.
400 	 */
401 	switch (hw->fc.current_mode) {
402 	case igc_fc_none:
403 		/* Flow control (Rx & Tx) is completely disabled by a
404 		 * software over-ride.
405 		 */
406 		mii_autoneg_adv_reg &= ~(NWAY_AR_ASM_DIR | NWAY_AR_PAUSE);
407 		break;
408 	case igc_fc_rx_pause:
409 		/* Rx Flow control is enabled, and Tx Flow control is
410 		 * disabled, by a software over-ride.
411 		 *
412 		 * Since there really isn't a way to advertise that we are
413 		 * capable of Rx Pause ONLY, we will advertise that we
414 		 * support both symmetric and asymmetric Rx PAUSE.  Later
415 		 * (in igc_config_fc_after_link_up) we will disable the
416 		 * hw's ability to send PAUSE frames.
417 		 */
418 		mii_autoneg_adv_reg |= (NWAY_AR_ASM_DIR | NWAY_AR_PAUSE);
419 		break;
420 	case igc_fc_tx_pause:
421 		/* Tx Flow control is enabled, and Rx Flow control is
422 		 * disabled, by a software over-ride.
423 		 */
424 		mii_autoneg_adv_reg |= NWAY_AR_ASM_DIR;
425 		mii_autoneg_adv_reg &= ~NWAY_AR_PAUSE;
426 		break;
427 	case igc_fc_full:
428 		/* Flow control (both Rx and Tx) is enabled by a software
429 		 * over-ride.
430 		 */
431 		mii_autoneg_adv_reg |= (NWAY_AR_ASM_DIR | NWAY_AR_PAUSE);
432 		break;
433 	default:
434 		DEBUGOUT("Flow control param set incorrectly\n");
435 		return -IGC_ERR_CONFIG;
436 	}
437 
438 	ret_val = phy->ops.write_reg(hw, PHY_AUTONEG_ADV, mii_autoneg_adv_reg);
439 	if (ret_val)
440 		return ret_val;
441 
442 	DEBUGOUT1("Auto-Neg Advertising %x\n", mii_autoneg_adv_reg);
443 
444 	if (phy->autoneg_mask & ADVERTISE_1000_FULL)
445 		ret_val = phy->ops.write_reg(hw, PHY_1000T_CTRL,
446 		    mii_1000t_ctrl_reg);
447 
448 	if ((phy->autoneg_mask & ADVERTISE_2500_FULL) &&
449 	    hw->phy.id == I225_I_PHY_ID)
450 		ret_val = phy->ops.write_reg(hw,
451 		    (STANDARD_AN_REG_MASK << MMD_DEVADDR_SHIFT) |
452 		    ANEG_MULTIGBT_AN_CTRL, aneg_multigbt_an_ctrl);
453 
454 	return ret_val;
455 }
456 
457 /**
458  *  igc_copper_link_autoneg - Setup/Enable autoneg for copper link
459  *  @hw: pointer to the HW structure
460  *
461  *  Performs initial bounds checking on autoneg advertisement parameter, then
462  *  configure to advertise the full capability.  Setup the PHY to autoneg
463  *  and restart the negotiation process between the link partner.  If
464  *  autoneg_wait_to_complete, then wait for autoneg to complete before exiting.
465  **/
466 int
467 igc_copper_link_autoneg(struct igc_hw *hw)
468 {
469 	struct igc_phy_info *phy = &hw->phy;
470 	uint16_t phy_ctrl;
471 	int ret_val;
472 
473 	DEBUGFUNC("igc_copper_link_autoneg");
474 
475 	/* Perform some bounds checking on the autoneg advertisement
476 	 * parameter.
477 	 */
478 	phy->autoneg_advertised &= phy->autoneg_mask;
479 
480 	/* If autoneg_advertised is zero, we assume it was not defaulted
481 	 * by the calling code so we set to advertise full capability.
482 	 */
483 	if (!phy->autoneg_advertised)
484 		phy->autoneg_advertised = phy->autoneg_mask;
485 
486 	DEBUGOUT("Reconfiguring auto-neg advertisement params\n");
487 	ret_val = igc_phy_setup_autoneg(hw);
488 	if (ret_val) {
489 		DEBUGOUT("Error Setting up Auto-Negotiation\n");
490 		return ret_val;
491 	}
492 	DEBUGOUT("Restarting Auto-Neg\n");
493 
494 	/* Restart auto-negotiation by setting the Auto Neg Enable bit and
495 	 * the Auto Neg Restart bit in the PHY control register.
496 	 */
497 	ret_val = phy->ops.read_reg(hw, PHY_CONTROL, &phy_ctrl);
498 	if (ret_val)
499 		return ret_val;
500 
501 	phy_ctrl |= (MII_CR_AUTO_NEG_EN | MII_CR_RESTART_AUTO_NEG);
502 	ret_val = phy->ops.write_reg(hw, PHY_CONTROL, phy_ctrl);
503 	if (ret_val)
504 		return ret_val;
505 
506 	/* Does the user want to wait for Auto-Neg to complete here, or
507 	 * check at a later time (for example, callback routine).
508 	 */
509 	if (phy->autoneg_wait_to_complete) {
510 		ret_val = igc_wait_autoneg(hw);
511 		if (ret_val)
512 			return ret_val;
513 	}
514 
515 	hw->mac.get_link_status = true;
516 
517 	return ret_val;
518 }
519 
520 /**
521  *  igc_setup_copper_link_generic - Configure copper link settings
522  *  @hw: pointer to the HW structure
523  *
524  *  Calls the appropriate function to configure the link for auto-neg or forced
525  *  speed and duplex.  Then we check for link, once link is established calls
526  *  to configure collision distance and flow control are called.  If link is
527  *  not established, we return -IGC_ERR_PHY (-2).
528  **/
529 int
530 igc_setup_copper_link_generic(struct igc_hw *hw)
531 {
532 	int ret_val;
533 	bool link;
534 
535 	DEBUGFUNC("igc_setup_copper_link_generic");
536 
537 	if (hw->mac.autoneg) {
538 		/* Setup autoneg and flow control advertisement and perform
539 		 * autonegotiation.
540 		 */
541 		ret_val = igc_copper_link_autoneg(hw);
542 		if (ret_val)
543 			return ret_val;
544 	} else {
545 		/* PHY will be set to 10H, 10F, 100H or 100F
546 		 * depending on user settings.
547 		 */
548 		DEBUGOUT("Forcing Speed and Duplex\n");
549 		ret_val = hw->phy.ops.force_speed_duplex(hw);
550 		if (ret_val) {
551 			DEBUGOUT("Error Forcing Speed and Duplex\n");
552 			return ret_val;
553 		}
554 	}
555 
556 	/* Check link status. Wait up to 100 microseconds for link to become
557 	 * valid.
558 	 */
559 	ret_val = igc_phy_has_link_generic(hw, COPPER_LINK_UP_LIMIT, 10,
560 	    &link);
561 	if (ret_val)
562 		return ret_val;
563 
564 	if (link) {
565 		DEBUGOUT("Valid link established!!!\n");
566 		hw->mac.ops.config_collision_dist(hw);
567 		ret_val = igc_config_fc_after_link_up_generic(hw);
568 	} else
569 		DEBUGOUT("Unable to establish link!!!\n");
570 
571 	return ret_val;
572 }
573 
574 /**
575  *  igc_check_downshift_generic - Checks whether a downshift in speed occurred
576  *  @hw: pointer to the HW structure
577  *
578  *  Success returns 0, Failure returns 1
579  *
580  *  A downshift is detected by querying the PHY link health.
581  **/
582 int
583 igc_check_downshift_generic(struct igc_hw *hw)
584 {
585 	struct igc_phy_info *phy = &hw->phy;
586 	int ret_val;
587 
588 	DEBUGFUNC("igc_check_downshift_generic");
589 
590 	switch (phy->type) {
591 	case igc_phy_i225:
592 	default:
593 		/* speed downshift not supported */
594 		phy->speed_downgraded = false;
595 		return IGC_SUCCESS;
596 	}
597 
598 	return ret_val;
599 }
600 
601 /**
602  *  igc_wait_autoneg - Wait for auto-neg completion
603  *  @hw: pointer to the HW structure
604  *
605  *  Waits for auto-negotiation to complete or for the auto-negotiation time
606  *  limit to expire, which ever happens first.
607  **/
608 int
609 igc_wait_autoneg(struct igc_hw *hw)
610 {
611 	uint16_t i, phy_status;
612 	int ret_val = IGC_SUCCESS;
613 
614 	DEBUGFUNC("igc_wait_autoneg");
615 
616 	if (!hw->phy.ops.read_reg)
617 		return IGC_SUCCESS;
618 
619 	/* Break after autoneg completes or PHY_AUTO_NEG_LIMIT expires. */
620 	for (i = PHY_AUTO_NEG_LIMIT; i > 0; i--) {
621 		ret_val = hw->phy.ops.read_reg(hw, PHY_STATUS, &phy_status);
622 		if (ret_val)
623 			break;
624 		ret_val = hw->phy.ops.read_reg(hw, PHY_STATUS, &phy_status);
625 		if (ret_val)
626 			break;
627 		if (phy_status & MII_SR_AUTONEG_COMPLETE)
628 			break;
629 		msec_delay(100);
630 	}
631 
632 	/* PHY_AUTO_NEG_TIME expiration doesn't guarantee auto-negotiation
633 	 * has completed.
634 	 */
635 	return ret_val;
636 }
637 
638 /**
639  *  igc_phy_has_link_generic - Polls PHY for link
640  *  @hw: pointer to the HW structure
641  *  @iterations: number of times to poll for link
642  *  @usec_interval: delay between polling attempts
643  *  @success: pointer to whether polling was successful or not
644  *
645  *  Polls the PHY status register for link, 'iterations' number of times.
646  **/
647 int
648 igc_phy_has_link_generic(struct igc_hw *hw, uint32_t iterations,
649     uint32_t usec_interval, bool *success)
650 {
651 	uint16_t i, phy_status;
652 	int ret_val = IGC_SUCCESS;
653 
654 	DEBUGFUNC("igc_phy_has_link_generic");
655 
656 	if (!hw->phy.ops.read_reg)
657 		return IGC_SUCCESS;
658 
659 	for (i = 0; i < iterations; i++) {
660 		/* Some PHYs require the PHY_STATUS register to be read
661 		 * twice due to the link bit being sticky.  No harm doing
662 		 * it across the board.
663 		 */
664 		ret_val = hw->phy.ops.read_reg(hw, PHY_STATUS, &phy_status);
665 		if (ret_val) {
666 			/* If the first read fails, another entity may have
667 			 * ownership of the resources, wait and try again to
668 			 * see if they have relinquished the resources yet.
669 			 */
670 			if (usec_interval >= 1000)
671 				msec_delay(usec_interval/1000);
672 			else
673 				DELAY(usec_interval);
674 		}
675 		ret_val = hw->phy.ops.read_reg(hw, PHY_STATUS, &phy_status);
676 		if (ret_val)
677 			break;
678 		if (phy_status & MII_SR_LINK_STATUS)
679 			break;
680 		if (usec_interval >= 1000)
681 			msec_delay(usec_interval/1000);
682 		else
683 			DELAY(usec_interval);
684 	}
685 
686 	*success = (i < iterations);
687 
688 	return ret_val;
689 }
690 
691 /**
692  *  igc_phy_sw_reset_generic - PHY software reset
693  *  @hw: pointer to the HW structure
694  *
695  *  Does a software reset of the PHY by reading the PHY control register and
696  *  setting/write the control register reset bit to the PHY.
697  **/
698 int
699 igc_phy_sw_reset_generic(struct igc_hw *hw)
700 {
701 	uint16_t phy_ctrl;
702 	int ret_val;
703 
704 	DEBUGFUNC("igc_phy_sw_reset_generic");
705 
706 	if (!hw->phy.ops.read_reg)
707 		return IGC_SUCCESS;
708 
709 	ret_val = hw->phy.ops.read_reg(hw, PHY_CONTROL, &phy_ctrl);
710 	if (ret_val)
711 		return ret_val;
712 
713 	phy_ctrl |= MII_CR_RESET;
714 	ret_val = hw->phy.ops.write_reg(hw, PHY_CONTROL, phy_ctrl);
715 	if (ret_val)
716 		return ret_val;
717 
718 	DELAY(1);
719 
720 	return ret_val;
721 }
722 
723 /**
724  * igc_power_up_phy_copper - Restore copper link in case of PHY power down
725  * @hw: pointer to the HW structure
726  *
727  * In the case of a PHY power down to save power, or to turn off link during a
728  * driver unload, or wake on lan is not enabled, restore the link to previous
729  * settings.
730  **/
731 void
732 igc_power_up_phy_copper(struct igc_hw *hw)
733 {
734 	uint16_t mii_reg = 0;
735 
736 	/* The PHY will retain its settings across a power down/up cycle */
737 	hw->phy.ops.read_reg(hw, PHY_CONTROL, &mii_reg);
738 	mii_reg &= ~MII_CR_POWER_DOWN;
739 	hw->phy.ops.write_reg(hw, PHY_CONTROL, mii_reg);
740 	DELAY(300);
741 }
742 
743 /**
744  * igc_power_down_phy_copper - Restore copper link in case of PHY power down
745  * @hw: pointer to the HW structure
746  *
747  * In the case of a PHY power down to save power, or to turn off link during a
748  * driver unload, or wake on lan is not enabled, restore the link to previous
749  * settings.
750  **/
751 void
752 igc_power_down_phy_copper(struct igc_hw *hw)
753 {
754 	uint16_t mii_reg = 0;
755 
756 	/* The PHY will retain its settings across a power down/up cycle */
757 	hw->phy.ops.read_reg(hw, PHY_CONTROL, &mii_reg);
758 	mii_reg |= MII_CR_POWER_DOWN;
759 	hw->phy.ops.write_reg(hw, PHY_CONTROL, mii_reg);
760 	msec_delay(1);
761 }
762 
763 /**
764  *  igc_write_phy_reg_gpy - Write GPY PHY register
765  *  @hw: pointer to the HW structure
766  *  @offset: register offset to write to
767  *  @data: data to write at register offset
768  *
769  *  Acquires semaphore, if necessary, then writes the data to PHY register
770  *  at the offset.  Release any acquired semaphores before exiting.
771  **/
772 int
773 igc_write_phy_reg_gpy(struct igc_hw *hw, uint32_t offset, uint16_t data)
774 {
775 	uint8_t dev_addr = (offset & GPY_MMD_MASK) >> GPY_MMD_SHIFT;
776 	int ret_val;
777 
778 	DEBUGFUNC("igc_write_phy_reg_gpy");
779 
780 	offset = offset & GPY_REG_MASK;
781 
782 	if (!dev_addr) {
783 		ret_val = hw->phy.ops.acquire(hw);
784 		if (ret_val)
785 			return ret_val;
786 		ret_val = igc_write_phy_reg_mdic(hw, offset, data);
787 		if (ret_val)
788 			return ret_val;
789 		hw->phy.ops.release(hw);
790 	} else {
791 		ret_val = igc_write_xmdio_reg(hw, (uint16_t)offset, dev_addr,
792 		    data);
793 	}
794 
795 	return ret_val;
796 }
797 
798 /**
799  *  igc_read_phy_reg_gpy - Read GPY PHY register
800  *  @hw: pointer to the HW structure
801  *  @offset: lower half is register offset to read to
802  *     upper half is MMD to use.
803  *  @data: data to read at register offset
804  *
805  *  Acquires semaphore, if necessary, then reads the data in the PHY register
806  *  at the offset.  Release any acquired semaphores before exiting.
807  **/
808 int
809 igc_read_phy_reg_gpy(struct igc_hw *hw, uint32_t offset, uint16_t *data)
810 {
811 	uint8_t dev_addr = (offset & GPY_MMD_MASK) >> GPY_MMD_SHIFT;
812 	int ret_val;
813 
814 	DEBUGFUNC("igc_read_phy_reg_gpy");
815 
816 	offset = offset & GPY_REG_MASK;
817 
818 	if (!dev_addr) {
819 		ret_val = hw->phy.ops.acquire(hw);
820 		if (ret_val)
821 			return ret_val;
822 		ret_val = igc_read_phy_reg_mdic(hw, offset, data);
823 		if (ret_val)
824 			return ret_val;
825 		hw->phy.ops.release(hw);
826 	} else {
827 		ret_val = igc_read_xmdio_reg(hw, (uint16_t)offset, dev_addr,
828 		    data);
829 	}
830 
831 	return ret_val;
832 }
833 
834 /**
835  *  __igc_access_xmdio_reg - Read/write XMDIO register
836  *  @hw: pointer to the HW structure
837  *  @address: XMDIO address to program
838  *  @dev_addr: device address to program
839  *  @data: pointer to value to read/write from/to the XMDIO address
840  *  @read: boolean flag to indicate read or write
841  **/
842 int
843 __igc_access_xmdio_reg(struct igc_hw *hw, uint16_t address, uint8_t dev_addr,
844     uint16_t *data, bool read)
845 {
846 	int ret_val;
847 
848 	DEBUGFUNC("__igc_access_xmdio_reg");
849 
850 	ret_val = hw->phy.ops.write_reg(hw, IGC_MMDAC, dev_addr);
851 	if (ret_val)
852 		return ret_val;
853 
854 	ret_val = hw->phy.ops.write_reg(hw, IGC_MMDAAD, address);
855 	if (ret_val)
856 		return ret_val;
857 
858 	ret_val = hw->phy.ops.write_reg(hw, IGC_MMDAC, IGC_MMDAC_FUNC_DATA |
859 	    dev_addr);
860 	if (ret_val)
861 		return ret_val;
862 
863 	if (read)
864 		ret_val = hw->phy.ops.read_reg(hw, IGC_MMDAAD, data);
865 	else
866 		ret_val = hw->phy.ops.write_reg(hw, IGC_MMDAAD, *data);
867 	if (ret_val)
868 		return ret_val;
869 
870 	/* Recalibrate the device back to 0 */
871 	ret_val = hw->phy.ops.write_reg(hw, IGC_MMDAC, 0);
872 	if (ret_val)
873 		return ret_val;
874 
875 	return ret_val;
876 }
877 
878 /**
879  *  igc_read_xmdio_reg - Read XMDIO register
880  *  @hw: pointer to the HW structure
881  *  @addr: XMDIO address to program
882  *  @dev_addr: device address to program
883  *  @data: value to be read from the EMI address
884  **/
885 int
886 igc_read_xmdio_reg(struct igc_hw *hw, uint16_t addr, uint8_t dev_addr,
887     uint16_t *data)
888 {
889 	DEBUGFUNC("igc_read_xmdio_reg");
890 
891 	return __igc_access_xmdio_reg(hw, addr, dev_addr, data, true);
892 }
893 
894 /**
895  *  igc_write_xmdio_reg - Write XMDIO register
896  *  @hw: pointer to the HW structure
897  *  @addr: XMDIO address to program
898  *  @dev_addr: device address to program
899  *  @data: value to be written to the XMDIO address
900  **/
901 int
902 igc_write_xmdio_reg(struct igc_hw *hw, uint16_t addr, uint8_t dev_addr,
903     uint16_t data)
904 {
905 	DEBUGFUNC("igc_write_xmdio_reg");
906 
907 	return __igc_access_xmdio_reg(hw, addr, dev_addr, &data, false);
908 }
909