ReactOS 0.4.15-dev-7961-gdcf9eb0
phy.c
Go to the documentation of this file.
1/*
2 * PROJECT: ReactOS nVidia nForce Ethernet Controller Driver
3 * LICENSE: GPL-2.0-or-later (https://spdx.org/licenses/GPL-2.0-or-later)
4 * PURPOSE: PHY layer setup and management
5 * COPYRIGHT: Copyright 2021-2022 Dmitry Borisov <di.sean@protonmail.com>
6 */
7
8/*
9 * HW access code was taken from the Linux forcedeth driver
10 * Copyright (C) 2003,4,5 Manfred Spraul
11 * Copyright (C) 2004 Andrew de Quincey
12 * Copyright (C) 2004 Carl-Daniel Hailfinger
13 * Copyright (c) 2004,2005,2006,2007,2008,2009 NVIDIA Corporation
14 */
15
16/* INCLUDES *******************************************************************/
17
18#include "nvnet.h"
19
20#define NDEBUG
21#include "debug.h"
22
23/* GLOBALS ********************************************************************/
24
27 _In_ PNVNET_ADAPTER Adapter,
28 _In_ ULONG PhyAddress,
29 _In_ ULONG RegAddress,
31{
32 ULONG i;
33
35
37 {
40 }
41
42 NV_WRITE(Adapter, NvRegMIIData, Data);
44 NVREG_MIICTL_WRITE | (PhyAddress << NVREG_MIICTL_ADDRSHIFT) | RegAddress);
45
46 for (i = NV_MIIPHY_DELAYMAX; i > 0; --i)
47 {
49
51 break;
52 }
53 if (i == 0)
54 {
55 return FALSE;
56 }
57
58 return TRUE;
59}
60
63 _In_ PNVNET_ADAPTER Adapter,
64 _In_ ULONG PhyAddress,
65 _In_ ULONG RegAddress,
67{
68 ULONG i;
69
71
73 {
76 }
77
78 NV_WRITE(Adapter, NvRegMIIControl, (PhyAddress << NVREG_MIICTL_ADDRSHIFT) | RegAddress);
79
80 for (i = NV_MIIPHY_DELAYMAX; i > 0; --i)
81 {
83
85 break;
86 }
87 if (i == 0)
88 {
89 *Data = 0;
90 return FALSE;
91 }
92
94 {
95 *Data = 0;
96 return FALSE;
97 }
98
99 *Data = NV_READ(Adapter, NvRegMIIData);
100 return TRUE;
101}
102
103static
104CODE_SEG("PAGE")
107 _In_ PNVNET_ADAPTER Adapter)
108{
109 ULONG i;
110 const struct
111 {
113 ULONG Data;
114 } Sequence[] =
115 {
123 };
124
125 PAGED_CODE();
126
127 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
128
129 for (i = 0; i < RTL_NUMBER_OF(Sequence); ++i)
130 {
131 if (!MiiWrite(Adapter, Adapter->PhyAddress, Sequence[i].Register, Sequence[i].Data))
132 return FALSE;
133 }
134
135 return TRUE;
136}
137
138static
139CODE_SEG("PAGE")
142 _In_ PNVNET_ADAPTER Adapter)
143{
144 ULONG PowerState, MiiRegister;
145
146 PAGED_CODE();
147
148 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
149
151
153 NdisMSleep(25000);
154
156 NdisMSleep(25000);
157
158 MiiRead(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG6, &MiiRegister);
159 MiiRegister |= PHY_REALTEK_INIT9;
160 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG6, MiiRegister))
161 return FALSE;
162
163 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG1, PHY_REALTEK_INIT10))
164 return FALSE;
165
166 MiiRead(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG7, &MiiRegister);
167 if (!(MiiRegister & PHY_REALTEK_INIT11))
168 {
169 MiiRegister |= PHY_REALTEK_INIT11;
170 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG7, MiiRegister))
171 return FALSE;
172 }
173
174 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG1, PHY_REALTEK_INIT1))
175 return FALSE;
176
177 return TRUE;
178}
179
180static
181CODE_SEG("PAGE")
184 _In_ PNVNET_ADAPTER Adapter,
185 _In_ BOOLEAN DisableCrossoverDetection)
186{
187 ULONG MiiRegister;
188
189 PAGED_CODE();
190
191 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
192
193 if (Adapter->Features & DEV_NEED_PHY_INIT_FIX)
194 {
195 MiiRead(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG6, &MiiRegister);
196 MiiRegister |= PHY_REALTEK_INIT7;
197 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG6, MiiRegister))
198 return FALSE;
199 }
200
201 if (DisableCrossoverDetection)
202 {
203 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG1, PHY_REALTEK_INIT3))
204 return FALSE;
205
206 MiiRead(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG2, &MiiRegister);
207 MiiRegister &= ~PHY_REALTEK_INIT_MSK1;
208 MiiRegister |= PHY_REALTEK_INIT3;
209 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG2, MiiRegister))
210 return FALSE;
211
212 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_REALTEK_INIT_REG1, PHY_REALTEK_INIT1))
213 return FALSE;
214 }
215
216 return TRUE;
217}
218
219static
220CODE_SEG("PAGE")
223 _In_ PNVNET_ADAPTER Adapter,
224 _In_ ULONG PhyInterface)
225{
226 ULONG MiiRegister;
227
228 PAGED_CODE();
229
230 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
231
232 if (PhyInterface & PHY_RGMII)
233 {
234 MiiRead(Adapter, Adapter->PhyAddress, PHY_CICADA_INIT_REG2, &MiiRegister);
235 MiiRegister &= ~(PHY_CICADA_INIT1 | PHY_CICADA_INIT2);
236 MiiRegister |= (PHY_CICADA_INIT3 | PHY_CICADA_INIT4);
237 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_CICADA_INIT_REG2, MiiRegister))
238 return FALSE;
239
240 MiiRead(Adapter, Adapter->PhyAddress, PHY_CICADA_INIT_REG3, &MiiRegister);
241 MiiRegister |= PHY_CICADA_INIT5;
242 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_CICADA_INIT_REG3, MiiRegister))
243 return FALSE;
244 }
245
246 MiiRead(Adapter, Adapter->PhyAddress, PHY_CICADA_INIT_REG1, &MiiRegister);
247 MiiRegister |= PHY_CICADA_INIT6;
248 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_CICADA_INIT_REG1, MiiRegister))
249 return FALSE;
250
251 return TRUE;
252}
253
254static
255CODE_SEG("PAGE")
258 _In_ PNVNET_ADAPTER Adapter)
259{
260 ULONG MiiRegister;
261
262 PAGED_CODE();
263
264 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
265
266 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG1, PHY_VITESSE_INIT1))
267 return FALSE;
268
269 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG2, PHY_VITESSE_INIT2))
270 return FALSE;
271
272 MiiRead(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG4, &MiiRegister);
273 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG4, MiiRegister))
274 return FALSE;
275
276 MiiRead(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG3, &MiiRegister);
277 MiiRegister &= ~PHY_VITESSE_INIT_MSK1;
278 MiiRegister |= PHY_VITESSE_INIT3;
279 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG3, MiiRegister))
280 return FALSE;
281
282 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG2, PHY_VITESSE_INIT4))
283 return FALSE;
284
285 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG2, PHY_VITESSE_INIT5))
286 return FALSE;
287
288 MiiRead(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG4, &MiiRegister);
289 MiiRegister &= ~PHY_VITESSE_INIT_MSK1;
290 MiiRegister |= PHY_VITESSE_INIT3;
291 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG4, MiiRegister))
292 return FALSE;
293
294 MiiRead(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG3, &MiiRegister);
295 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG3, MiiRegister))
296 return FALSE;
297
298 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG2, PHY_VITESSE_INIT6))
299 return FALSE;
300
301 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG2, PHY_VITESSE_INIT7))
302 return FALSE;
303
304 MiiRead(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG4, &MiiRegister);
305 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG4, MiiRegister))
306 return FALSE;
307
308 MiiRead(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG3, &MiiRegister);
309 MiiRegister &= ~PHY_VITESSE_INIT_MSK2;
310 MiiRegister |= PHY_VITESSE_INIT8;
311 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG3, MiiRegister))
312 return FALSE;
313
314 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG2, PHY_VITESSE_INIT9))
315 return FALSE;
316
317 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_VITESSE_INIT_REG1, PHY_VITESSE_INIT10))
318 return FALSE;
319
320 return TRUE;
321}
322
323static
324CODE_SEG("PAGE")
327 _In_ PNVNET_ADAPTER Adapter,
328 _In_ ULONG ControlSetup)
329{
330 ULONG Tries = 0, MiiControl = MII_CR_RESET | ControlSetup;
331
332 PAGED_CODE();
333
334 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
335
336 if (!MiiWrite(Adapter, Adapter->PhyAddress, MII_CONTROL, MiiControl))
337 return FALSE;
338
339 NdisMSleep(500000);
340
341 do
342 {
343 NdisMSleep(10000);
344
345 MiiRead(Adapter, Adapter->PhyAddress, MII_CONTROL, &MiiControl);
346
347 if (Tries++ > 100)
348 return FALSE;
349 }
350 while (MiiControl & MII_CR_RESET);
351
352 return TRUE;
353}
354
355static
356CODE_SEG("PAGE")
359 _In_ PNVNET_ADAPTER Adapter)
360{
361 ULONG PhyInterface, MiiRegister, MiiStatus, MiiControl;
362
363 PAGED_CODE();
364
365 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
366
367 /* PHY errata for E3016 PHY */
368 if (Adapter->PhyModel == PHY_MODEL_MARVELL_E3016)
369 {
370 MiiRead(Adapter, Adapter->PhyAddress, PHY_MARVELL_INIT_REG1, &MiiRegister);
371 MiiRegister &= ~PHY_MARVELL_E3016_INITMASK;
372 if (!MiiWrite(Adapter, Adapter->PhyAddress, PHY_MARVELL_INIT_REG1, MiiRegister))
373 {
374 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed\n"));
375 return NDIS_STATUS_FAILURE;
376 }
377 }
378
379 if (Adapter->PhyOui == PHY_OUI_REALTEK)
380 {
381 if (Adapter->PhyModel == PHY_MODEL_REALTEK_8211 &&
382 Adapter->PhyRevision == PHY_REV_REALTEK_8211B)
383 {
384 if (!PhyInitRealtek8211b(Adapter))
385 {
386 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed\n"));
387 return NDIS_STATUS_FAILURE;
388 }
389 }
390 else if (Adapter->PhyModel == PHY_MODEL_REALTEK_8211 &&
391 Adapter->PhyRevision == PHY_REV_REALTEK_8211C)
392 {
393 if (!PhyInitRealtek8211c(Adapter))
394 {
395 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed\n"));
396 return NDIS_STATUS_FAILURE;
397 }
398 }
399 else if (Adapter->PhyModel == PHY_MODEL_REALTEK_8201)
400 {
401 if (!PhyInitRealtek8201(Adapter, FALSE))
402 {
403 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed\n"));
404 return NDIS_STATUS_FAILURE;
405 }
406 }
407 }
408
409 /* Set advertise register */
410 MiiRead(Adapter, Adapter->PhyAddress, MII_AUTONEG_ADVERTISE, &MiiRegister);
411 if (Adapter->Flags & NV_FORCE_SPEED_AND_DUPLEX)
412 {
415
416 if (Adapter->Flags & NV_USER_SPEED_100)
417 {
418 if (Adapter->Flags & NV_FORCE_FULL_DUPLEX)
419 MiiRegister |= MII_ADV_100T_FD;
420 else
421 MiiRegister |= MII_ADV_100T_HD;
422 }
423 else
424 {
425 if (Adapter->Flags & NV_FORCE_FULL_DUPLEX)
426 MiiRegister |= MII_ADV_10T_FD;
427 else
428 MiiRegister |= MII_ADV_10T_HD;
429 }
430
431 Adapter->PauseFlags &= ~(NV_PAUSEFRAME_AUTONEG | NV_PAUSEFRAME_RX_ENABLE |
433 if (Adapter->PauseFlags & NV_PAUSEFRAME_RX_REQ)
434 {
435 /* For RX we set both advertisements but disable TX pause */
436 MiiRegister |= MII_ADV_PAUSE_SYM | MII_ADV_PAUSE_ASYM;
437 Adapter->PauseFlags |= NV_PAUSEFRAME_RX_ENABLE;
438 }
439 if (Adapter->PauseFlags & NV_PAUSEFRAME_TX_REQ)
440 {
441 MiiRegister |= MII_ADV_PAUSE_ASYM;
442 Adapter->PauseFlags |= NV_PAUSEFRAME_TX_ENABLE;
443 }
444 }
445 else
446 {
449 }
450 if (!MiiWrite(Adapter, Adapter->PhyAddress, MII_AUTONEG_ADVERTISE, MiiRegister))
451 {
452 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed!\n"));
453 return NDIS_STATUS_FAILURE;
454 }
455
456 /* Get PHY interface type */
457 PhyInterface = NV_READ(Adapter, NvRegPhyInterface);
458
459 /* See if gigabit PHY */
460 MiiRead(Adapter, Adapter->PhyAddress, MII_STATUS, &MiiStatus);
461 if (MiiStatus & PHY_GIGABIT)
462 {
463 ULONG MiiControl1000;
464
465 Adapter->Flags |= NV_GIGABIT_PHY;
466
467 MiiRead(Adapter, Adapter->PhyAddress, MII_MASTER_SLAVE_CONTROL, &MiiControl1000);
468 MiiControl1000 &= ~MII_MS_CR_1000T_HD;
469 if ((PhyInterface & PHY_RGMII) && !(Adapter->Flags & NV_FORCE_SPEED_AND_DUPLEX))
470 MiiControl1000 |= MII_MS_CR_1000T_FD;
471 else
472 MiiControl1000 &= ~MII_MS_CR_1000T_FD;
473 if (!MiiWrite(Adapter, Adapter->PhyAddress, MII_MASTER_SLAVE_CONTROL, MiiControl1000))
474 {
475 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed\n"));
476 return NDIS_STATUS_FAILURE;
477 }
478 }
479 else
480 {
481 Adapter->Flags &= ~NV_GIGABIT_PHY;
482 }
483
484 MiiRead(Adapter, Adapter->PhyAddress, MII_CONTROL, &MiiControl);
485 MiiControl |= MII_CR_AUTONEG;
486 if (Adapter->PhyOui == PHY_OUI_REALTEK &&
487 Adapter->PhyModel == PHY_MODEL_REALTEK_8211 &&
488 Adapter->PhyRevision == PHY_REV_REALTEK_8211C)
489 {
490 /* Start auto-negation since we already performed HW reset above */
491 MiiControl |= MII_CR_AUTONEG_RESTART;
492 if (!MiiWrite(Adapter, Adapter->PhyAddress, MII_CONTROL, MiiControl))
493 {
494 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed\n"));
495 return NDIS_STATUS_FAILURE;
496 }
497 }
498 else
499 {
500 /* Reset the PHY (certain PHYs need BMCR to be setup with reset) */
501 if (!PhyReset(Adapter, MiiControl))
502 {
503 NDIS_DbgPrint(MAX_TRACE, ("PHY reset failed\n"));
504 return NDIS_STATUS_FAILURE;
505 }
506 }
507
508 /* PHY vendor specific configuration */
509 if (Adapter->PhyOui == PHY_OUI_CICADA)
510 {
511 if (!PhyInitCicadaSemiconductor(Adapter, PhyInterface))
512 {
513 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed\n"));
514 return NDIS_STATUS_FAILURE;
515 }
516 }
517 else if (Adapter->PhyOui == PHY_OUI_VITESSE)
518 {
519 if (!PhyInitVitesseSemiconductor(Adapter))
520 {
521 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed\n"));
522 return NDIS_STATUS_FAILURE;
523 }
524 }
525 else if (Adapter->PhyOui == PHY_OUI_REALTEK)
526 {
527 if (Adapter->PhyModel == PHY_MODEL_REALTEK_8211 &&
528 Adapter->PhyRevision == PHY_REV_REALTEK_8211B)
529 {
530 /* Reset could have cleared these out, set them back */
531 if (!PhyInitRealtek8211b(Adapter))
532 {
533 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed\n"));
534 return NDIS_STATUS_FAILURE;
535 }
536 }
537 else if (Adapter->PhyModel == PHY_MODEL_REALTEK_8201)
538 {
539 if (!PhyInitRealtek8201(Adapter, TRUE))
540 {
541 NDIS_DbgPrint(MAX_TRACE, ("PHY init failed\n"));
542 return NDIS_STATUS_FAILURE;
543 }
544 }
545 }
546
547 /* Some PHYs clear out pause advertisement on reset, set it back */
548 MiiWrite(Adapter, Adapter->PhyAddress, MII_AUTONEG_ADVERTISE, MiiRegister);
549
550 /* Restart auto-negotiation */
551 MiiRead(Adapter, Adapter->PhyAddress, MII_CONTROL, &MiiControl);
552 MiiControl |= (MII_CR_AUTONEG_RESTART | MII_CR_AUTONEG);
553 if (!MiiWrite(Adapter, Adapter->PhyAddress, MII_CONTROL, MiiControl))
554 return NDIS_STATUS_FAILURE;
555
556 return NDIS_STATUS_SUCCESS;
557}
558
559static
560CODE_SEG("PAGE")
563 _Inout_ PNVNET_ADAPTER Adapter)
564{
565 ULONG Phy;
566
567 PAGED_CODE();
568
569 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
570
571 for (Phy = 1; Phy <= 32; ++Phy)
572 {
573 ULONG PhyAddress = Phy & 0x1F; /* Check the PHY 0 last */
574 ULONG PhyIdLow, PhyIdHigh;
575
576 if (!MiiRead(Adapter, PhyAddress, MII_PHY_ID1, &PhyIdLow))
577 continue;
578 if (PhyIdLow == 0xFFFF)
579 continue;
580
581 if (!MiiRead(Adapter, PhyAddress, MII_PHY_ID2, &PhyIdHigh))
582 continue;
583 if (PhyIdHigh == 0xFFFF)
584 continue;
585
586 Adapter->PhyAddress = PhyAddress;
587 Adapter->PhyModel = PhyIdHigh & PHYID2_MODEL_MASK;
588 Adapter->PhyOui = ((PhyIdLow & PHYID1_OUI_MASK) << PHYID1_OUI_SHFT) |
589 ((PhyIdHigh & PHYID2_OUI_MASK) >> PHYID2_OUI_SHFT);
590
591 /* Realtek hardcoded PhyIdLow to all zero's on certain PHYs */
592 if (Adapter->PhyOui == PHY_OUI_REALTEK2)
593 Adapter->PhyOui = PHY_OUI_REALTEK;
594
595 /* Setup PHY revision for Realtek */
596 if (Adapter->PhyOui == PHY_OUI_REALTEK && Adapter->PhyModel == PHY_MODEL_REALTEK_8211)
597 {
598 ULONG PhyRevision;
599
600 MiiRead(Adapter, PhyAddress, PHY_REALTEK_REVISION, &PhyRevision);
601 Adapter->PhyRevision = PhyRevision & PHY_REV_MASK;
602 }
603
604 NDIS_DbgPrint(MIN_TRACE, ("Found PHY %X %X %X\n",
605 Adapter->PhyAddress,
606 Adapter->PhyModel,
607 Adapter->PhyOui));
608 break;
609 }
610 if (Phy == 33)
611 {
612 return FALSE;
613 }
614
615 return TRUE;
616}
617
618static
619CODE_SEG("PAGE")
622 _Inout_ PNVNET_ADAPTER Adapter)
623{
624 ULONG i;
625
626 PAGED_CODE();
627
628 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
629
630 for (i = 10; i > 0; --i)
631 {
634 {
635 break;
636 }
637
638 NdisMSleep(500000);
639 }
640 if (i == 0)
641 {
642 return FALSE;
643 }
644
645 for (i = 0; i < 2; ++i)
646 {
647 ULONG TxControl = NV_READ(Adapter, NvRegTransmitterControl);
648
650
651 /* Verify that the semaphore was acquired */
652 TxControl = NV_READ(Adapter, NvRegTransmitterControl);
655 {
656 Adapter->Flags |= NV_UNIT_SEMAPHORE_ACQUIRED;
657 return TRUE;
658 }
659
661 }
662
663 return FALSE;
664}
665
666VOID
668 _In_ PNVNET_ADAPTER Adapter)
669{
670 if (Adapter->Flags & NV_UNIT_SEMAPHORE_ACQUIRED)
671 {
672 ULONG TxControl;
673
674 TxControl = NV_READ(Adapter, NvRegTransmitterControl);
675 TxControl &= ~NVREG_XMITCTL_HOST_SEMA_ACQ;
676 NV_WRITE(Adapter, NvRegTransmitterControl, TxControl);
677 }
678}
679
680static
681CODE_SEG("PAGE")
684 _In_ PNVNET_ADAPTER Adapter,
686{
687 ULONG i, DataReady, DataReady2;
688
689 PAGED_CODE();
690
691 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
692
693 DataReady = NV_READ(Adapter, NvRegTransmitterControl);
694
697
698 for (i = 100000; i > 0; --i)
699 {
700 DataReady2 = NV_READ(Adapter, NvRegTransmitterControl);
701
702 if ((DataReady & NVREG_XMITCTL_DATA_READY) != (DataReady2 & NVREG_XMITCTL_DATA_READY))
703 {
704 break;
705 }
706
708 }
709 if (i == 0 || DataReady2 & NVREG_XMITCTL_DATA_ERROR)
710 {
711 return FALSE;
712 }
713
715
716 return TRUE;
717}
718
719static
722 _In_ PNVNET_ADAPTER Adapter,
723 _Out_ PULONG MiiAdvertise,
724 _Out_ PULONG MiiLinkPartnerAbility,
725 _Out_ PULONG LinkSpeed,
726 _Out_ PBOOLEAN FullDuplex)
727{
728 ULONG MiiStatus, AdvLpa;
729
730 *MiiAdvertise = 0;
731 *MiiLinkPartnerAbility = 0;
732
733 /* Link status is a latched-low bit, read it twice */
734 MiiRead(Adapter, Adapter->PhyAddress, MII_STATUS, &MiiStatus);
735 MiiRead(Adapter, Adapter->PhyAddress, MII_STATUS, &MiiStatus);
736
737 /* Check link status */
738 if (!(MiiStatus & MII_SR_LINK_STATUS))
739 {
740 /* No link detected - configure NIC for 10 MB HD */
741 *LinkSpeed = NVREG_LINKSPEED_10;
742 *FullDuplex = FALSE;
743 return FALSE;
744 }
745
746 /* If we are forcing speed and duplex */
747 if (Adapter->Flags & NV_FORCE_SPEED_AND_DUPLEX)
748 {
749 if (Adapter->Flags & NV_USER_SPEED_100)
750 {
751 *LinkSpeed = NVREG_LINKSPEED_100;
752 }
753 else
754 {
755 *LinkSpeed = NVREG_LINKSPEED_10;
756 }
757 *FullDuplex = !!(Adapter->Flags & NV_FORCE_FULL_DUPLEX);
758 return TRUE;
759 }
760
761 /* Check auto-negotiation is complete */
762 if (!(MiiStatus & MII_SR_AUTONEG_COMPLETE))
763 {
764 /* Still in auto-negotiation - configure NIC for 10 MBit HD and wait */
765 *LinkSpeed = NVREG_LINKSPEED_10;
766 *FullDuplex = FALSE;
767 return FALSE;
768 }
769
770 MiiRead(Adapter, Adapter->PhyAddress, MII_AUTONEG_ADVERTISE, MiiAdvertise);
771 MiiRead(Adapter, Adapter->PhyAddress, MII_AUTONEG_LINK_PARTNER, MiiLinkPartnerAbility);
772
773 /* Gigabit ethernet */
774 if (Adapter->Flags & NV_GIGABIT_PHY)
775 {
776 ULONG MiiControl1000, MiiStatus1000;
777
778 MiiRead(Adapter, Adapter->PhyAddress, MII_MASTER_SLAVE_CONTROL, &MiiControl1000);
779 MiiRead(Adapter, Adapter->PhyAddress, MII_MASTER_SLAVE_STATUS, &MiiStatus1000);
780
781 if ((MiiControl1000 & MII_MS_CR_1000T_FD) && (MiiStatus1000 & MII_MS_SR_1000T_FD))
782 {
783 *LinkSpeed = NVREG_LINKSPEED_1000;
784 *FullDuplex = TRUE;
785 return TRUE;
786 }
787 }
788
789 AdvLpa = (*MiiAdvertise) & (*MiiLinkPartnerAbility);
790 if (AdvLpa & MII_LP_100T_FD)
791 {
792 *LinkSpeed = NVREG_LINKSPEED_100;
793 *FullDuplex = TRUE;
794 }
795 else if (AdvLpa & MII_LP_100T_HD)
796 {
797 *LinkSpeed = NVREG_LINKSPEED_100;
798 *FullDuplex = FALSE;
799 }
800 else if (AdvLpa & MII_LP_10T_FD)
801 {
802 *LinkSpeed = NVREG_LINKSPEED_10;
803 *FullDuplex = TRUE;
804 }
805 else if (AdvLpa & MII_LP_10T_HD)
806 {
807 *LinkSpeed = NVREG_LINKSPEED_10;
808 *FullDuplex = FALSE;
809 }
810 else
811 {
812 *LinkSpeed = NVREG_LINKSPEED_10;
813 *FullDuplex = FALSE;
814 }
815
816 return TRUE;
817}
818
819static
820VOID
822 _In_ PNVNET_ADAPTER Adapter,
823 _In_ ULONG MiiAdvertise,
824 _In_ ULONG MiiLinkPartnerAbility)
825{
826 ULONG PhyRegister, TxDeferral, PauseFlags, MiiExpansion;
827 BOOLEAN RestartTransmitter = FALSE, RestartReceiver = FALSE;
828
829 /* The transmitter and receiver must be restarted for safe update */
831 {
832 RestartTransmitter = TRUE;
833 NvNetStopTransmitter(Adapter);
834 }
836 {
837 RestartReceiver = TRUE;
838 NvNetStopReceiver(Adapter);
839 }
840
841 if (Adapter->Flags & NV_GIGABIT_PHY)
842 {
843 PhyRegister = NV_READ(Adapter, NvRegSlotTime);
844 PhyRegister &= ~NVREG_SLOTTIME_1000_FULL;
845 if ((Adapter->LinkSpeed == NVREG_LINKSPEED_10) ||
846 (Adapter->LinkSpeed == NVREG_LINKSPEED_100))
847 {
848 PhyRegister |= NVREG_SLOTTIME_10_100_FULL;
849 }
850 else if (Adapter->LinkSpeed == NVREG_LINKSPEED_1000)
851 {
852 PhyRegister |= NVREG_SLOTTIME_1000_FULL;
853 }
854 NV_WRITE(Adapter, NvRegSlotTime, PhyRegister);
855 }
856
857 PhyRegister = NV_READ(Adapter, NvRegPhyInterface);
858 PhyRegister &= ~(PHY_HALF | PHY_100 | PHY_1000);
859 if (!Adapter->FullDuplex)
860 {
861 PhyRegister |= PHY_HALF;
862 }
863 if (Adapter->LinkSpeed == NVREG_LINKSPEED_100)
864 PhyRegister |= PHY_100;
865 else if (Adapter->LinkSpeed == NVREG_LINKSPEED_1000)
866 PhyRegister |= PHY_1000;
867 NV_WRITE(Adapter, NvRegPhyInterface, PhyRegister);
868
869 /* Setup the deferral register */
870 MiiRead(Adapter, Adapter->PhyAddress, MII_AUTONEG_EXPANSION, &MiiExpansion);
871 if (PhyRegister & PHY_RGMII)
872 {
873 if (Adapter->LinkSpeed == NVREG_LINKSPEED_1000)
874 {
875 TxDeferral = NVREG_TX_DEFERRAL_RGMII_1000;
876 }
877 else
878 {
879 if (!(MiiExpansion & MII_EXP_LP_AUTONEG) && !Adapter->FullDuplex &&
880 (Adapter->Features & DEV_HAS_COLLISION_FIX))
881 {
883 }
884 else
885 {
887 }
888 }
889 }
890 else
891 {
892 if (!(MiiExpansion & MII_EXP_LP_AUTONEG) && !Adapter->FullDuplex &&
893 (Adapter->Features & DEV_HAS_COLLISION_FIX))
894 {
896 }
897 else
898 {
899 TxDeferral = NVREG_TX_DEFERRAL_DEFAULT;
900 }
901 }
902 NV_WRITE(Adapter, NvRegTxDeferral, TxDeferral);
903
904 /* Setup the watermark register */
905 if (Adapter->Features & (DEV_HAS_HIGH_DMA | DEV_HAS_LARGEDESC))
906 {
907 if (Adapter->LinkSpeed == NVREG_LINKSPEED_1000)
909 else
911 }
912 else
913 {
915 }
916
917 NV_WRITE(Adapter, NvRegMisc1, NVREG_MISC1_FORCE | (Adapter->FullDuplex ? 0 : NVREG_MISC1_HD));
918 NV_WRITE(Adapter, NvRegLinkSpeed, Adapter->LinkSpeed | NVREG_LINKSPEED_FORCE);
919
920 PauseFlags = 0;
921
922 /* Setup pause frames */
923 if (Adapter->FullDuplex)
924 {
925 if (!(Adapter->Flags & NV_FORCE_SPEED_AND_DUPLEX) &&
926 (Adapter->PauseFlags & NV_PAUSEFRAME_AUTONEG))
927 {
928 ULONG AdvPause = MiiAdvertise & (MII_ADV_PAUSE_SYM | MII_ADV_PAUSE_ASYM);
929 ULONG LpaPause = MiiLinkPartnerAbility & (MII_LP_PAUSE_SYM | MII_LP_PAUSE_ASYM);
930
931 switch (AdvPause)
932 {
934 {
935 if (LpaPause & MII_LP_PAUSE_SYM)
936 {
937 PauseFlags |= NV_PAUSEFRAME_RX_ENABLE;
938
939 if (Adapter->PauseFlags & NV_PAUSEFRAME_TX_REQ)
940 PauseFlags |= NV_PAUSEFRAME_TX_ENABLE;
941 }
942 break;
943 }
945 {
946 if (LpaPause == (MII_LP_PAUSE_SYM | MII_LP_PAUSE_ASYM))
947 {
948 PauseFlags |= NV_PAUSEFRAME_TX_ENABLE;
949 }
950 break;
951 }
953 {
954 if (LpaPause & MII_LP_PAUSE_SYM)
955 {
956 PauseFlags |= NV_PAUSEFRAME_RX_ENABLE;
957
958 if (Adapter->PauseFlags & NV_PAUSEFRAME_TX_REQ)
959 PauseFlags |= NV_PAUSEFRAME_TX_ENABLE;
960 }
961 if (LpaPause == MII_LP_PAUSE_ASYM)
962 {
963 PauseFlags |= NV_PAUSEFRAME_RX_ENABLE;
964 }
965 break;
966 }
967
968 default:
969 break;
970 }
971 }
972 else
973 {
974 PauseFlags = Adapter->PauseFlags;
975 }
976 }
977 NvNetUpdatePauseFrame(Adapter, PauseFlags);
978
979 if (RestartTransmitter)
980 {
981 NvNetStartTransmitter(Adapter);
982 }
983 if (RestartReceiver)
984 {
985 NvNetStartReceiver(Adapter);
986 }
987}
988
991 _In_ PNVNET_ADAPTER Adapter)
992{
993 ULONG MiiAdvertise, MiiLinkPartnerAbility, LinkSpeed;
994 BOOLEAN FullDuplex, LinkUp;
995
996 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
997
999 &MiiAdvertise,
1000 &MiiLinkPartnerAbility,
1001 &LinkSpeed,
1002 &FullDuplex);
1003 if (Adapter->FullDuplex == FullDuplex && Adapter->LinkSpeed == LinkSpeed)
1004 {
1005 return LinkUp;
1006 }
1007
1008 NDIS_DbgPrint(MIN_TRACE, ("Configuring MAC from '%lx %s-duplex' to '%lx %s-duplex'\n",
1009 Adapter->LinkSpeed,
1010 Adapter->FullDuplex ? "full" : "half",
1011 LinkSpeed,
1012 FullDuplex ? "full" : "half"));
1013
1014 Adapter->FullDuplex = FullDuplex;
1015 Adapter->LinkSpeed = LinkSpeed;
1016
1017 if (Adapter->Flags & NV_ACTIVE)
1018 {
1019 NdisDprAcquireSpinLock(&Adapter->Send.Lock);
1020 NdisDprAcquireSpinLock(&Adapter->Receive.Lock);
1021 }
1022
1023 NvNetSetSpeedAndDuplex(Adapter, MiiAdvertise, MiiLinkPartnerAbility);
1024
1025 if (Adapter->Flags & NV_ACTIVE)
1026 {
1027 NdisDprReleaseSpinLock(&Adapter->Receive.Lock);
1028 NdisDprReleaseSpinLock(&Adapter->Send.Lock);
1029 }
1030
1031 return LinkUp;
1032}
1033
1034CODE_SEG("PAGE")
1037 _In_ PNVNET_ADAPTER Adapter)
1038{
1039 ULONG PhyState;
1040 BOOLEAN RestorePhyState = FALSE, PhyInitialized = FALSE;
1041
1042 PAGED_CODE();
1043
1044 NDIS_DbgPrint(MIN_TRACE, ("()\n"));
1045
1046 /* Take PHY and NIC out of low power mode */
1047 if (Adapter->Features & DEV_HAS_POWER_CNTRL)
1048 {
1050
1051 PowerState &= ~NVREG_POWERSTATE2_POWERUP_MASK;
1052 if ((Adapter->Features & DEV_NEED_LOW_POWER_FIX) && Adapter->RevisionId >= 0xA3)
1053 {
1055 }
1057 }
1058
1059 /* Clear PHY state and temporarily halt PHY interrupts */
1060 NV_WRITE(Adapter, NvRegMIIMask, 0);
1061 PhyState = NV_READ(Adapter, NvRegAdapterControl);
1062 if (PhyState & NVREG_ADAPTCTL_RUNNING)
1063 {
1064 RestorePhyState = TRUE;
1065
1066 PhyState &= ~NVREG_ADAPTCTL_RUNNING;
1067 NV_WRITE(Adapter, NvRegAdapterControl, PhyState);
1068 }
1070
1071 if (Adapter->Features & DEV_HAS_MGMT_UNIT)
1072 {
1073 ULONG UnitVersion;
1074
1075 /* Management unit running on the MAC? */
1079 SidebandUnitGetVersion(Adapter, &UnitVersion))
1080 {
1081 if (UnitVersion > 0)
1082 {
1084 Adapter->Flags |= NV_MAC_IN_USE;
1085 else
1086 Adapter->Flags &= ~NV_MAC_IN_USE;
1087 }
1088 else
1089 {
1090 Adapter->Flags |= NV_MAC_IN_USE;
1091 }
1092
1093 NDIS_DbgPrint(MIN_TRACE, ("Management unit is running. MAC in use\n"));
1094
1095 /* Management unit setup the PHY already? */
1096 if ((Adapter->Flags & NV_MAC_IN_USE) &&
1099 {
1100 /* PHY is inited by management unit */
1101 PhyInitialized = TRUE;
1102
1103 NDIS_DbgPrint(MIN_TRACE, ("PHY already initialized by management unit\n"));
1104 }
1105 }
1106 }
1107
1108 /* Find a suitable PHY */
1109 if (!FindPhyDevice(Adapter))
1110 {
1111 NDIS_DbgPrint(MAX_TRACE, ("Could not find a valid PHY\n"));
1112 goto Failure;
1113 }
1114
1115 /* We need to init the PHY */
1116 if (!PhyInitialized)
1117 {
1118 if (!PhyInit(Adapter))
1119 {
1120 /* It's not critical for init, continue */
1121 }
1122 }
1123 else
1124 {
1125 ULONG MiiStatus;
1126
1127 /* See if it is a gigabit PHY */
1128 MiiRead(Adapter, Adapter->PhyAddress, MII_STATUS, &MiiStatus);
1129 if (MiiStatus & PHY_GIGABIT)
1130 {
1131 Adapter->Flags |= NV_GIGABIT_PHY;
1132 }
1133 }
1134
1135 return NDIS_STATUS_SUCCESS;
1136
1137Failure:
1138 if (RestorePhyState)
1139 {
1141 }
1142
1143 return NDIS_STATUS_FAILURE;
1144}
#define PAGED_CODE()
#define CODE_SEG(...)
unsigned char BOOLEAN
#define RTL_NUMBER_OF(x)
Definition: RtlRegistry.c:12
#define MIN_TRACE
Definition: debug.h:14
#define MAX_TRACE
Definition: debug.h:16
BOOLEAN MiiRead(_In_ PDC21X4_ADAPTER Adapter, _In_ ULONG PhyAddress, _In_ ULONG RegAddress, _Out_ PULONG Data)
Definition: phy.c:101
BOOLEAN MiiWrite(_In_ PDC21X4_ADAPTER Adapter, _In_ ULONG PhyAddress, _In_ ULONG RegAddress, _In_ ULONG Data)
Definition: phy.c:78
#define MII_EXP_LP_AUTONEG
Definition: dc21x4hw.h:589
#define MII_STATUS
Definition: dc21x4hw.h:566
#define MII_LP_10T_HD
Definition: dc21x4hw.h:581
#define MII_MASTER_SLAVE_STATUS
Definition: dc21x4hw.h:593
#define MII_SR_AUTONEG_COMPLETE
Definition: dc21x4hw.h:568
#define MII_MS_SR_1000T_FD
Definition: dc21x4hw.h:594
#define MII_ADV_PAUSE_SYM
Definition: dc21x4hw.h:578
#define MII_ADV_10T_FD
Definition: dc21x4hw.h:574
#define MII_LP_100T_HD
Definition: dc21x4hw.h:583
#define MII_ADV_100T4
Definition: dc21x4hw.h:577
#define MII_PHY_ID2
Definition: dc21x4hw.h:570
#define MII_ADV_PAUSE_ASYM
Definition: dc21x4hw.h:579
#define MII_AUTONEG_ADVERTISE
Definition: dc21x4hw.h:571
#define MII_CR_RESET
Definition: dc21x4hw.h:565
#define MII_CR_AUTONEG
Definition: dc21x4hw.h:562
#define MII_SR_LINK_STATUS
Definition: dc21x4hw.h:567
#define MII_CR_AUTONEG_RESTART
Definition: dc21x4hw.h:559
#define MII_LP_10T_FD
Definition: dc21x4hw.h:582
#define MII_MS_CR_1000T_FD
Definition: dc21x4hw.h:592
#define MII_LP_100T_FD
Definition: dc21x4hw.h:584
#define MII_ADV_100T_HD
Definition: dc21x4hw.h:575
#define MII_AUTONEG_EXPANSION
Definition: dc21x4hw.h:588
#define MII_AUTONEG_LINK_PARTNER
Definition: dc21x4hw.h:580
#define MII_LP_PAUSE_ASYM
Definition: dc21x4hw.h:587
#define MII_ADV_100T_FD
Definition: dc21x4hw.h:576
#define MII_ADV_10T_HD
Definition: dc21x4hw.h:573
#define MII_MASTER_SLAVE_CONTROL
Definition: dc21x4hw.h:590
#define MII_LP_PAUSE_SYM
Definition: dc21x4hw.h:586
#define MII_PHY_ID1
Definition: dc21x4hw.h:569
#define MII_CONTROL
Definition: dc21x4hw.h:556
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define NDIS_DbgPrint(_t_, _x_)
Definition: debug.h:40
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define _Inout_
Definition: ms_sal.h:378
#define _Out_
Definition: ms_sal.h:345
#define _In_
Definition: ms_sal.h:308
#define NdisDprReleaseSpinLock(_SpinLock)
Definition: ndis.h:4133
#define NDIS_STATUS_FAILURE
Definition: ndis.h:465
#define NdisStallExecution
Definition: ndis.h:4453
#define NDIS_STATUS_SUCCESS
Definition: ndis.h:346
#define NdisDprAcquireSpinLock(_SpinLock)
Definition: ndis.h:4124
VOID EXPORT NdisMSleep(IN ULONG MicrosecondsToSleep)
Definition: miniport.c:2928
VOID NvNetStartTransmitter(_In_ PNVNET_ADAPTER Adapter)
Definition: nic.c:130
VOID NvNetStartReceiver(_In_ PNVNET_ADAPTER Adapter)
Definition: nic.c:104
VOID NvNetStopReceiver(_In_ PNVNET_ADAPTER Adapter)
Definition: nic.c:147
VOID NvNetStopTransmitter(_In_ PNVNET_ADAPTER Adapter)
Definition: nic.c:178
VOID NvNetUpdatePauseFrame(_Inout_ PNVNET_ADAPTER Adapter, _In_ ULONG PauseFlags)
Definition: nic.c:242
int NDIS_STATUS
Definition: ntddndis.h:475
#define NVREG_MGMTUNITVERSION
Definition: nic.h:280
#define PHY_VITESSE_INIT8
Definition: nic.h:515
#define NV_MIIBUSY_DELAY
Definition: nic.h:460
#define PHY_MODEL_MARVELL_E3016
Definition: nic.h:482
#define NVREG_MGMTUNITGETVERSION
Definition: nic.h:277
#define DEV_HAS_POWER_CNTRL
Definition: nic.h:26
#define PHY_REALTEK_INIT2
Definition: nic.h:535
#define PHY_MODEL_REALTEK_8201
Definition: nic.h:481
#define NVREG_XMITCTL_SYNC_MASK
Definition: nic.h:97
#define PHY_CICADA_INIT1
Definition: nic.h:495
#define PHY_REALTEK_INIT_REG3
Definition: nic.h:524
#define PHY_VITESSE_INIT10
Definition: nic.h:518
#define PHY_REALTEK_INIT_REG6
Definition: nic.h:521
#define PHY_MODEL_REALTEK_8211
Definition: nic.h:480
#define NVREG_RCVCTL_START
Definition: nic.h:125
#define PHY_VITESSE_INIT_REG3
Definition: nic.h:510
#define NVREG_MIISTAT_MASK_RW
Definition: nic.h:228
#define PHY_REV_REALTEK_8211B
Definition: nic.h:530
#define NV_PAUSEFRAME_TX_REQ
Definition: nic.h:548
#define PHY_VITESSE_INIT1
Definition: nic.h:517
#define NVREG_XMITCTL_DATA_START
Definition: nic.h:106
#define PHY_VITESSE_INIT2
Definition: nic.h:504
#define PHY_REALTEK_INIT5
Definition: nic.h:527
#define PHY_1000
Definition: nic.h:165
#define PHY_CICADA_INIT_REG3
Definition: nic.h:499
#define NV_MIIPHY_DELAY
Definition: nic.h:461
#define PHY_REALTEK_INIT4
Definition: nic.h:525
#define DEV_NEED_PHY_INIT_FIX
Definition: nic.h:40
#define PHY_REALTEK_INIT1
Definition: nic.h:539
#define NVREG_MISC1_FORCE
Definition: nic.h:92
#define NVREG_MIICTL_INUSE
Definition: nic.h:246
#define PHYID1_OUI_MASK
Definition: nic.h:484
#define NVREG_XMITCTL_START
Definition: nic.h:95
#define NV_PAUSEFRAME_AUTONEG
Definition: nic.h:549
#define PHY_MARVELL_INIT_REG1
Definition: nic.h:501
#define NVREG_TX_WM_DESC1_DEFAULT
Definition: nic.h:196
#define PHY_OUI_CICADA
Definition: nic.h:476
#define NVREG_LINKSPEED_1000
Definition: nic.h:189
#define DEV_HAS_LARGEDESC
Definition: nic.h:20
#define PHY_VITESSE_INIT5
Definition: nic.h:506
#define NVREG_LINKSPEED_100
Definition: nic.h:188
#define NVREG_SLOTTIME_1000_FULL
Definition: nic.h:134
#define PHY_OUI_REALTEK
Definition: nic.h:478
#define PHY_HALF
Definition: nic.h:166
#define PHY_GIGABIT
Definition: nic.h:490
#define NVREG_SLOTTIME_10_100_FULL
Definition: nic.h:133
#define PHY_REALTEK_INIT3
Definition: nic.h:540
#define DEV_HAS_COLLISION_FIX
Definition: nic.h:33
#define NVREG_TX_DEFERRAL_DEFAULT
Definition: nic.h:140
#define PHY_REV_MASK
Definition: nic.h:529
#define NV_PAUSEFRAME_RX_ENABLE
Definition: nic.h:545
#define PHY_REALTEK_REVISION
Definition: nic.h:528
#define NVREG_XMITCTL_HOST_SEMA_ACQ
Definition: nic.h:103
#define PHY_VITESSE_INIT_REG4
Definition: nic.h:511
#define NV_MIIPHY_DELAYMAX
Definition: nic.h:462
#define PHY_VITESSE_INIT7
Definition: nic.h:508
#define PHY_REALTEK_INIT_REG2
Definition: nic.h:534
#define PHY_OUI_REALTEK2
Definition: nic.h:479
#define PHY_REALTEK_INIT_REG1
Definition: nic.h:538
#define NVREG_XMITCTL_HOST_SEMA_MASK
Definition: nic.h:102
#define NVREG_XMITCTL_MGMT_ST
Definition: nic.h:96
#define PHYID1_OUI_SHFT
Definition: nic.h:485
#define NVREG_XMITCTL_DATA_ERROR
Definition: nic.h:108
#define PHY_CICADA_INIT3
Definition: nic.h:497
#define PHY_REALTEK_INIT7
Definition: nic.h:522
#define NVREG_POWERSTATE2_POWERUP_REV_A3
Definition: nic.h:336
#define PHY_VITESSE_INIT6
Definition: nic.h:507
#define PHY_VITESSE_INIT9
Definition: nic.h:509
#define NVREG_MIICTL_ADDRSHIFT
Definition: nic.h:248
#define PHY_REALTEK_INIT6
Definition: nic.h:533
#define NVREG_TX_DEFERRAL_RGMII_STRETCH_100
Definition: nic.h:144
#define PHY_100
Definition: nic.h:164
#define NVREG_TX_WM_DESC2_3_DEFAULT
Definition: nic.h:197
#define NVREG_ADAPTCTL_RUNNING
Definition: nic.h:238
#define PHY_REALTEK_INIT_REG4
Definition: nic.h:526
#define PHY_VITESSE_INIT_REG1
Definition: nic.h:516
#define NVREG_MGMTUNITCONTROL_INUSE
Definition: nic.h:297
#define PHYID2_OUI_MASK
Definition: nic.h:487
#define PHY_REALTEK_INIT11
Definition: nic.h:520
#define PHY_CICADA_INIT5
Definition: nic.h:500
#define PHY_CICADA_INIT4
Definition: nic.h:498
#define NVREG_MIISTAT_MASK_ALL
Definition: nic.h:229
#define NVREG_TX_WM_DESC2_3_1000
Definition: nic.h:198
#define PHY_VITESSE_INIT3
Definition: nic.h:513
#define PHY_REALTEK_INIT_REG7
Definition: nic.h:519
#define PHY_OUI_VITESSE
Definition: nic.h:477
#define PHYID2_MODEL_MASK
Definition: nic.h:486
#define PHY_CICADA_INIT2
Definition: nic.h:496
#define PHY_CICADA_INIT_REG1
Definition: nic.h:492
#define NVREG_MIICTL_WRITE
Definition: nic.h:247
#define PHY_VITESSE_INIT4
Definition: nic.h:505
#define DEV_HAS_MGMT_UNIT
Definition: nic.h:31
#define NVREG_XMITCTL_MGMT_SEMA_MASK
Definition: nic.h:100
#define PHY_VITESSE_INIT_REG2
Definition: nic.h:503
#define NV_PAUSEFRAME_TX_ENABLE
Definition: nic.h:546
#define PHY_CICADA_INIT_REG2
Definition: nic.h:494
#define PHYID2_OUI_SHFT
Definition: nic.h:488
#define DEV_HAS_HIGH_DMA
Definition: nic.h:21
#define NVREG_TX_DEFERRAL_MII_STRETCH
Definition: nic.h:145
#define PHY_REV_REALTEK_8211C
Definition: nic.h:531
#define NVREG_XMITCTL_MGMT_SEMA_FREE
Definition: nic.h:101
#define NVREG_POWERSTATE2_PHY_RESET
Definition: nic.h:337
#define PHY_REALTEK_INIT9
Definition: nic.h:523
#define NVREG_TX_DEFERRAL_RGMII_STRETCH_10
Definition: nic.h:143
#define PHY_RGMII
Definition: nic.h:167
#define NVREG_MIISTAT_ERROR
Definition: nic.h:226
#define NVREG_XMITCTL_SYNC_PHY_INIT
Definition: nic.h:99
#define NVREG_LINKSPEED_FORCE
Definition: nic.h:186
#define NVREG_MISC1_HD
Definition: nic.h:91
#define PHY_REALTEK_INIT10
Definition: nic.h:541
#define DEV_NEED_LOW_POWER_FIX
Definition: nic.h:41
#define NVREG_LINKSPEED_10
Definition: nic.h:187
#define PHY_CICADA_INIT6
Definition: nic.h:493
@ NvRegMIIData
Definition: nic.h:250
@ NvRegTxWatermark
Definition: nic.h:195
@ NvRegSlotTime
Definition: nic.h:131
@ NvRegAdapterControl
Definition: nic.h:234
@ NvRegMgmtUnitGetVersion
Definition: nic.h:276
@ NvRegTxDeferral
Definition: nic.h:139
@ NvRegReceiverControl
Definition: nic.h:124
@ NvRegPowerState2
Definition: nic.h:334
@ NvRegLinkSpeed
Definition: nic.h:185
@ NvRegPhyInterface
Definition: nic.h:163
@ NvRegMIIStatus
Definition: nic.h:225
@ NvRegMIIMask
Definition: nic.h:231
@ NvRegMgmtUnitControl
Definition: nic.h:296
@ NvRegTransmitterControl
Definition: nic.h:94
@ NvRegMIIControl
Definition: nic.h:245
@ NvRegMisc1
Definition: nic.h:89
@ NvRegMgmtUnitVersion
Definition: nic.h:279
#define NVREG_TX_DEFERRAL_RGMII_1000
Definition: nic.h:142
#define PHY_REALTEK_INIT_REG5
Definition: nic.h:532
#define NV_PAUSEFRAME_RX_REQ
Definition: nic.h:547
#define NVREG_XMITCTL_DATA_READY
Definition: nic.h:107
static VOID NvNetSetSpeedAndDuplex(_In_ PNVNET_ADAPTER Adapter, _In_ ULONG MiiAdvertise, _In_ ULONG MiiLinkPartnerAbility)
Definition: phy.c:821
static BOOLEAN PhyInitRealtek8211c(_In_ PNVNET_ADAPTER Adapter)
Definition: phy.c:141
VOID SidebandUnitReleaseSemaphore(_In_ PNVNET_ADAPTER Adapter)
Definition: phy.c:667
static BOOLEAN PhyInitRealtek8211b(_In_ PNVNET_ADAPTER Adapter)
Definition: phy.c:106
static BOOLEAN FindPhyDevice(_Inout_ PNVNET_ADAPTER Adapter)
Definition: phy.c:562
static BOOLEAN SidebandUnitAcquireSemaphore(_Inout_ PNVNET_ADAPTER Adapter)
Definition: phy.c:621
static BOOLEAN SidebandUnitGetVersion(_In_ PNVNET_ADAPTER Adapter, _Out_ PULONG Version)
Definition: phy.c:683
static BOOLEAN PhyInitRealtek8201(_In_ PNVNET_ADAPTER Adapter, _In_ BOOLEAN DisableCrossoverDetection)
Definition: phy.c:183
BOOLEAN NvNetUpdateLinkSpeed(_In_ PNVNET_ADAPTER Adapter)
Definition: phy.c:990
static NDIS_STATUS PhyInit(_In_ PNVNET_ADAPTER Adapter)
Definition: phy.c:358
static BOOLEAN PhyInitVitesseSemiconductor(_In_ PNVNET_ADAPTER Adapter)
Definition: phy.c:257
static BOOLEAN PhyInitCicadaSemiconductor(_In_ PNVNET_ADAPTER Adapter, _In_ ULONG PhyInterface)
Definition: phy.c:222
static BOOLEAN PhyReset(_In_ PNVNET_ADAPTER Adapter, _In_ ULONG ControlSetup)
Definition: phy.c:326
static BOOLEAN MiiGetSpeedAndDuplex(_In_ PNVNET_ADAPTER Adapter, _Out_ PULONG MiiAdvertise, _Out_ PULONG MiiLinkPartnerAbility, _Out_ PULONG LinkSpeed, _Out_ PBOOLEAN FullDuplex)
Definition: phy.c:721
NDIS_STATUS NvNetPhyInit(_In_ PNVNET_ADAPTER Adapter)
Definition: phy.c:1036
#define NV_UNIT_SEMAPHORE_ACQUIRED
Definition: nvnet.h:293
#define NV_MAC_IN_USE
Definition: nvnet.h:291
#define NV_ACTIVE
Definition: nvnet.h:286
#define NV_FORCE_SPEED_AND_DUPLEX
Definition: nvnet.h:295
#define NV_GIGABIT_PHY
Definition: nvnet.h:292
#define NV_FORCE_FULL_DUPLEX
Definition: nvnet.h:296
FORCEINLINE VOID NV_WRITE(_In_ PNVNET_ADAPTER Adapter, _In_ NVNET_REGISTER Register, _In_ ULONG Value)
Definition: nvnet.h:646
FORCEINLINE ULONG NV_READ(_In_ PNVNET_ADAPTER Adapter, _In_ NVNET_REGISTER Register)
Definition: nvnet.h:656
#define NV_USER_SPEED_100
Definition: nvnet.h:297
@ LinkUp
Definition: srb.h:741
uint32_t * PULONG
Definition: typedefs.h:59
unsigned char * PBOOLEAN
Definition: typedefs.h:53
uint32_t ULONG
Definition: typedefs.h:59
_Must_inspect_result_ _In_ PWDFDEVICE_INIT _In_ WDF_DEVICE_POWER_STATE PowerState
Definition: wdfdevice.h:3034
_Must_inspect_result_ _In_ WDFDEVICE _In_ LPCGUID _Out_ PINTERFACE _In_ USHORT _In_ USHORT Version
Definition: wdffdo.h:469