1 /*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22 /*
23 * Copyright (c) 2010-2013, by Broadcom, Inc.
24 * All Rights Reserved.
25 */
26
27 /*
28 * Copyright (c) 2002, 2010, Oracle and/or its affiliates.
29 * All rights reserved.
30 */
31
32 /*
33 * Copyright 2023 Oxide Computer Company
34 */
35
36 #include "bge_impl.h"
37
38 /*
39 * Bit test macros, returning boolean_t values
40 */
41 #define BIS(w, b) (((w) & (b)) ? B_TRUE : B_FALSE)
42 #define BIC(w, b) (((w) & (b)) ? B_FALSE : B_TRUE)
43 #define UPORDOWN(x) ((x) ? "up" : "down")
44
45 /*
46 * ========== Copper (PHY) support ==========
47 */
48
49 #define BGE_DBG BGE_DBG_PHY /* debug flag for this code */
50
51 /*
52 * #defines:
53 * BGE_COPPER_WIRESPEED controls whether the Broadcom WireSpeed(tm)
54 * feature is enabled. We need to recheck whether this can be
55 * enabled; at one time it seemed to interact unpleasantly with the
56 * loopback modes.
57 *
58 * BGE_COPPER_IDLEOFF controls whether the (copper) PHY power is
59 * turned off when the PHY is idled i.e. during driver suspend().
60 * For now this is disabled because the chip doesn't seem to
61 * resume cleanly if the PHY power is turned off.
62 */
63 #define BGE_COPPER_WIRESPEED B_TRUE
64 #define BGE_COPPER_IDLEOFF B_FALSE
65
66 /*
67 * The arrays below can be indexed by the MODE bits from the Auxiliary
68 * Status register to determine the current speed/duplex settings.
69 */
70 static const int16_t bge_copper_link_speed[] = {
71 0, /* MII_AUX_STATUS_MODE_NONE */
72 10, /* MII_AUX_STATUS_MODE_10_H */
73 10, /* MII_AUX_STATUS_MODE_10_F */
74 100, /* MII_AUX_STATUS_MODE_100_H */
75 0, /* MII_AUX_STATUS_MODE_100_4 */
76 100, /* MII_AUX_STATUS_MODE_100_F */
77 1000, /* MII_AUX_STATUS_MODE_1000_H */
78 1000 /* MII_AUX_STATUS_MODE_1000_F */
79 };
80
81 static const int8_t bge_copper_link_duplex[] = {
82 LINK_DUPLEX_UNKNOWN, /* MII_AUX_STATUS_MODE_NONE */
83 LINK_DUPLEX_HALF, /* MII_AUX_STATUS_MODE_10_H */
84 LINK_DUPLEX_FULL, /* MII_AUX_STATUS_MODE_10_F */
85 LINK_DUPLEX_HALF, /* MII_AUX_STATUS_MODE_100_H */
86 LINK_DUPLEX_UNKNOWN, /* MII_AUX_STATUS_MODE_100_4 */
87 LINK_DUPLEX_FULL, /* MII_AUX_STATUS_MODE_100_F */
88 LINK_DUPLEX_HALF, /* MII_AUX_STATUS_MODE_1000_H */
89 LINK_DUPLEX_FULL /* MII_AUX_STATUS_MODE_1000_F */
90 };
91
92 static const int16_t bge_copper_link_speed_5906[] = {
93 0, /* MII_AUX_STATUS_MODE_NONE */
94 10, /* MII_AUX_STATUS_MODE_10_H */
95 10, /* MII_AUX_STATUS_MODE_10_F */
96 100, /* MII_AUX_STATUS_MODE_100_H */
97 0, /* MII_AUX_STATUS_MODE_100_4 */
98 100, /* MII_AUX_STATUS_MODE_100_F */
99 0, /* MII_AUX_STATUS_MODE_1000_H */
100 0 /* MII_AUX_STATUS_MODE_1000_F */
101 };
102
103 static const int8_t bge_copper_link_duplex_5906[] = {
104 LINK_DUPLEX_UNKNOWN, /* MII_AUX_STATUS_MODE_NONE */
105 LINK_DUPLEX_HALF, /* MII_AUX_STATUS_MODE_10_H */
106 LINK_DUPLEX_FULL, /* MII_AUX_STATUS_MODE_10_F */
107 LINK_DUPLEX_HALF, /* MII_AUX_STATUS_MODE_100_H */
108 LINK_DUPLEX_UNKNOWN, /* MII_AUX_STATUS_MODE_100_4 */
109 LINK_DUPLEX_FULL, /* MII_AUX_STATUS_MODE_100_F */
110 LINK_DUPLEX_UNKNOWN, /* MII_AUX_STATUS_MODE_1000_H */
111 LINK_DUPLEX_UNKNOWN /* MII_AUX_STATUS_MODE_1000_F */
112 };
113
114 #if BGE_DEBUGGING
115
116 static void
bge_phydump(bge_t * bgep,uint16_t mii_status,uint16_t aux)117 bge_phydump(bge_t *bgep, uint16_t mii_status, uint16_t aux)
118 {
119 uint16_t regs[32];
120 int i;
121
122 ASSERT(mutex_owned(bgep->genlock));
123
124 for (i = 0; i < 32; ++i)
125 switch (i) {
126 default:
127 regs[i] = bge_mii_get16(bgep, i);
128 break;
129
130 case MII_STATUS:
131 regs[i] = mii_status;
132 break;
133
134 case MII_AUX_STATUS:
135 regs[i] = aux;
136 break;
137
138 case 0x0b: case 0x0c: case 0x0d: case 0x0e:
139 case 0x15: case 0x16: case 0x17:
140 case 0x1c:
141 case 0x1f:
142 /* reserved registers -- don't read these */
143 regs[i] = 0;
144 break;
145 }
146
147 for (i = 0; i < 32; i += 8)
148 BGE_DEBUG(("bge_phydump: "
149 "0x%04x %04x %04x %04x %04x %04x %04x %04x",
150 regs[i+0], regs[i+1], regs[i+2], regs[i+3],
151 regs[i+4], regs[i+5], regs[i+6], regs[i+7]));
152 }
153
154 #endif /* BGE_DEBUGGING */
155
156 static void
bge_phy_toggle_auxctl_smdsp(bge_t * bgep,boolean_t enable)157 bge_phy_toggle_auxctl_smdsp(bge_t *bgep,
158 boolean_t enable)
159 {
160 uint16_t val;
161
162 val = bge_mii_get16(bgep, MII_AUX_CONTROL);
163
164 if (enable) {
165 val |= MII_AUX_CTRL_SMDSP_ENA;
166 } else {
167 val &= ~MII_AUX_CTRL_SMDSP_ENA;
168 }
169
170 bge_mii_put16(bgep, MII_AUX_CONTROL, (val | MII_AUX_CTRL_TX_6DB));
171 }
172
173 /*
174 * Basic low-level function to probe for a PHY
175 *
176 * Returns TRUE if the PHY responds with valid data, FALSE otherwise
177 */
178 static boolean_t
bge_phy_probe(bge_t * bgep)179 bge_phy_probe(bge_t *bgep)
180 {
181 uint16_t miicfg;
182 uint32_t nicsig, niccfg;
183 int i;
184
185 BGE_TRACE(("bge_phy_probe($%p)", (void *)bgep));
186
187 ASSERT(mutex_owned(bgep->genlock));
188
189 nicsig = bge_nic_read32(bgep, BGE_NIC_DATA_SIG_ADDR);
190 if (nicsig == BGE_NIC_DATA_SIG) {
191 niccfg = bge_nic_read32(bgep, BGE_NIC_DATA_NIC_CFG_ADDR);
192 switch (niccfg & BGE_NIC_CFG_PHY_TYPE_MASK) {
193 default:
194 case BGE_NIC_CFG_PHY_TYPE_COPPER:
195 return (B_TRUE);
196 case BGE_NIC_CFG_PHY_TYPE_FIBER:
197 return (B_FALSE);
198 }
199 } else {
200 /*
201 * Read the MII_STATUS register twice, in
202 * order to clear any sticky bits (but they should
203 * have been cleared by the RESET, I think).
204 */
205 for (i = 0; i < 100; i++) {
206 drv_usecwait(40);
207 miicfg = bge_mii_get16(bgep, MII_STATUS);
208 }
209 BGE_DEBUG(("bge_phy_probe: status 0x%x", miicfg));
210
211 /*
212 * Now check the value read; it should have at least one bit set
213 * (for the device capabilities) and at least one clear (one of
214 * the error bits). So if we see all 0s or all 1s, there's a
215 * problem. In particular, bge_mii_get16() returns all 1s if
216 * communications fails ...
217 */
218 switch (miicfg) {
219 case 0x0000:
220 case 0xffff:
221 return (B_FALSE);
222
223 default:
224 return (B_TRUE);
225 }
226 }
227 }
228
229 /*
230 * Basic low-level function to reset the PHY.
231 * Doesn't incorporate any special-case workarounds.
232 *
233 * Returns TRUE on success, FALSE if the RESET bit doesn't clear
234 */
235 static boolean_t
bge_phy_reset(bge_t * bgep)236 bge_phy_reset(bge_t *bgep)
237 {
238 uint16_t control;
239 uint_t count;
240
241 BGE_TRACE(("bge_phy_reset($%p)", (void *)bgep));
242
243 ASSERT(mutex_owned(bgep->genlock));
244
245 if (DEVICE_5906_SERIES_CHIPSETS(bgep)) {
246 drv_usecwait(40);
247 /* put PHY into ready state */
248 bge_reg_clr32(bgep, MISC_CONFIG_REG, MISC_CONFIG_EPHY_IDDQ);
249 (void) bge_reg_get32(bgep, MISC_CONFIG_REG); /* flush */
250 drv_usecwait(40);
251 }
252
253 /*
254 * Set the PHY RESET bit, then wait up to 5 ms for it to self-clear
255 */
256 bge_mii_put16(bgep, MII_CONTROL, MII_CONTROL_RESET);
257 for (count = 0; ++count < 1000; ) {
258 drv_usecwait(5);
259 control = bge_mii_get16(bgep, MII_CONTROL);
260 if (BIC(control, MII_CONTROL_RESET))
261 return (B_TRUE);
262 }
263
264 if (DEVICE_5906_SERIES_CHIPSETS(bgep))
265 (void) bge_adj_volt_5906(bgep);
266
267 BGE_DEBUG(("bge_phy_reset: FAILED, control now 0x%x", control));
268
269 return (B_FALSE);
270 }
271
272 /*
273 * Basic low-level function to powerdown the PHY, if supported
274 * If powerdown support is compiled out, this function does nothing.
275 */
276 static void
bge_phy_powerdown(bge_t * bgep)277 bge_phy_powerdown(bge_t *bgep)
278 {
279 BGE_TRACE(("bge_phy_powerdown"));
280 #if BGE_COPPER_IDLEOFF
281 bge_mii_put16(bgep, MII_CONTROL, MII_CONTROL_PWRDN);
282 #endif /* BGE_COPPER_IDLEOFF */
283 }
284
285 /*
286 * The following functions are based on sample code provided by
287 * Broadcom (20-June-2003), and implement workarounds said to be
288 * required on the early revisions of the BCM5703/4C.
289 *
290 * The registers and values used are mostly UNDOCUMENTED, and
291 * therefore don't have symbolic names ;-(
292 *
293 * Many of the comments are straight out of the Broadcom code:
294 * even where the code has been restructured, the original
295 * comments have been preserved in order to explain what these
296 * undocumented registers & values are all about ...
297 */
298
299 static void
bge_phy_macro_wait(bge_t * bgep)300 bge_phy_macro_wait(bge_t *bgep)
301 {
302 uint_t count;
303
304 for (count = 100; --count; )
305 if ((bge_mii_get16(bgep, 0x16) & 0x1000) == 0)
306 break;
307 }
308
309 /*
310 * PHY test data pattern:
311 *
312 * For 5703/04, each DFE TAP has 21-bits (low word 15, hi word 6)
313 * For 5705, each DFE TAP has 19-bits (low word 15, hi word 4)
314 * For simplicity, we check only 19-bits, so we don't have to
315 * distinguish which chip it is.
316 * the LO word contains 15 bits, make sure pattern data is < 0x7fff
317 * the HI word contains 6 bits, make sure pattern data is < 0x003f
318 */
319 #define N_CHANNELS 4
320 #define N_TAPS 3
321
322 static struct {
323 uint16_t lo;
324 uint16_t hi;
325 } tap_data[N_CHANNELS][N_TAPS] = {
326 {
327 { 0x5555, 0x0005 }, /* ch0, TAP 0, LO/HI pattern */
328 { 0x2aaa, 0x000a }, /* ch0, TAP 1, LO/HI pattern */
329 { 0x3456, 0x0003 } /* ch0, TAP 2, LO/HI pattern */
330 },
331 {
332 { 0x2aaa, 0x000a }, /* ch1, TAP 0, LO/HI pattern */
333 { 0x3333, 0x0003 }, /* ch1, TAP 1, LO/HI pattern */
334 { 0x789a, 0x0005 } /* ch1, TAP 2, LO/HI pattern */
335 },
336 {
337 { 0x5a5a, 0x0005 }, /* ch2, TAP 0, LO/HI pattern */
338 { 0x2a6a, 0x000a }, /* ch2, TAP 1, LO/HI pattern */
339 { 0x1bcd, 0x0003 } /* ch2, TAP 2, LO/HI pattern */
340 },
341 {
342 { 0x2a5a, 0x000a }, /* ch3, TAP 0, LO/HI pattern */
343 { 0x33c3, 0x0003 }, /* ch3, TAP 1, LO/HI pattern */
344 { 0x2ef1, 0x0005 } /* ch3, TAP 2, LO/HI pattern */
345 }
346 };
347
348 /*
349 * Check whether the PHY has locked up after a RESET.
350 *
351 * Returns TRUE if it did, FALSE is it's OK ;-)
352 */
353 static boolean_t
bge_phy_locked_up(bge_t * bgep)354 bge_phy_locked_up(bge_t *bgep)
355 {
356 uint16_t dataLo;
357 uint16_t dataHi;
358 uint_t chan;
359 uint_t tap;
360
361 /*
362 * Check TAPs for all 4 channels, as soon as we see a lockup
363 * we'll stop checking.
364 */
365 for (chan = 0; chan < N_CHANNELS; ++chan) {
366 /* Select channel and set TAP index to 0 */
367 bge_mii_put16(bgep, 0x17, (chan << 13) | 0x0200);
368 /* Freeze filter again just to be safe */
369 bge_mii_put16(bgep, 0x16, 0x0002);
370
371 /*
372 * Write fixed pattern to the RAM, 3 TAPs for
373 * each channel, each TAP have 2 WORDs (LO/HI)
374 */
375 for (tap = 0; tap < N_TAPS; ++tap) {
376 bge_mii_put16(bgep, 0x15, tap_data[chan][tap].lo);
377 bge_mii_put16(bgep, 0x15, tap_data[chan][tap].hi);
378 }
379
380 /*
381 * Active PHY's Macro operation to write DFE
382 * TAP from RAM, and wait for Macro to complete.
383 */
384 bge_mii_put16(bgep, 0x16, 0x0202);
385 bge_phy_macro_wait(bgep);
386
387 /*
388 * Done with write phase, now begin read phase.
389 */
390
391 /* Select channel and set TAP index to 0 */
392 bge_mii_put16(bgep, 0x17, (chan << 13) | 0x0200);
393
394 /*
395 * Active PHY's Macro operation to load DFE
396 * TAP to RAM, and wait for Macro to complete
397 */
398 bge_mii_put16(bgep, 0x16, 0x0082);
399 bge_phy_macro_wait(bgep);
400
401 /* Enable "pre-fetch" */
402 bge_mii_put16(bgep, 0x16, 0x0802);
403 bge_phy_macro_wait(bgep);
404
405 /*
406 * Read back the TAP values. 3 TAPs for each
407 * channel, each TAP have 2 WORDs (LO/HI)
408 */
409 for (tap = 0; tap < N_TAPS; ++tap) {
410 /*
411 * Read Lo/Hi then wait for 'done' is faster.
412 * For DFE TAP, the HI word contains 6 bits,
413 * LO word contains 15 bits
414 */
415 dataLo = bge_mii_get16(bgep, 0x15) & 0x7fff;
416 dataHi = bge_mii_get16(bgep, 0x15) & 0x003f;
417 bge_phy_macro_wait(bgep);
418
419 /*
420 * Check if what we wrote is what we read back.
421 * If failed, then the PHY is locked up, we need
422 * to do PHY reset again
423 */
424 if (dataLo != tap_data[chan][tap].lo)
425 return (B_TRUE); /* wedged! */
426
427 if (dataHi != tap_data[chan][tap].hi)
428 return (B_TRUE); /* wedged! */
429 }
430 }
431
432 /*
433 * The PHY isn't locked up ;-)
434 */
435 return (B_FALSE);
436 }
437
438 /*
439 * Special-case code to reset the PHY on the 5702/5703/5704C/5705/5782.
440 * Tries up to 5 times to recover from failure to reset or PHY lockup.
441 *
442 * Returns TRUE on success, FALSE if there's an unrecoverable problem
443 */
444 static boolean_t
bge_phy_reset_and_check(bge_t * bgep)445 bge_phy_reset_and_check(bge_t *bgep)
446 {
447 boolean_t reset_success;
448 boolean_t phy_locked;
449 uint16_t extctrl;
450 uint16_t gigctrl;
451 uint_t retries;
452
453 for (retries = 0; retries < 5; ++retries) {
454 /* Issue a phy reset, and wait for reset to complete */
455 /* Assuming reset is successful first */
456 reset_success = bge_phy_reset(bgep);
457
458 /*
459 * Now go check the DFE TAPs to see if locked up, but
460 * first, we need to set up PHY so we can read DFE
461 * TAPs.
462 */
463
464 /*
465 * Disable Transmitter and Interrupt, while we play
466 * with the PHY registers, so the link partner won't
467 * see any strange data and the Driver won't see any
468 * interrupts.
469 */
470 extctrl = bge_mii_get16(bgep, 0x10);
471 bge_mii_put16(bgep, 0x10, extctrl | 0x3000);
472
473 /* Setup Full-Duplex, 1000 mbps */
474 bge_mii_put16(bgep, 0x0, 0x0140);
475
476 /* Set to Master mode */
477 gigctrl = bge_mii_get16(bgep, 0x9);
478 bge_mii_put16(bgep, 0x9, 0x1800);
479
480 /* Enable SM_DSP_CLOCK & 6dB */
481 bge_mii_put16(bgep, 0x18, 0x0c00); /* "the ADC fix" */
482
483 /* Work-arounds */
484 bge_mii_put16(bgep, 0x17, 0x201f);
485 bge_mii_put16(bgep, 0x15, 0x2aaa);
486
487 /* More workarounds */
488 bge_mii_put16(bgep, 0x17, 0x000a);
489 bge_mii_put16(bgep, 0x15, 0x0323); /* "the Gamma fix" */
490
491 /* Blocks the PHY control access */
492 bge_mii_put16(bgep, 0x17, 0x8005);
493 bge_mii_put16(bgep, 0x15, 0x0800);
494
495 /* Test whether PHY locked up ;-( */
496 phy_locked = bge_phy_locked_up(bgep);
497 if (reset_success && !phy_locked)
498 break;
499
500 /*
501 * Some problem here ... log it & retry
502 */
503 if (!reset_success)
504 BGE_REPORT((bgep, "PHY didn't reset!"));
505 if (phy_locked)
506 BGE_REPORT((bgep, "PHY locked up!"));
507 }
508
509 /* Remove block phy control */
510 bge_mii_put16(bgep, 0x17, 0x8005);
511 bge_mii_put16(bgep, 0x15, 0x0000);
512
513 /* Unfreeze DFE TAP filter for all channels */
514 bge_mii_put16(bgep, 0x17, 0x8200);
515 bge_mii_put16(bgep, 0x16, 0x0000);
516
517 /* Restore PHY back to operating state */
518 bge_mii_put16(bgep, 0x18, 0x0400);
519
520 /* Restore 1000BASE-T Control Register */
521 bge_mii_put16(bgep, 0x9, gigctrl);
522
523 /* Enable transmitter and interrupt */
524 extctrl = bge_mii_get16(bgep, 0x10);
525 bge_mii_put16(bgep, 0x10, extctrl & ~0x3000);
526
527 if (DEVICE_5906_SERIES_CHIPSETS(bgep))
528 (void) bge_adj_volt_5906(bgep);
529
530 if (!reset_success)
531 bge_fm_ereport(bgep, DDI_FM_DEVICE_NO_RESPONSE);
532 else if (phy_locked)
533 bge_fm_ereport(bgep, DDI_FM_DEVICE_INVAL_STATE);
534 return (reset_success && !phy_locked);
535 }
536
537 static void
bge_phy_tweak_gmii(bge_t * bgep)538 bge_phy_tweak_gmii(bge_t *bgep)
539 {
540 /* Tweak GMII timing */
541 bge_mii_put16(bgep, 0x1c, 0x8d68);
542 bge_mii_put16(bgep, 0x1c, 0x8d68);
543 }
544
545 /* Bit Error Rate reduction fix */
546 static void
bge_phy_bit_err_fix(bge_t * bgep)547 bge_phy_bit_err_fix(bge_t *bgep)
548 {
549 bge_mii_put16(bgep, 0x18, 0x0c00);
550 bge_mii_put16(bgep, 0x17, 0x000a);
551 bge_mii_put16(bgep, 0x15, 0x310b);
552 bge_mii_put16(bgep, 0x17, 0x201f);
553 bge_mii_put16(bgep, 0x15, 0x9506);
554 bge_mii_put16(bgep, 0x17, 0x401f);
555 bge_mii_put16(bgep, 0x15, 0x14e2);
556 bge_mii_put16(bgep, 0x18, 0x0400);
557 }
558
559 /*
560 * End of Broadcom-derived workaround code
561 */
562
563 static int
bge_restart_copper(bge_t * bgep,boolean_t powerdown)564 bge_restart_copper(bge_t *bgep, boolean_t powerdown)
565 {
566 uint16_t phy_status;
567 boolean_t reset_ok;
568 uint16_t extctrl, auxctrl;
569 int i;
570
571 BGE_TRACE(("bge_restart_copper($%p, %d)", (void *)bgep, powerdown));
572
573 ASSERT(mutex_owned(bgep->genlock));
574
575 switch (MHCR_CHIP_ASIC_REV(bgep)) {
576 default:
577 /*
578 * Shouldn't happen; it means we don't recognise this chip.
579 * It's probably a new one, so we'll try our best anyway ...
580 */
581 case MHCR_CHIP_ASIC_REV_5703:
582 case MHCR_CHIP_ASIC_REV_5704:
583 case MHCR_CHIP_ASIC_REV_5705:
584 case MHCR_CHIP_ASIC_REV_5752:
585 case MHCR_CHIP_ASIC_REV_5714:
586 case MHCR_CHIP_ASIC_REV_5715:
587 reset_ok = bge_phy_reset_and_check(bgep);
588 break;
589
590 case MHCR_CHIP_ASIC_REV_5906:
591 case MHCR_CHIP_ASIC_REV_5700:
592 case MHCR_CHIP_ASIC_REV_5701:
593 case MHCR_CHIP_ASIC_REV_5723: /* 5717, 5725, 57765 series as well */
594 case MHCR_CHIP_ASIC_REV_5721_5751:
595 /*
596 * Just a plain reset; the "check" code breaks these chips
597 */
598 reset_ok = bge_phy_reset(bgep);
599 if (!reset_ok)
600 bge_fm_ereport(bgep, DDI_FM_DEVICE_NO_RESPONSE);
601 break;
602 }
603 if (!reset_ok) {
604 BGE_REPORT((bgep, "PHY failed to reset correctly"));
605 return (DDI_FAILURE);
606 }
607
608 /*
609 * Step 5: disable WOL (not required after RESET)
610 *
611 * Step 6: refer to errata
612 */
613 switch (bgep->chipid.asic_rev) {
614 default:
615 break;
616
617 case MHCR_CHIP_REV_5704_A0:
618 bge_phy_tweak_gmii(bgep);
619 break;
620 }
621
622 switch (MHCR_CHIP_ASIC_REV(bgep)) {
623 case MHCR_CHIP_ASIC_REV_5705:
624 case MHCR_CHIP_ASIC_REV_5721_5751:
625 bge_phy_bit_err_fix(bgep);
626 break;
627 }
628
629 if (!(bgep->chipid.flags & CHIP_FLAG_NO_JUMBO) &&
630 (bgep->chipid.default_mtu > BGE_DEFAULT_MTU)) {
631 /* Set the GMII Fifo Elasticity to high latency */
632 extctrl = bge_mii_get16(bgep, 0x10);
633 bge_mii_put16(bgep, 0x10, extctrl | 0x1);
634
635 /* Allow reception of extended length packets */
636 bge_mii_put16(bgep, MII_AUX_CONTROL, 0x0007);
637 auxctrl = bge_mii_get16(bgep, MII_AUX_CONTROL);
638 auxctrl |= 0x4000;
639 bge_mii_put16(bgep, MII_AUX_CONTROL, auxctrl);
640 }
641
642 /*
643 * Step 7: read the MII_INTR_STATUS register twice,
644 * in order to clear any sticky bits (but they should
645 * have been cleared by the RESET, I think), and we're
646 * not using PHY interrupts anyway.
647 *
648 * Step 8: enable the PHY to interrupt on link status
649 * change (not required)
650 *
651 * Step 9: configure PHY LED Mode - not applicable?
652 *
653 * Step 10: read the MII_STATUS register twice, in
654 * order to clear any sticky bits (but they should
655 * have been cleared by the RESET, I think).
656 */
657 for (i = 0; i < 100; i++) {
658 drv_usecwait(40);
659 phy_status = bge_mii_get16(bgep, MII_STATUS);
660 }
661 BGE_DEBUG(("bge_restart_copper: status 0x%x", phy_status));
662
663 /*
664 * Finally, shut down the PHY, if required
665 */
666 if (powerdown)
667 bge_phy_powerdown(bgep);
668 return (DDI_SUCCESS);
669 }
670
671 boolean_t
bge_eee_cap(bge_t * bgep)672 bge_eee_cap(bge_t * bgep)
673 {
674 if (!(DEVICE_5717_SERIES_CHIPSETS(bgep) ||
675 DEVICE_5725_SERIES_CHIPSETS(bgep))) {
676 /* EEE is not supported on this chip */
677 BGE_DEBUG(("bge_eee: eee not supported (device 0x%x)",
678 bgep->chipid.device));
679 return (B_FALSE);
680 }
681
682 switch (CHIP_ASIC_REV_PROD_ID(bgep)) {
683 case CHIP_ASIC_REV_5717_B0: /* = CHIP_ASIC_REV_5718_B0 */
684 case CHIP_ASIC_REV_5717_C0:
685 /* case CHIP_ASIC_REV_5718_B0: */
686 case CHIP_ASIC_REV_5719_A0:
687 case CHIP_ASIC_REV_5719_A1:
688 case CHIP_ASIC_REV_5720_A0:
689 case CHIP_ASIC_REV_5725_A0:
690 case CHIP_ASIC_REV_5727_B0:
691 return (B_TRUE);
692
693 default:
694 /* EEE is not supported on this asic rev */
695 BGE_DEBUG(("bge_eee: eee not supported (asic rev 0x%08x)",
696 bgep->chipid.asic_rev));
697 return (B_FALSE);
698 }
699 }
700
701 void
bge_eee_init(bge_t * bgep)702 bge_eee_init(bge_t * bgep)
703 {
704 uint32_t val;
705
706 BGE_TRACE(("bge_eee_init($%p)", (void *)bgep));
707
708 ASSERT(mutex_owned(bgep->genlock));
709
710 if (!bge_eee_cap(bgep)) {
711 return;
712 }
713
714 /* Enable MAC control of LPI */
715
716 val = (EEE_LINK_IDLE_PCIE_NL0 | EEE_LINK_IDLE_UART_IDL);
717 if (DEVICE_5725_SERIES_CHIPSETS(bgep))
718 val |= EEE_LINK_IDLE_APE_TX_MT;
719 bge_reg_put32(bgep, EEE_LINK_IDLE_CONTROL_REG, val);
720
721 bge_reg_put32(bgep, EEE_CONTROL_REG, EEE_CONTROL_EXIT_20_1_US);
722
723 val = EEE_MODE_ERLY_L1_XIT_DET | EEE_MODE_LPI_IN_TX |
724 EEE_MODE_LPI_IN_RX | EEE_MODE_EEE_ENABLE;
725
726 if (bgep->chipid.device != DEVICE_ID_5717)
727 val |= EEE_MODE_SND_IDX_DET_EN;
728
729 //val |= EEE_MODE_APE_TX_DET_EN;
730
731 if (!bgep->chipid.eee) {
732 val = 0;
733 }
734
735 bge_reg_put32(bgep, EEE_MODE_REG, val);
736
737 /* Set EEE timer debounce values */
738
739 bge_reg_put32(bgep, EEE_DEBOUNCE_T1_CONTROL_REG,
740 EEE_DEBOUNCE_T1_PCIEXIT_2047US | EEE_DEBOUNCE_T1_LNKIDLE_2047US);
741
742 bge_reg_put32(bgep, EEE_DEBOUNCE_T2_CONTROL_REG,
743 EEE_DEBOUNCE_T2_APE_TX_2047US | EEE_DEBOUNCE_T2_TXIDXEQ_2047US);
744 }
745
746 void
bge_eee_autoneg(bge_t * bgep,boolean_t adv_100fdx,boolean_t adv_1000fdx)747 bge_eee_autoneg(bge_t * bgep, boolean_t adv_100fdx, boolean_t adv_1000fdx)
748 {
749 uint32_t val;
750 uint16_t mii_val;
751
752 BGE_TRACE(("bge_eee_autoneg($%p)", (void *)bgep));
753
754 ASSERT(mutex_owned(bgep->genlock));
755
756 if (!bge_eee_cap(bgep)) {
757 return;
758 }
759
760 /* Disable LPI Requests */
761 val = bge_reg_get32(bgep, EEE_MODE_REG);
762 val &= ~EEE_MODE_LPI_ENABLE;
763 bge_reg_put32(bgep, EEE_MODE_REG, val);
764
765 bge_phy_toggle_auxctl_smdsp(bgep, B_TRUE);
766
767 mii_val = 0;
768
769 if (bgep->chipid.eee) {
770 if (adv_100fdx) {
771 mii_val |= EEE_CL45_D7_RESULT_STAT_LP_100TX;
772 }
773 if (adv_1000fdx) {
774 mii_val |= EEE_CL45_D7_RESULT_STAT_LP_1000T;
775 }
776 }
777
778 /* Enable EEE advertisement for the specified mode(s)... */
779 bge_mii_put16(bgep, MII_MMD_CTRL, MDIO_MMD_AN);
780 bge_mii_put16(bgep, MII_MMD_ADDRESS_DATA, MDIO_AN_EEE_ADV);
781 bge_mii_put16(bgep, MII_MMD_CTRL,
782 MII_MMD_CTRL_DATA_NOINC | MDIO_MMD_AN);
783 bge_mii_put16(bgep, MII_MMD_ADDRESS_DATA, mii_val);
784
785 /* Setup PHY DSP for EEE */
786 switch (bgep->chipid.device) {
787 case DEVICE_ID_5717:
788 case DEVICE_ID_5718:
789 case DEVICE_ID_5719:
790 /* If we advertised any EEE advertisements above... */
791 if (mii_val) {
792 mii_val = (MII_DSP_TAP26_ALNOKO |
793 MII_DSP_TAP26_RMRXSTO |
794 MII_DSP_TAP26_OPCSINPT);
795 }
796 bge_phydsp_write(bgep, MII_DSP_TAP26, mii_val);
797 /* fall through */
798 case DEVICE_ID_5720:
799 case DEVICE_ID_5725:
800 case DEVICE_ID_5727:
801 mii_val = bge_phydsp_read(bgep, MII_DSP_CH34TP2);
802 bge_phydsp_write(bgep, MII_DSP_CH34TP2,
803 (mii_val | MII_DSP_CH34TP2_HIBW01));
804 }
805
806 bge_phy_toggle_auxctl_smdsp(bgep, B_FALSE);
807 }
808
809 void
bge_eee_adjust(bge_t * bgep)810 bge_eee_adjust(bge_t * bgep)
811 {
812 uint32_t val;
813 uint16_t mii_val;
814
815 BGE_TRACE(("bge_eee_adjust($%p, %d)", (void *)bgep));
816
817 ASSERT(mutex_owned(bgep->genlock));
818
819 if (!bge_eee_cap(bgep)) {
820 return;
821 }
822
823 bgep->eee_lpi_wait = 0;
824
825 /* Check for PHY link status */
826 if (bgep->param_link_up) {
827 BGE_DEBUG(("bge_eee_adjust: link status up"));
828
829 /*
830 * XXX if duplex full and speed is 1000 or 100 then do the
831 * following...
832 */
833
834 if (bgep->param_link_speed == 1000) {
835 BGE_DEBUG(("bge_eee_adjust: eee timing for 1000Mb"));
836 bge_reg_put32(bgep, EEE_CONTROL_REG,
837 EEE_CONTROL_EXIT_16_5_US);
838 } else if (bgep->param_link_speed == 100) {
839 BGE_DEBUG(("bge_eee_adjust: eee timing for 100Mb"));
840 bge_reg_put32(bgep, EEE_CONTROL_REG,
841 EEE_CONTROL_EXIT_36_US);
842 }
843
844 /* Read PHY's EEE negotiation status */
845 bge_mii_put16(bgep, MII_MMD_CTRL, MDIO_MMD_AN);
846 bge_mii_put16(bgep, MII_MMD_ADDRESS_DATA,
847 EEE_CL45_D7_RESULT_STAT);
848 bge_mii_put16(bgep, MII_MMD_CTRL,
849 MII_MMD_CTRL_DATA_NOINC | MDIO_MMD_AN);
850 mii_val = bge_mii_get16(bgep, MII_MMD_ADDRESS_DATA);
851
852 /* Enable EEE LPI request if EEE negotiated */
853 if ((mii_val == EEE_CL45_D7_RESULT_STAT_LP_1000T) ||
854 (mii_val == EEE_CL45_D7_RESULT_STAT_LP_100TX)) {
855 BGE_DEBUG(("bge_eee_adjust: eee negotiaton success, lpi scheduled"));
856 bgep->eee_lpi_wait = 2;
857 } else {
858 BGE_DEBUG(("bge_eee_adjust: eee negotiation failed"));
859 }
860 } else {
861 BGE_DEBUG(("bge_eee_adjust: link status down"));
862 }
863
864 if (!bgep->eee_lpi_wait) {
865 if (bgep->param_link_up) {
866 bge_phy_toggle_auxctl_smdsp(bgep, B_TRUE);
867 bge_phydsp_write(bgep, MII_DSP_TAP26, 0);
868 bge_phy_toggle_auxctl_smdsp(bgep, B_FALSE);
869 }
870
871 /* Disable LPI requests */
872 val = bge_reg_get32(bgep, EEE_MODE_REG);
873 val &= ~EEE_MODE_LPI_ENABLE;
874 bge_reg_put32(bgep, EEE_MODE_REG, val);
875 }
876 }
877
878 void
bge_eee_enable(bge_t * bgep)879 bge_eee_enable(bge_t * bgep)
880 {
881 uint32_t val;
882
883 /* XXX check for EEE for 5717 family... */
884
885 if (bgep->param_link_speed == 1000) {
886 bge_phy_toggle_auxctl_smdsp(bgep, B_TRUE);
887 bge_phydsp_write(bgep, MII_DSP_TAP26,
888 MII_DSP_TAP26_ALNOKO | MII_DSP_TAP26_RMRXSTO);
889 bge_phy_toggle_auxctl_smdsp(bgep, B_FALSE);
890 }
891
892 val = bge_reg_get32(bgep, EEE_MODE_REG);
893 val |= EEE_MODE_LPI_ENABLE;
894 bge_reg_put32(bgep, EEE_MODE_REG, val);
895 }
896
897 /*
898 * Synchronise the (copper) PHY's speed/duplex/autonegotiation capabilities
899 * and advertisements with the required settings as specified by the various
900 * param_* variables that can be poked via the NDD interface.
901 *
902 * We always reset the PHY and reprogram *all* the relevant registers,
903 * not just those changed. This should cause the link to go down, and then
904 * back up again once the link is stable and autonegotiation (if enabled)
905 * is complete. We should get a link state change interrupt somewhere along
906 * the way ...
907 *
908 * NOTE: <genlock> must already be held by the caller
909 */
910 static int
bge_update_copper(bge_t * bgep)911 bge_update_copper(bge_t *bgep)
912 {
913 boolean_t adv_autoneg;
914 boolean_t adv_pause;
915 boolean_t adv_asym_pause;
916 boolean_t adv_1000fdx;
917 boolean_t adv_1000hdx;
918 boolean_t adv_100fdx;
919 boolean_t adv_100hdx;
920 boolean_t adv_10fdx;
921 boolean_t adv_10hdx;
922
923 uint16_t control;
924 uint16_t gigctrl;
925 uint16_t auxctrl;
926 uint16_t anar;
927
928 BGE_TRACE(("bge_update_copper($%p)", (void *)bgep));
929
930 ASSERT(mutex_owned(bgep->genlock));
931
932 BGE_DEBUG(("bge_update_copper: autoneg %d "
933 "pause %d asym_pause %d "
934 "1000fdx %d 1000hdx %d "
935 "100fdx %d 100hdx %d "
936 "10fdx %d 10hdx %d ",
937 bgep->param_adv_autoneg,
938 bgep->param_adv_pause, bgep->param_adv_asym_pause,
939 bgep->param_adv_1000fdx, bgep->param_adv_1000hdx,
940 bgep->param_adv_100fdx, bgep->param_adv_100hdx,
941 bgep->param_adv_10fdx, bgep->param_adv_10hdx));
942
943 control = gigctrl = auxctrl = anar = 0;
944
945 /*
946 * PHY settings are normally based on the param_* variables,
947 * but if any loopback mode is in effect, that takes precedence.
948 *
949 * BGE supports MAC-internal loopback, PHY-internal loopback,
950 * and External loopback at a variety of speeds (with a special
951 * cable). In all cases, autoneg is turned OFF, full-duplex
952 * is turned ON, and the speed/mastership is forced.
953 */
954 switch (bgep->param_loop_mode) {
955 case BGE_LOOP_NONE:
956 default:
957 adv_autoneg = bgep->param_adv_autoneg;
958 adv_pause = bgep->param_adv_pause;
959 adv_asym_pause = bgep->param_adv_asym_pause;
960 adv_1000fdx = bgep->param_adv_1000fdx;
961 adv_1000hdx = bgep->param_adv_1000hdx;
962 adv_100fdx = bgep->param_adv_100fdx;
963 adv_100hdx = bgep->param_adv_100hdx;
964 adv_10fdx = bgep->param_adv_10fdx;
965 adv_10hdx = bgep->param_adv_10hdx;
966 break;
967
968 case BGE_LOOP_EXTERNAL_1000:
969 case BGE_LOOP_EXTERNAL_100:
970 case BGE_LOOP_EXTERNAL_10:
971 case BGE_LOOP_INTERNAL_PHY:
972 case BGE_LOOP_INTERNAL_MAC:
973 adv_autoneg = adv_pause = adv_asym_pause = B_FALSE;
974 adv_1000fdx = adv_100fdx = adv_10fdx = B_FALSE;
975 adv_1000hdx = adv_100hdx = adv_10hdx = B_FALSE;
976 bgep->param_link_duplex = LINK_DUPLEX_FULL;
977
978 switch (bgep->param_loop_mode) {
979 case BGE_LOOP_EXTERNAL_1000:
980 bgep->param_link_speed = 1000;
981 adv_1000fdx = B_TRUE;
982 auxctrl = MII_AUX_CTRL_NORM_EXT_LOOPBACK;
983 gigctrl |= MII_MSCONTROL_MANUAL;
984 gigctrl |= MII_MSCONTROL_MASTER;
985 break;
986
987 case BGE_LOOP_EXTERNAL_100:
988 bgep->param_link_speed = 100;
989 adv_100fdx = B_TRUE;
990 auxctrl = MII_AUX_CTRL_NORM_EXT_LOOPBACK;
991 break;
992
993 case BGE_LOOP_EXTERNAL_10:
994 bgep->param_link_speed = 10;
995 adv_10fdx = B_TRUE;
996 auxctrl = MII_AUX_CTRL_NORM_EXT_LOOPBACK;
997 break;
998
999 case BGE_LOOP_INTERNAL_PHY:
1000 bgep->param_link_speed = 1000;
1001 adv_1000fdx = B_TRUE;
1002 control = MII_CONTROL_LOOPBACK;
1003 break;
1004
1005 case BGE_LOOP_INTERNAL_MAC:
1006 bgep->param_link_speed = 1000;
1007 adv_1000fdx = B_TRUE;
1008 break;
1009 }
1010 }
1011
1012 BGE_DEBUG(("bge_update_copper: autoneg %d "
1013 "pause %d asym_pause %d "
1014 "1000fdx %d 1000hdx %d "
1015 "100fdx %d 100hdx %d "
1016 "10fdx %d 10hdx %d ",
1017 adv_autoneg,
1018 adv_pause, adv_asym_pause,
1019 adv_1000fdx, adv_1000hdx,
1020 adv_100fdx, adv_100hdx,
1021 adv_10fdx, adv_10hdx));
1022
1023 /*
1024 * We should have at least one technology capability set;
1025 * if not, we select a default of 1000Mb/s full-duplex
1026 */
1027 if (!adv_1000fdx && !adv_100fdx && !adv_10fdx &&
1028 !adv_1000hdx && !adv_100hdx && !adv_10hdx)
1029 adv_1000fdx = B_TRUE;
1030
1031 /*
1032 * Now transform the adv_* variables into the proper settings
1033 * of the PHY registers ...
1034 *
1035 * If autonegotiation is (now) enabled, we want to trigger
1036 * a new autonegotiation cycle once the PHY has been
1037 * programmed with the capabilities to be advertised.
1038 */
1039 if (adv_autoneg)
1040 control |= MII_CONTROL_ANE|MII_CONTROL_RSAN;
1041
1042 if (adv_1000fdx)
1043 control |= MII_CONTROL_1GB|MII_CONTROL_FDUPLEX;
1044 else if (adv_1000hdx)
1045 control |= MII_CONTROL_1GB;
1046 else if (adv_100fdx)
1047 control |= MII_CONTROL_100MB|MII_CONTROL_FDUPLEX;
1048 else if (adv_100hdx)
1049 control |= MII_CONTROL_100MB;
1050 else if (adv_10fdx)
1051 control |= MII_CONTROL_FDUPLEX;
1052 else if (adv_10hdx)
1053 control |= 0;
1054 else
1055 { _NOTE(EMPTY); } /* Can't get here anyway ... */
1056
1057 if (adv_1000fdx)
1058 gigctrl |= MII_MSCONTROL_1000T_FD;
1059 if (adv_1000hdx)
1060 gigctrl |= MII_MSCONTROL_1000T;
1061
1062 if (adv_100fdx)
1063 anar |= MII_ABILITY_100BASE_TX_FD;
1064 if (adv_100hdx)
1065 anar |= MII_ABILITY_100BASE_TX;
1066 if (adv_10fdx)
1067 anar |= MII_ABILITY_10BASE_T_FD;
1068 if (adv_10hdx)
1069 anar |= MII_ABILITY_10BASE_T;
1070
1071 if (adv_pause)
1072 anar |= MII_ABILITY_PAUSE;
1073 if (adv_asym_pause)
1074 anar |= MII_ABILITY_ASMPAUSE;
1075
1076 /*
1077 * Munge in any other fixed bits we require ...
1078 */
1079 anar |= MII_AN_SELECTOR_8023;
1080 auxctrl |= MII_AUX_CTRL_NORM_TX_MODE;
1081 auxctrl |= MII_AUX_CTRL_NORMAL;
1082
1083 /*
1084 * Restart the PHY and write the new values. Note the
1085 * time, so that we can say whether subsequent link state
1086 * changes can be attributed to our reprogramming the PHY
1087 */
1088 if ((*bgep->physops->phys_restart)(bgep, B_FALSE) == DDI_FAILURE)
1089 return (DDI_FAILURE);
1090 bge_mii_put16(bgep, MII_AN_ADVERT, anar);
1091 if (auxctrl & MII_AUX_CTRL_NORM_EXT_LOOPBACK)
1092 bge_mii_put16(bgep, MII_AUX_CONTROL, auxctrl);
1093 bge_mii_put16(bgep, MII_MSCONTROL, gigctrl);
1094 bge_mii_put16(bgep, MII_CONTROL, control);
1095
1096 BGE_DEBUG(("bge_update_copper: anar <- 0x%x", anar));
1097 BGE_DEBUG(("bge_update_copper: auxctrl <- 0x%x", auxctrl));
1098 BGE_DEBUG(("bge_update_copper: gigctrl <- 0x%x", gigctrl));
1099 BGE_DEBUG(("bge_update_copper: control <- 0x%x", control));
1100
1101 #if BGE_COPPER_WIRESPEED
1102 /*
1103 * Enable the 'wire-speed' feature, if the chip supports it
1104 * and we haven't got (any) loopback mode selected.
1105 */
1106 switch (bgep->chipid.device) {
1107 case DEVICE_ID_5700:
1108 case DEVICE_ID_5700x:
1109 case DEVICE_ID_5705C:
1110 case DEVICE_ID_5782:
1111 /*
1112 * These chips are known or assumed not to support it
1113 */
1114 break;
1115
1116 default:
1117 /*
1118 * All other Broadcom chips are expected to support it.
1119 */
1120 if (bgep->param_loop_mode == BGE_LOOP_NONE)
1121 bge_mii_put16(bgep, MII_AUX_CONTROL,
1122 MII_AUX_CTRL_MISC_WRITE_ENABLE |
1123 MII_AUX_CTRL_MISC_WIRE_SPEED |
1124 MII_AUX_CTRL_MISC);
1125 break;
1126 }
1127 #endif /* BGE_COPPER_WIRESPEED */
1128
1129 /* enable EEE on those chips that support it */
1130 bge_eee_autoneg(bgep, adv_100fdx, adv_1000fdx);
1131
1132 return (DDI_SUCCESS);
1133 }
1134
1135 static boolean_t
bge_check_copper(bge_t * bgep,boolean_t recheck)1136 bge_check_copper(bge_t *bgep, boolean_t recheck)
1137 {
1138 uint32_t emac_status;
1139 uint16_t mii_status;
1140 uint16_t aux;
1141 uint_t mode;
1142 boolean_t linkup;
1143 int i;
1144
1145 /*
1146 * Step 10: read the status from the PHY (which is self-clearing
1147 * on read!); also read & clear the main (Ethernet) MAC status
1148 * (the relevant bits of this are write-one-to-clear).
1149 */
1150 for (i = 0; i < 100; i++) {
1151 drv_usecwait(40);
1152 mii_status = bge_mii_get16(bgep, MII_STATUS);
1153 }
1154 emac_status = bge_reg_get32(bgep, ETHERNET_MAC_STATUS_REG);
1155 bge_reg_put32(bgep, ETHERNET_MAC_STATUS_REG, emac_status);
1156
1157 BGE_DEBUG(("bge_check_copper: link %d/%s, MII status 0x%x "
1158 "(was 0x%x), Ethernet MAC status 0x%x",
1159 bgep->link_state, UPORDOWN(bgep->param_link_up), mii_status,
1160 bgep->phy_gen_status, emac_status));
1161
1162 /*
1163 * If the PHY status hasn't changed since last we looked, and
1164 * we not forcing a recheck (i.e. the link state was already
1165 * known), there's nothing to do.
1166 */
1167 if (mii_status == bgep->phy_gen_status && !recheck) {
1168 BGE_DEBUG(("bge_check_copper: no link change"));
1169 return (B_FALSE);
1170 }
1171
1172 do {
1173 /*
1174 * Step 11: read AUX STATUS register to find speed/duplex
1175 */
1176 for (i = 0; i < 2000; i++) {
1177 drv_usecwait(10);
1178 aux = bge_mii_get16(bgep, MII_AUX_STATUS);
1179 }
1180 BGE_CDB(bge_phydump, (bgep, mii_status, aux));
1181
1182 /*
1183 * We will only consider the link UP if all the readings
1184 * are consistent and give meaningful results ...
1185 */
1186 mode = aux & MII_AUX_STATUS_MODE_MASK;
1187 mode >>= MII_AUX_STATUS_MODE_SHIFT;
1188 if (DEVICE_5906_SERIES_CHIPSETS(bgep)) {
1189 linkup = BIS(aux, MII_AUX_STATUS_LINKUP);
1190 linkup &= BIS(mii_status, MII_STATUS_LINKUP);
1191 } else {
1192 linkup = bge_copper_link_speed[mode] > 0;
1193 linkup &= bge_copper_link_duplex[mode] !=
1194 LINK_DUPLEX_UNKNOWN;
1195 linkup &= BIS(aux, MII_AUX_STATUS_LINKUP);
1196 linkup &= BIS(mii_status, MII_STATUS_LINKUP);
1197 }
1198
1199 BGE_DEBUG(("bge_check_copper: MII status 0x%x aux 0x%x "
1200 "=> mode %d (%s)",
1201 mii_status, aux,
1202 mode, UPORDOWN(linkup)));
1203
1204 /*
1205 * Record current register values, then reread status
1206 * register & loop until it stabilises ...
1207 */
1208 bgep->phy_aux_status = aux;
1209 bgep->phy_gen_status = mii_status;
1210
1211 for (i = 0; i < 100; i++)
1212 {
1213 drv_usecwait(40);
1214 mii_status = bge_mii_get16(bgep, MII_STATUS);
1215 }
1216 } while (mii_status != bgep->phy_gen_status);
1217
1218 /*
1219 * Assume very little ...
1220 */
1221 bgep->param_lp_autoneg = B_FALSE;
1222 bgep->param_lp_1000fdx = B_FALSE;
1223 bgep->param_lp_1000hdx = B_FALSE;
1224 bgep->param_lp_100fdx = B_FALSE;
1225 bgep->param_lp_100hdx = B_FALSE;
1226 bgep->param_lp_10fdx = B_FALSE;
1227 bgep->param_lp_10hdx = B_FALSE;
1228 bgep->param_lp_pause = B_FALSE;
1229 bgep->param_lp_asym_pause = B_FALSE;
1230 bgep->param_link_autoneg = B_FALSE;
1231 bgep->param_link_tx_pause = B_FALSE;
1232 if (bgep->param_adv_autoneg)
1233 bgep->param_link_rx_pause = B_FALSE;
1234 else
1235 bgep->param_link_rx_pause = bgep->param_adv_pause;
1236
1237 /*
1238 * Discover all the link partner's abilities.
1239 * These are scattered through various registers ...
1240 */
1241 if (BIS(aux, MII_AUX_STATUS_LP_ANEG_ABLE)) {
1242 bgep->param_lp_autoneg = B_TRUE;
1243 bgep->param_link_autoneg = B_TRUE;
1244 bgep->param_link_tx_pause = BIS(aux, MII_AUX_STATUS_TX_PAUSE);
1245 bgep->param_link_rx_pause = BIS(aux, MII_AUX_STATUS_RX_PAUSE);
1246
1247 aux = bge_mii_get16(bgep, MII_MSSTATUS);
1248 bgep->param_lp_1000fdx = BIS(aux, MII_MSSTATUS_LP1000T_FD);
1249 bgep->param_lp_1000hdx = BIS(aux, MII_MSSTATUS_LP1000T);
1250
1251 aux = bge_mii_get16(bgep, MII_AN_LPABLE);
1252 bgep->param_lp_100fdx = BIS(aux, MII_ABILITY_100BASE_TX_FD);
1253 bgep->param_lp_100hdx = BIS(aux, MII_ABILITY_100BASE_TX);
1254 bgep->param_lp_10fdx = BIS(aux, MII_ABILITY_10BASE_T_FD);
1255 bgep->param_lp_10hdx = BIS(aux, MII_ABILITY_10BASE_T);
1256 bgep->param_lp_pause = BIS(aux, MII_ABILITY_PAUSE);
1257 bgep->param_lp_asym_pause = BIS(aux, MII_ABILITY_ASMPAUSE);
1258 }
1259
1260 /*
1261 * Step 12: update ndd-visible state parameters, BUT!
1262 * we don't transfer the new state to <link_state> just yet;
1263 * instead we mark the <link_state> as UNKNOWN, and our caller
1264 * will resolve it once the status has stopped changing and
1265 * been stable for several seconds.
1266 */
1267 BGE_DEBUG(("bge_check_copper: link was %s speed %d duplex %d",
1268 UPORDOWN(bgep->param_link_up),
1269 bgep->param_link_speed,
1270 bgep->param_link_duplex));
1271
1272 if (!linkup)
1273 mode = MII_AUX_STATUS_MODE_NONE;
1274 bgep->param_link_up = linkup;
1275 bgep->link_state = LINK_STATE_UNKNOWN;
1276 if (DEVICE_5906_SERIES_CHIPSETS(bgep)) {
1277 if (bgep->phy_aux_status & MII_AUX_STATUS_NEG_ENABLED_5906) {
1278 bgep->param_link_speed =
1279 bge_copper_link_speed_5906[mode];
1280 bgep->param_link_duplex =
1281 bge_copper_link_duplex_5906[mode];
1282 } else {
1283 bgep->param_link_speed = (bgep->phy_aux_status &
1284 MII_AUX_STATUS_SPEED_IND_5906) ? 100 : 10;
1285 bgep->param_link_duplex = (bgep->phy_aux_status &
1286 MII_AUX_STATUS_DUPLEX_IND_5906) ? LINK_DUPLEX_FULL :
1287 LINK_DUPLEX_HALF;
1288 }
1289 } else {
1290 bgep->param_link_speed = bge_copper_link_speed[mode];
1291 bgep->param_link_duplex = bge_copper_link_duplex[mode];
1292 }
1293
1294 bge_eee_adjust(bgep);
1295
1296 bge_log(bgep, "bge_check_copper: link now %s speed %d duplex %d",
1297 UPORDOWN(bgep->param_link_up),
1298 bgep->param_link_speed,
1299 bgep->param_link_duplex);
1300
1301 return (B_TRUE);
1302 }
1303
1304 static const phys_ops_t copper_ops = {
1305 bge_restart_copper,
1306 bge_update_copper,
1307 bge_check_copper
1308 };
1309
1310
1311 /*
1312 * ========== SerDes support ==========
1313 */
1314
1315 #undef BGE_DBG
1316 #define BGE_DBG BGE_DBG_SERDES /* debug flag for this code */
1317
1318 /*
1319 * Reinitialise the SerDes interface. Note that it normally powers
1320 * up in the disabled state, so we need to explicitly activate it.
1321 */
1322 static int
bge_restart_serdes(bge_t * bgep,boolean_t powerdown)1323 bge_restart_serdes(bge_t *bgep, boolean_t powerdown)
1324 {
1325 uint32_t macmode;
1326
1327 BGE_TRACE(("bge_restart_serdes($%p, %d)", (void *)bgep, powerdown));
1328
1329 ASSERT(mutex_owned(bgep->genlock));
1330
1331 /*
1332 * Ensure that the main Ethernet MAC mode register is programmed
1333 * appropriately for the SerDes interface ...
1334 */
1335 macmode = bge_reg_get32(bgep, ETHERNET_MAC_MODE_REG);
1336 macmode &= ~ETHERNET_MODE_LINK_POLARITY;
1337 macmode &= ~ETHERNET_MODE_PORTMODE_MASK;
1338 if (DEVICE_5717_SERIES_CHIPSETS(bgep) ||
1339 DEVICE_5725_SERIES_CHIPSETS(bgep) ||
1340 DEVICE_5714_SERIES_CHIPSETS(bgep) ||
1341 DEVICE_57765_SERIES_CHIPSETS(bgep)) {
1342 macmode |= ETHERNET_MODE_PORTMODE_GMII;
1343 } else {
1344 macmode |= ETHERNET_MODE_PORTMODE_TBI;
1345 }
1346 bge_reg_put32(bgep, ETHERNET_MAC_MODE_REG, macmode);
1347
1348 /*
1349 * Ensure that loopback is OFF and comma detection is enabled. Then
1350 * disable the SerDes output (the first time through, it may/will
1351 * already be disabled). If we're shutting down, leave it disabled.
1352 */
1353 bge_reg_clr32(bgep, SERDES_CONTROL_REG, SERDES_CONTROL_TBI_LOOPBACK);
1354 bge_reg_set32(bgep, SERDES_CONTROL_REG, SERDES_CONTROL_COMMA_DETECT);
1355 bge_reg_set32(bgep, SERDES_CONTROL_REG, SERDES_CONTROL_TX_DISABLE);
1356 if (powerdown)
1357 return (DDI_SUCCESS);
1358
1359 /*
1360 * Otherwise, pause, (re-)enable the SerDes output, and send
1361 * all-zero config words in order to force autoneg restart.
1362 * Invalidate the saved "link partners received configs", as
1363 * we're starting over ...
1364 */
1365 drv_usecwait(10000);
1366 bge_reg_clr32(bgep, SERDES_CONTROL_REG, SERDES_CONTROL_TX_DISABLE);
1367 bge_reg_put32(bgep, TX_1000BASEX_AUTONEG_REG, 0);
1368 bge_reg_set32(bgep, ETHERNET_MAC_MODE_REG, ETHERNET_MODE_SEND_CFGS);
1369 drv_usecwait(10);
1370 bge_reg_clr32(bgep, ETHERNET_MAC_MODE_REG, ETHERNET_MODE_SEND_CFGS);
1371 bgep->serdes_lpadv = AUTONEG_CODE_FAULT_ANEG_ERR;
1372 bgep->serdes_status = ~0U;
1373 return (DDI_SUCCESS);
1374 }
1375
1376 /*
1377 * Synchronise the SerDes speed/duplex/autonegotiation capabilities and
1378 * advertisements with the required settings as specified by the various
1379 * param_* variables that can be poked via the NDD interface.
1380 *
1381 * We always reinitalise the SerDes; this should cause the link to go down,
1382 * and then back up again once the link is stable and autonegotiation
1383 * (if enabled) is complete. We should get a link state change interrupt
1384 * somewhere along the way ...
1385 *
1386 * NOTE: SerDes only supports 1000FDX/HDX (with or without pause) so the
1387 * param_* variables relating to lower speeds are ignored.
1388 *
1389 * NOTE: <genlock> must already be held by the caller
1390 */
1391 static int
bge_update_serdes(bge_t * bgep)1392 bge_update_serdes(bge_t *bgep)
1393 {
1394 boolean_t adv_autoneg;
1395 boolean_t adv_pause;
1396 boolean_t adv_asym_pause;
1397 boolean_t adv_1000fdx;
1398 boolean_t adv_1000hdx;
1399
1400 uint32_t serdes;
1401 uint32_t advert;
1402
1403 BGE_TRACE(("bge_update_serdes($%p)", (void *)bgep));
1404
1405 ASSERT(mutex_owned(bgep->genlock));
1406
1407 BGE_DEBUG(("bge_update_serdes: autoneg %d "
1408 "pause %d asym_pause %d "
1409 "1000fdx %d 1000hdx %d "
1410 "100fdx %d 100hdx %d "
1411 "10fdx %d 10hdx %d ",
1412 bgep->param_adv_autoneg,
1413 bgep->param_adv_pause, bgep->param_adv_asym_pause,
1414 bgep->param_adv_1000fdx, bgep->param_adv_1000hdx,
1415 bgep->param_adv_100fdx, bgep->param_adv_100hdx,
1416 bgep->param_adv_10fdx, bgep->param_adv_10hdx));
1417
1418 serdes = advert = 0;
1419
1420 /*
1421 * SerDes settings are normally based on the param_* variables,
1422 * but if any loopback mode is in effect, that takes precedence.
1423 *
1424 * BGE supports MAC-internal loopback, PHY-internal loopback,
1425 * and External loopback at a variety of speeds (with a special
1426 * cable). In all cases, autoneg is turned OFF, full-duplex
1427 * is turned ON, and the speed/mastership is forced.
1428 *
1429 * Note: for the SerDes interface, "PHY" internal loopback is
1430 * interpreted as SerDes internal loopback, and all external
1431 * loopback modes are treated equivalently, as 1Gb/external.
1432 */
1433 switch (bgep->param_loop_mode) {
1434 case BGE_LOOP_NONE:
1435 default:
1436 adv_autoneg = bgep->param_adv_autoneg;
1437 adv_pause = bgep->param_adv_pause;
1438 adv_asym_pause = bgep->param_adv_asym_pause;
1439 adv_1000fdx = bgep->param_adv_1000fdx;
1440 adv_1000hdx = bgep->param_adv_1000hdx;
1441 break;
1442
1443 case BGE_LOOP_INTERNAL_PHY:
1444 serdes |= SERDES_CONTROL_TBI_LOOPBACK;
1445 /* FALLTHRU */
1446 case BGE_LOOP_INTERNAL_MAC:
1447 case BGE_LOOP_EXTERNAL_1000:
1448 case BGE_LOOP_EXTERNAL_100:
1449 case BGE_LOOP_EXTERNAL_10:
1450 adv_autoneg = adv_pause = adv_asym_pause = B_FALSE;
1451 adv_1000fdx = B_TRUE;
1452 adv_1000hdx = B_FALSE;
1453 break;
1454 }
1455
1456 BGE_DEBUG(("bge_update_serdes: autoneg %d "
1457 "pause %d asym_pause %d "
1458 "1000fdx %d 1000hdx %d ",
1459 adv_autoneg,
1460 adv_pause, adv_asym_pause,
1461 adv_1000fdx, adv_1000hdx));
1462
1463 /*
1464 * We should have at least one gigabit technology capability
1465 * set; if not, we select a default of 1000Mb/s full-duplex
1466 */
1467 if (!adv_1000fdx && !adv_1000hdx)
1468 adv_1000fdx = B_TRUE;
1469
1470 /*
1471 * Now transform the adv_* variables into the proper settings
1472 * of the SerDes registers ...
1473 *
1474 * If autonegotiation is (now) not enabled, pretend it's been
1475 * done and failed ...
1476 */
1477 if (!adv_autoneg)
1478 advert |= AUTONEG_CODE_FAULT_ANEG_ERR;
1479
1480 if (adv_1000fdx) {
1481 advert |= AUTONEG_CODE_FULL_DUPLEX;
1482 bgep->param_adv_1000fdx = adv_1000fdx;
1483 bgep->param_link_duplex = LINK_DUPLEX_FULL;
1484 bgep->param_link_speed = 1000;
1485 }
1486 if (adv_1000hdx) {
1487 advert |= AUTONEG_CODE_HALF_DUPLEX;
1488 bgep->param_adv_1000hdx = adv_1000hdx;
1489 bgep->param_link_duplex = LINK_DUPLEX_HALF;
1490 bgep->param_link_speed = 1000;
1491 }
1492
1493 if (adv_pause)
1494 advert |= AUTONEG_CODE_PAUSE;
1495 if (adv_asym_pause)
1496 advert |= AUTONEG_CODE_ASYM_PAUSE;
1497
1498 /*
1499 * Restart the SerDes and write the new values. Note the
1500 * time, so that we can say whether subsequent link state
1501 * changes can be attributed to our reprogramming the SerDes
1502 */
1503 bgep->serdes_advert = advert;
1504 (void) bge_restart_serdes(bgep, B_FALSE);
1505 bge_reg_set32(bgep, SERDES_CONTROL_REG, serdes);
1506
1507 BGE_DEBUG(("bge_update_serdes: serdes |= 0x%x, advert 0x%x",
1508 serdes, advert));
1509 return (DDI_SUCCESS);
1510 }
1511
1512 /*
1513 * Bare-minimum autoneg protocol
1514 *
1515 * This code is only called when the link is up and we're receiving config
1516 * words, which implies that the link partner wants to autonegotiate
1517 * (otherwise, we wouldn't see configs and wouldn't reach this code).
1518 */
1519 static void
bge_autoneg_serdes(bge_t * bgep)1520 bge_autoneg_serdes(bge_t *bgep)
1521 {
1522 boolean_t ack;
1523
1524 bgep->serdes_lpadv = bge_reg_get32(bgep, RX_1000BASEX_AUTONEG_REG);
1525 ack = BIS(bgep->serdes_lpadv, AUTONEG_CODE_ACKNOWLEDGE);
1526
1527 if (!ack) {
1528 /*
1529 * Phase 1: after SerDes reset, we send a few zero configs
1530 * but then stop. Here the partner is sending configs, but
1531 * not ACKing ours; we assume that's 'cos we're not sending
1532 * any. So here we send ours, with ACK already set.
1533 */
1534 bge_reg_put32(bgep, TX_1000BASEX_AUTONEG_REG,
1535 bgep->serdes_advert | AUTONEG_CODE_ACKNOWLEDGE);
1536 bge_reg_set32(bgep, ETHERNET_MAC_MODE_REG,
1537 ETHERNET_MODE_SEND_CFGS);
1538 } else {
1539 /*
1540 * Phase 2: partner has ACKed our configs, so now we can
1541 * stop sending; once our partner also stops sending, we
1542 * can resolve the Tx/Rx configs.
1543 */
1544 bge_reg_clr32(bgep, ETHERNET_MAC_MODE_REG,
1545 ETHERNET_MODE_SEND_CFGS);
1546 }
1547
1548 BGE_DEBUG(("bge_autoneg_serdes: Rx 0x%x %s Tx 0x%x",
1549 bgep->serdes_lpadv,
1550 ack ? "stop" : "send",
1551 bgep->serdes_advert));
1552 }
1553
1554 static boolean_t
bge_check_serdes(bge_t * bgep,boolean_t recheck)1555 bge_check_serdes(bge_t *bgep, boolean_t recheck)
1556 {
1557 uint32_t emac_status;
1558 uint32_t tx_status;
1559 uint32_t lpadv;
1560 boolean_t linkup;
1561 boolean_t linkup_old = bgep->param_link_up;
1562
1563 for (;;) {
1564 /*
1565 * Step 10: BCM5714S, BCM5715S only
1566 * Don't call function bge_autoneg_serdes() as
1567 * RX_1000BASEX_AUTONEG_REG (0x0448) is not applicable
1568 * to BCM5705, BCM5788, BCM5721, BCM5751, BCM5752,
1569 * BCM5714, BCM5715, and BCM57765 family devices.
1570 */
1571 if (DEVICE_5717_SERIES_CHIPSETS(bgep) ||
1572 DEVICE_5725_SERIES_CHIPSETS(bgep) ||
1573 DEVICE_5714_SERIES_CHIPSETS(bgep) ||
1574 DEVICE_57765_SERIES_CHIPSETS(bgep)) {
1575 tx_status = bge_reg_get32(bgep,
1576 TRANSMIT_MAC_STATUS_REG);
1577 linkup = BIS(tx_status, TRANSMIT_STATUS_LINK_UP);
1578 emac_status = bge_reg_get32(bgep,
1579 ETHERNET_MAC_STATUS_REG);
1580 bgep->serdes_status = emac_status;
1581 /* clear write-one-to-clear bits in MAC status */
1582 if ((emac_status & ETHERNET_STATUS_MI_COMPLETE) &&
1583 (DEVICE_5717_SERIES_CHIPSETS(bgep) ||
1584 DEVICE_5725_SERIES_CHIPSETS(bgep))) {
1585 emac_status |= ETHERNET_STATUS_SYNC_CHANGED |
1586 ETHERNET_STATUS_CFG_CHANGED;
1587 }
1588 bge_reg_put32(bgep,
1589 ETHERNET_MAC_STATUS_REG, emac_status);
1590 /*
1591 * If the link status has not changed then then
1592 * break. If it has loop around and recheck again.
1593 * Keep looping until the link status has not
1594 * changed.
1595 */
1596 if ((linkup && linkup_old) ||
1597 (!linkup && !linkup_old)) {
1598 break;
1599 }
1600 if (linkup)
1601 linkup_old = B_TRUE;
1602 else
1603 linkup_old = B_FALSE;
1604 recheck = B_TRUE;
1605 } else {
1606 /*
1607 * Step 10: others
1608 * read & clear the main (Ethernet) MAC status
1609 * (the relevant bits of this are write-one-to-clear).
1610 */
1611 emac_status = bge_reg_get32(bgep,
1612 ETHERNET_MAC_STATUS_REG);
1613 bge_reg_put32(bgep,
1614 ETHERNET_MAC_STATUS_REG, emac_status);
1615
1616 BGE_DEBUG(("bge_check_serdes: link %d/%s, "
1617 "MAC status 0x%x (was 0x%x)",
1618 bgep->link_state, UPORDOWN(bgep->param_link_up),
1619 emac_status, bgep->serdes_status));
1620
1621 /*
1622 * We will only consider the link UP if all the readings
1623 * are consistent and give meaningful results ...
1624 */
1625 bgep->serdes_status = emac_status;
1626 linkup = BIS(emac_status,
1627 ETHERNET_STATUS_SIGNAL_DETECT);
1628 linkup &= BIS(emac_status, ETHERNET_STATUS_PCS_SYNCHED);
1629
1630 /*
1631 * Now some fiddling with the interpretation:
1632 * if there's been an error at the PCS level, treat
1633 * it as a link change (the h/w doesn't do this)
1634 *
1635 * if there's been a change, but it's only a PCS
1636 * sync change (not a config change), AND the link
1637 * already was & is still UP, then ignore the
1638 * change
1639 */
1640 if (BIS(emac_status, ETHERNET_STATUS_PCS_ERROR))
1641 emac_status |= ETHERNET_STATUS_LINK_CHANGED;
1642 else if (BIC(emac_status, ETHERNET_STATUS_CFG_CHANGED))
1643 if (bgep->param_link_up && linkup)
1644 emac_status &=
1645 ~ETHERNET_STATUS_LINK_CHANGED;
1646
1647 BGE_DEBUG(("bge_check_serdes: status 0x%x => 0x%x %s",
1648 bgep->serdes_status, emac_status,
1649 UPORDOWN(linkup)));
1650
1651 /*
1652 * If we're receiving configs, run the autoneg protocol
1653 */
1654 if (linkup && BIS(emac_status,
1655 ETHERNET_STATUS_RECEIVING_CFG))
1656 bge_autoneg_serdes(bgep);
1657
1658 /*
1659 * If the SerDes status hasn't changed, we're done ...
1660 */
1661 if (BIC(emac_status, ETHERNET_STATUS_LINK_CHANGED))
1662 break;
1663
1664 /*
1665 * Go round again until we no longer see a change ...
1666 */
1667 recheck = B_TRUE;
1668 }
1669 }
1670
1671 /*
1672 * If we're not forcing a recheck (i.e. the link state was already
1673 * known), and we didn't see the hardware flag a change, there's
1674 * no more to do (and we tell the caller nothing happened).
1675 */
1676 if (!recheck)
1677 return (B_FALSE);
1678
1679 /*
1680 * Don't resolve autoneg until we're no longer receiving configs
1681 */
1682 if (linkup && BIS(emac_status, ETHERNET_STATUS_RECEIVING_CFG))
1683 return (B_FALSE);
1684
1685 /*
1686 * Assume very little ...
1687 */
1688 bgep->param_lp_autoneg = B_FALSE;
1689 bgep->param_lp_1000fdx = B_FALSE;
1690 bgep->param_lp_1000hdx = B_FALSE;
1691 bgep->param_lp_100fdx = B_FALSE;
1692 bgep->param_lp_100hdx = B_FALSE;
1693 bgep->param_lp_10fdx = B_FALSE;
1694 bgep->param_lp_10hdx = B_FALSE;
1695 bgep->param_lp_pause = B_FALSE;
1696 bgep->param_lp_asym_pause = B_FALSE;
1697 bgep->param_link_autoneg = B_FALSE;
1698 bgep->param_link_tx_pause = B_FALSE;
1699 if (bgep->param_adv_autoneg)
1700 bgep->param_link_rx_pause = B_FALSE;
1701 else
1702 bgep->param_link_rx_pause = bgep->param_adv_pause;
1703
1704 /*
1705 * Discover all the link partner's abilities.
1706 */
1707 lpadv = bgep->serdes_lpadv;
1708 if (lpadv != 0 && BIC(lpadv, AUTONEG_CODE_FAULT_MASK)) {
1709 /*
1710 * No fault, so derive partner's capabilities
1711 */
1712 bgep->param_lp_autoneg = B_TRUE;
1713 bgep->param_lp_1000fdx = BIS(lpadv, AUTONEG_CODE_FULL_DUPLEX);
1714 bgep->param_lp_1000hdx = BIS(lpadv, AUTONEG_CODE_HALF_DUPLEX);
1715 bgep->param_lp_pause = BIS(lpadv, AUTONEG_CODE_PAUSE);
1716 bgep->param_lp_asym_pause = BIS(lpadv, AUTONEG_CODE_ASYM_PAUSE);
1717
1718 /*
1719 * Pause direction resolution
1720 */
1721 bgep->param_link_autoneg = B_TRUE;
1722 if (bgep->param_adv_pause &&
1723 bgep->param_lp_pause) {
1724 bgep->param_link_tx_pause = B_TRUE;
1725 bgep->param_link_rx_pause = B_TRUE;
1726 }
1727 if (bgep->param_adv_asym_pause &&
1728 bgep->param_lp_asym_pause) {
1729 if (bgep->param_adv_pause)
1730 bgep->param_link_rx_pause = B_TRUE;
1731 if (bgep->param_lp_pause)
1732 bgep->param_link_tx_pause = B_TRUE;
1733 }
1734 }
1735
1736 /*
1737 * Step 12: update ndd-visible state parameters, BUT!
1738 * we don't transfer the new state to <link_state> just yet;
1739 * instead we mark the <link_state> as UNKNOWN, and our caller
1740 * will resolve it once the status has stopped changing and
1741 * been stable for several seconds.
1742 */
1743 BGE_DEBUG(("bge_check_serdes: link was %s speed %d duplex %d",
1744 UPORDOWN(bgep->param_link_up),
1745 bgep->param_link_speed,
1746 bgep->param_link_duplex));
1747
1748 if (linkup) {
1749 bgep->param_link_up = B_TRUE;
1750 bgep->param_link_speed = 1000;
1751 if (bgep->param_adv_1000fdx)
1752 bgep->param_link_duplex = LINK_DUPLEX_FULL;
1753 else
1754 bgep->param_link_duplex = LINK_DUPLEX_HALF;
1755 if (bgep->param_lp_autoneg && !bgep->param_lp_1000fdx)
1756 bgep->param_link_duplex = LINK_DUPLEX_HALF;
1757 } else {
1758 bgep->param_link_up = B_FALSE;
1759 bgep->param_link_speed = 0;
1760 bgep->param_link_duplex = LINK_DUPLEX_UNKNOWN;
1761 }
1762 bgep->link_state = LINK_STATE_UNKNOWN;
1763
1764 bge_log(bgep, "bge_check_serdes: link now %s speed %d duplex %d",
1765 UPORDOWN(bgep->param_link_up),
1766 bgep->param_link_speed,
1767 bgep->param_link_duplex);
1768
1769 return (B_TRUE);
1770 }
1771
1772 static const phys_ops_t serdes_ops = {
1773 bge_restart_serdes,
1774 bge_update_serdes,
1775 bge_check_serdes
1776 };
1777
1778 /*
1779 * ========== Exported physical layer control routines ==========
1780 */
1781
1782 #undef BGE_DBG
1783 #define BGE_DBG BGE_DBG_PHYS /* debug flag for this code */
1784
1785 /*
1786 * Here we have to determine which media we're using (copper or serdes).
1787 * Once that's done, we can initialise the physical layer appropriately.
1788 */
1789 int
bge_phys_init(bge_t * bgep)1790 bge_phys_init(bge_t *bgep)
1791 {
1792 uint32_t regval;
1793
1794 BGE_TRACE(("bge_phys_init($%p)", (void *)bgep));
1795
1796 mutex_enter(bgep->genlock);
1797
1798 /*
1799 * Probe for the (internal) PHY. If it's not there, we'll assume
1800 * that this is a 5703/4S, with a SerDes interface rather than
1801 * a PHY. BCM5714S/BCM5715S are not supported.It are based on
1802 * BCM800x PHY.
1803 */
1804 bgep->phy_mii_addr = 1;
1805
1806 if (DEVICE_5717_SERIES_CHIPSETS(bgep)) {
1807 bgep->phy_mii_addr = (bgep->pci_func + 1);
1808 regval = bge_reg_get32(bgep, SGMII_STATUS_REG);
1809 if (regval & MEDIA_SELECTION_MODE)
1810 bgep->phy_mii_addr += 7; /* sgmii */
1811 }
1812
1813 if (bge_phy_probe(bgep)) {
1814 bgep->chipid.flags &= ~CHIP_FLAG_SERDES;
1815 bgep->physops = &copper_ops;
1816 } else {
1817 bgep->chipid.flags |= CHIP_FLAG_SERDES;
1818 bgep->physops = &serdes_ops;
1819 }
1820
1821 if ((*bgep->physops->phys_restart)(bgep, B_FALSE) != DDI_SUCCESS) {
1822 mutex_exit(bgep->genlock);
1823 return (EIO);
1824 }
1825 if (bge_check_acc_handle(bgep, bgep->io_handle) != DDI_FM_OK) {
1826 mutex_exit(bgep->genlock);
1827 return (EIO);
1828 }
1829 mutex_exit(bgep->genlock);
1830 return (0);
1831 }
1832
1833 /*
1834 * Reset the physical layer
1835 */
1836 void
bge_phys_reset(bge_t * bgep)1837 bge_phys_reset(bge_t *bgep)
1838 {
1839 BGE_TRACE(("bge_phys_reset($%p)", (void *)bgep));
1840
1841 mutex_enter(bgep->genlock);
1842 if ((*bgep->physops->phys_restart)(bgep, B_FALSE) != DDI_SUCCESS)
1843 ddi_fm_service_impact(bgep->devinfo, DDI_SERVICE_UNAFFECTED);
1844 if (bge_check_acc_handle(bgep, bgep->io_handle) != DDI_FM_OK)
1845 ddi_fm_service_impact(bgep->devinfo, DDI_SERVICE_UNAFFECTED);
1846 mutex_exit(bgep->genlock);
1847 }
1848
1849 /*
1850 * Reset and power off the physical layer.
1851 *
1852 * Another RESET should get it back to working, but it may take a few
1853 * seconds it may take a few moments to return to normal operation ...
1854 */
1855 int
bge_phys_idle(bge_t * bgep)1856 bge_phys_idle(bge_t *bgep)
1857 {
1858 BGE_TRACE(("bge_phys_idle($%p)", (void *)bgep));
1859
1860 ASSERT(mutex_owned(bgep->genlock));
1861 return ((*bgep->physops->phys_restart)(bgep, B_TRUE));
1862 }
1863
1864 /*
1865 * Synchronise the PHYSICAL layer's speed/duplex/autonegotiation capabilities
1866 * and advertisements with the required settings as specified by the various
1867 * param_* variables that can be poked via the NDD interface.
1868 *
1869 * We always reset the PHYSICAL layer and reprogram *all* relevant registers.
1870 * This is expected to cause the link to go down, and then back up again once
1871 * the link is stable and autonegotiation (if enabled) is complete. We should
1872 * get a link state change interrupt somewhere along the way ...
1873 *
1874 * NOTE: <genlock> must already be held by the caller
1875 */
1876 int
bge_phys_update(bge_t * bgep)1877 bge_phys_update(bge_t *bgep)
1878 {
1879 BGE_TRACE(("bge_phys_update($%p)", (void *)bgep));
1880
1881 ASSERT(mutex_owned(bgep->genlock));
1882 return ((*bgep->physops->phys_update)(bgep));
1883 }
1884
1885 #undef BGE_DBG
1886 #define BGE_DBG BGE_DBG_LINK /* debug flag for this code */
1887
1888 /*
1889 * Read the link status and determine whether anything's changed ...
1890 *
1891 * This routine should be called whenever the chip flags a change
1892 * in the hardware link state.
1893 *
1894 * This routine returns B_FALSE if the link state has not changed,
1895 * returns B_TRUE when the change to the new state should be accepted.
1896 * In such a case, the param_* variables give the new hardware state,
1897 * which the caller should use to update link_state etc.
1898 *
1899 * The caller must already hold <genlock>
1900 */
1901 boolean_t
bge_phys_check(bge_t * bgep)1902 bge_phys_check(bge_t *bgep)
1903 {
1904 BGE_TRACE(("bge_phys_check($%p)", (void *)bgep));
1905
1906 ASSERT(mutex_owned(bgep->genlock));
1907
1908 /*
1909 * Force a link recheck if current state is unknown.
1910 * phys_check() returns TRUE if the link status changed,
1911 * FALSE otherwise.
1912 */
1913 return ((*bgep->physops->phys_check)(bgep,
1914 (bgep->link_state == LINK_STATE_UNKNOWN)));
1915 }
1916
1917 mac_ether_media_t
bge_phys_media(bge_t * bgep)1918 bge_phys_media(bge_t *bgep)
1919 {
1920 switch (bgep->link_state) {
1921 case LINK_STATE_UP:
1922 break;
1923 case LINK_STATE_DOWN:
1924 return (ETHER_MEDIA_NONE);
1925 case LINK_STATE_UNKNOWN:
1926 default:
1927 return (ETHER_MEDIA_UNKNOWN);
1928 }
1929
1930 if ((bgep->chipid.flags & CHIP_FLAG_SERDES) != 0) {
1931 switch (bgep->param_link_speed) {
1932 case 1000:
1933 return (ETHER_MEDIA_1000BASE_X);
1934 case 100:
1935 return (ETHER_MEDIA_100BASE_FX);
1936 default:
1937 break;
1938 }
1939 } else {
1940 switch (bgep->param_link_speed) {
1941 case 1000:
1942 return (ETHER_MEDIA_1000BASE_T);
1943 case 100:
1944 /*
1945 * All NetExtreme I docs we can find suggest that the
1946 * PHY never supported anything other than 100BASE-TX so
1947 * we don't further interrogate the device.
1948 */
1949 return (ETHER_MEDIA_100BASE_TX);
1950 case 10:
1951 return (ETHER_MEDIA_10BASE_T);
1952 default:
1953 break;
1954 }
1955 }
1956
1957 return (ETHER_MEDIA_UNKNOWN);
1958 }
1959