1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23#include "h/skdrv1st.h"
24#include "h/skdrv2nd.h"
25
26
27
28
29typedef struct s_PhyHack {
30 int PhyReg;
31 SK_U16 PhyVal;
32} BCOM_HACK;
33
34
35
36#if (defined(DEBUG) || ((!defined(LINT)) && (!defined(SK_SLIM))))
37static const char SysKonnectFileId[] =
38 "@(#) $Id: skxmac2.c,v 1.102 2003/10/02 16:53:58 rschmidt Exp $ (C) Marvell.";
39#endif
40
41#ifdef GENESIS
42BCOM_HACK BcomRegA1Hack[] = {
43 { 0x18, 0x0c20 }, { 0x17, 0x0012 }, { 0x15, 0x1104 }, { 0x17, 0x0013 },
44 { 0x15, 0x0404 }, { 0x17, 0x8006 }, { 0x15, 0x0132 }, { 0x17, 0x8006 },
45 { 0x15, 0x0232 }, { 0x17, 0x800D }, { 0x15, 0x000F }, { 0x18, 0x0420 },
46 { 0, 0 }
47};
48BCOM_HACK BcomRegC0Hack[] = {
49 { 0x18, 0x0c20 }, { 0x17, 0x0012 }, { 0x15, 0x1204 }, { 0x17, 0x0013 },
50 { 0x15, 0x0A04 }, { 0x18, 0x0420 },
51 { 0, 0 }
52};
53#endif
54
55
56#ifdef GENESIS
57static void SkXmInitPhyXmac(SK_AC*, SK_IOC, int, SK_BOOL);
58static void SkXmInitPhyBcom(SK_AC*, SK_IOC, int, SK_BOOL);
59static int SkXmAutoNegDoneXmac(SK_AC*, SK_IOC, int);
60static int SkXmAutoNegDoneBcom(SK_AC*, SK_IOC, int);
61#endif
62#ifdef YUKON
63static void SkGmInitPhyMarv(SK_AC*, SK_IOC, int, SK_BOOL);
64static int SkGmAutoNegDoneMarv(SK_AC*, SK_IOC, int);
65#endif
66#ifdef OTHER_PHY
67static void SkXmInitPhyLone(SK_AC*, SK_IOC, int, SK_BOOL);
68static void SkXmInitPhyNat (SK_AC*, SK_IOC, int, SK_BOOL);
69static int SkXmAutoNegDoneLone(SK_AC*, SK_IOC, int);
70static int SkXmAutoNegDoneNat (SK_AC*, SK_IOC, int);
71#endif
72
73
74#ifdef GENESIS
75
76
77
78
79
80
81
82
83
84void SkXmPhyRead(
85SK_AC *pAC,
86SK_IOC IoC,
87int Port,
88int PhyReg,
89SK_U16 SK_FAR *pVal)
90{
91 SK_U16 Mmu;
92 SK_GEPORT *pPrt;
93
94 pPrt = &pAC->GIni.GP[Port];
95
96
97 XM_OUT16(IoC, Port, XM_PHY_ADDR, PhyReg | pPrt->PhyAddr);
98
99
100 XM_IN16(IoC, Port, XM_PHY_DATA, pVal);
101
102 if (pPrt->PhyType != SK_PHY_XMAC) {
103 do {
104 XM_IN16(IoC, Port, XM_MMU_CMD, &Mmu);
105
106 } while ((Mmu & XM_MMU_PHY_RDY) == 0);
107
108
109 XM_IN16(IoC, Port, XM_PHY_DATA, pVal);
110 }
111}
112
113
114
115
116
117
118
119
120
121
122
123void SkXmPhyWrite(
124SK_AC *pAC,
125SK_IOC IoC,
126int Port,
127int PhyReg,
128SK_U16 Val)
129{
130 SK_U16 Mmu;
131 SK_GEPORT *pPrt;
132
133 pPrt = &pAC->GIni.GP[Port];
134
135 if (pPrt->PhyType != SK_PHY_XMAC) {
136 do {
137 XM_IN16(IoC, Port, XM_MMU_CMD, &Mmu);
138
139 } while ((Mmu & XM_MMU_PHY_BUSY) != 0);
140 }
141
142
143 XM_OUT16(IoC, Port, XM_PHY_ADDR, PhyReg | pPrt->PhyAddr);
144
145
146 XM_OUT16(IoC, Port, XM_PHY_DATA, Val);
147
148 if (pPrt->PhyType != SK_PHY_XMAC) {
149 do {
150 XM_IN16(IoC, Port, XM_MMU_CMD, &Mmu);
151
152 } while ((Mmu & XM_MMU_PHY_BUSY) != 0);
153 }
154}
155#endif
156
157
158#ifdef YUKON
159
160
161
162
163
164
165
166
167
168void SkGmPhyRead(
169SK_AC *pAC,
170SK_IOC IoC,
171int Port,
172int PhyReg,
173SK_U16 SK_FAR *pVal)
174{
175 SK_U16 Ctrl;
176 SK_GEPORT *pPrt;
177#ifdef VCPU
178 u_long SimCyle;
179 u_long SimLowTime;
180
181 VCPUgetTime(&SimCyle, &SimLowTime);
182 VCPUprintf(0, "SkGmPhyRead(%u), SimCyle=%u, SimLowTime=%u\n",
183 PhyReg, SimCyle, SimLowTime);
184#endif
185
186 pPrt = &pAC->GIni.GP[Port];
187
188
189 *pVal = (SK_U16)(GM_SMI_CT_PHY_AD(pPrt->PhyAddr) |
190 GM_SMI_CT_REG_AD(PhyReg) | GM_SMI_CT_OP_RD);
191
192 GM_OUT16(IoC, Port, GM_SMI_CTRL, *pVal);
193
194 GM_IN16(IoC, Port, GM_SMI_CTRL, &Ctrl);
195
196
197 if ((Ctrl & GM_SMI_CT_BUSY) == 0) {
198 *pVal = 0;
199 return;
200 }
201
202 *pVal |= GM_SMI_CT_BUSY;
203
204 do {
205#ifdef VCPU
206 VCPUwaitTime(1000);
207#endif
208
209 GM_IN16(IoC, Port, GM_SMI_CTRL, &Ctrl);
210
211
212 } while (Ctrl == *pVal);
213
214
215 GM_IN16(IoC, Port, GM_SMI_DATA, pVal);
216
217#ifdef VCPU
218 VCPUgetTime(&SimCyle, &SimLowTime);
219 VCPUprintf(0, "VCPUgetTime(), SimCyle=%u, SimLowTime=%u\n",
220 SimCyle, SimLowTime);
221#endif
222
223}
224
225
226
227
228
229
230
231
232
233
234
235void SkGmPhyWrite(
236SK_AC *pAC,
237SK_IOC IoC,
238int Port,
239int PhyReg,
240SK_U16 Val)
241{
242 SK_U16 Ctrl;
243 SK_GEPORT *pPrt;
244#ifdef VCPU
245 SK_U32 DWord;
246 u_long SimCyle;
247 u_long SimLowTime;
248
249 VCPUgetTime(&SimCyle, &SimLowTime);
250 VCPUprintf(0, "SkGmPhyWrite(Reg=%u, Val=0x%04x), SimCyle=%u, SimLowTime=%u\n",
251 PhyReg, Val, SimCyle, SimLowTime);
252#endif
253
254 pPrt = &pAC->GIni.GP[Port];
255
256
257 GM_OUT16(IoC, Port, GM_SMI_DATA, Val);
258
259
260 Val = GM_SMI_CT_PHY_AD(pPrt->PhyAddr) | GM_SMI_CT_REG_AD(PhyReg);
261
262 GM_OUT16(IoC, Port, GM_SMI_CTRL, Val);
263
264 GM_IN16(IoC, Port, GM_SMI_CTRL, &Ctrl);
265
266
267 if ((Ctrl & GM_SMI_CT_BUSY) == 0) {
268 return;
269 }
270
271 Val |= GM_SMI_CT_BUSY;
272
273 do {
274#ifdef VCPU
275
276 SK_IN32(IoC, B2_TI_VAL, &DWord);
277
278 VCPUwaitTime(1000);
279#endif
280
281 GM_IN16(IoC, Port, GM_SMI_CTRL, &Ctrl);
282
283
284 } while (Ctrl == Val);
285
286#ifdef VCPU
287 VCPUgetTime(&SimCyle, &SimLowTime);
288 VCPUprintf(0, "VCPUgetTime(), SimCyle=%u, SimLowTime=%u\n",
289 SimCyle, SimLowTime);
290#endif
291
292}
293#endif
294
295
296#ifdef SK_DIAG
297
298
299
300
301
302
303
304
305
306void SkGePhyRead(
307SK_AC *pAC,
308SK_IOC IoC,
309int Port,
310int PhyReg,
311SK_U16 *pVal)
312{
313 void (*r_func)(SK_AC *pAC, SK_IOC IoC, int Port, int Reg, SK_U16 *pVal);
314
315 if (pAC->GIni.GIGenesis) {
316 r_func = SkXmPhyRead;
317 }
318 else {
319 r_func = SkGmPhyRead;
320 }
321
322 r_func(pAC, IoC, Port, PhyReg, pVal);
323}
324
325
326
327
328
329
330
331
332
333
334
335void SkGePhyWrite(
336SK_AC *pAC,
337SK_IOC IoC,
338int Port,
339int PhyReg,
340SK_U16 Val)
341{
342 void (*w_func)(SK_AC *pAC, SK_IOC IoC, int Port, int Reg, SK_U16 Val);
343
344 if (pAC->GIni.GIGenesis) {
345 w_func = SkXmPhyWrite;
346 }
347 else {
348 w_func = SkGmPhyWrite;
349 }
350
351 w_func(pAC, IoC, Port, PhyReg, Val);
352}
353#endif
354
355
356
357
358
359
360
361
362
363
364
365
366
367void SkMacPromiscMode(
368SK_AC *pAC,
369SK_IOC IoC,
370int Port,
371SK_BOOL Enable)
372{
373#ifdef YUKON
374 SK_U16 RcReg;
375#endif
376#ifdef GENESIS
377 SK_U32 MdReg;
378#endif
379
380#ifdef GENESIS
381 if (pAC->GIni.GIGenesis) {
382
383 XM_IN32(IoC, Port, XM_MODE, &MdReg);
384
385 if (Enable) {
386 MdReg |= XM_MD_ENA_PROM;
387 }
388 else {
389 MdReg &= ~XM_MD_ENA_PROM;
390 }
391
392 XM_OUT32(IoC, Port, XM_MODE, MdReg);
393 }
394#endif
395
396#ifdef YUKON
397 if (pAC->GIni.GIYukon) {
398
399 GM_IN16(IoC, Port, GM_RX_CTRL, &RcReg);
400
401
402 if (Enable) {
403 RcReg &= ~(GM_RXCR_UCF_ENA | GM_RXCR_MCF_ENA);
404 }
405 else {
406 RcReg |= (GM_RXCR_UCF_ENA | GM_RXCR_MCF_ENA);
407 }
408
409 GM_OUT16(IoC, Port, GM_RX_CTRL, RcReg);
410 }
411#endif
412
413}
414
415
416
417
418
419
420
421
422
423
424
425
426
427void SkMacHashing(
428SK_AC *pAC,
429SK_IOC IoC,
430int Port,
431SK_BOOL Enable)
432{
433#ifdef YUKON
434 SK_U16 RcReg;
435#endif
436#ifdef GENESIS
437 SK_U32 MdReg;
438#endif
439
440#ifdef GENESIS
441 if (pAC->GIni.GIGenesis) {
442
443 XM_IN32(IoC, Port, XM_MODE, &MdReg);
444
445 if (Enable) {
446 MdReg |= XM_MD_ENA_HASH;
447 }
448 else {
449 MdReg &= ~XM_MD_ENA_HASH;
450 }
451
452 XM_OUT32(IoC, Port, XM_MODE, MdReg);
453 }
454#endif
455
456#ifdef YUKON
457 if (pAC->GIni.GIYukon) {
458
459 GM_IN16(IoC, Port, GM_RX_CTRL, &RcReg);
460
461
462 if (Enable) {
463 RcReg |= GM_RXCR_MCF_ENA;
464 }
465 else {
466 RcReg &= ~GM_RXCR_MCF_ENA;
467 }
468
469 GM_OUT16(IoC, Port, GM_RX_CTRL, RcReg);
470 }
471#endif
472
473}
474
475
476#ifdef SK_DIAG
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499static void SkXmSetRxCmd(
500SK_AC *pAC,
501SK_IOC IoC,
502int Port,
503int Mode)
504
505{
506 SK_U16 OldRxCmd;
507 SK_U16 RxCmd;
508
509 XM_IN16(IoC, Port, XM_RX_CMD, &OldRxCmd);
510
511 RxCmd = OldRxCmd;
512
513 switch (Mode & (SK_STRIP_FCS_ON | SK_STRIP_FCS_OFF)) {
514 case SK_STRIP_FCS_ON:
515 RxCmd |= XM_RX_STRIP_FCS;
516 break;
517 case SK_STRIP_FCS_OFF:
518 RxCmd &= ~XM_RX_STRIP_FCS;
519 break;
520 }
521
522 switch (Mode & (SK_STRIP_PAD_ON | SK_STRIP_PAD_OFF)) {
523 case SK_STRIP_PAD_ON:
524 RxCmd |= XM_RX_STRIP_PAD;
525 break;
526 case SK_STRIP_PAD_OFF:
527 RxCmd &= ~XM_RX_STRIP_PAD;
528 break;
529 }
530
531 switch (Mode & (SK_LENERR_OK_ON | SK_LENERR_OK_OFF)) {
532 case SK_LENERR_OK_ON:
533 RxCmd |= XM_RX_LENERR_OK;
534 break;
535 case SK_LENERR_OK_OFF:
536 RxCmd &= ~XM_RX_LENERR_OK;
537 break;
538 }
539
540 switch (Mode & (SK_BIG_PK_OK_ON | SK_BIG_PK_OK_OFF)) {
541 case SK_BIG_PK_OK_ON:
542 RxCmd |= XM_RX_BIG_PK_OK;
543 break;
544 case SK_BIG_PK_OK_OFF:
545 RxCmd &= ~XM_RX_BIG_PK_OK;
546 break;
547 }
548
549 switch (Mode & (SK_SELF_RX_ON | SK_SELF_RX_OFF)) {
550 case SK_SELF_RX_ON:
551 RxCmd |= XM_RX_SELF_RX;
552 break;
553 case SK_SELF_RX_OFF:
554 RxCmd &= ~XM_RX_SELF_RX;
555 break;
556 }
557
558
559 if (OldRxCmd != RxCmd) {
560 XM_OUT16(IoC, Port, XM_RX_CMD, RxCmd);
561 }
562}
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584static void SkGmSetRxCmd(
585SK_AC *pAC,
586SK_IOC IoC,
587int Port,
588int Mode)
589
590{
591 SK_U16 OldRxCmd;
592 SK_U16 RxCmd;
593
594 if ((Mode & (SK_STRIP_FCS_ON | SK_STRIP_FCS_OFF)) != 0) {
595
596 GM_IN16(IoC, Port, GM_RX_CTRL, &OldRxCmd);
597
598 RxCmd = OldRxCmd;
599
600 if ((Mode & SK_STRIP_FCS_ON) != 0) {
601 RxCmd |= GM_RXCR_CRC_DIS;
602 }
603 else {
604 RxCmd &= ~GM_RXCR_CRC_DIS;
605 }
606
607 if (OldRxCmd != RxCmd) {
608 GM_OUT16(IoC, Port, GM_RX_CTRL, RxCmd);
609 }
610 }
611
612 if ((Mode & (SK_BIG_PK_OK_ON | SK_BIG_PK_OK_OFF)) != 0) {
613
614 GM_IN16(IoC, Port, GM_SERIAL_MODE, &OldRxCmd);
615
616 RxCmd = OldRxCmd;
617
618 if ((Mode & SK_BIG_PK_OK_ON) != 0) {
619 RxCmd |= GM_SMOD_JUMBO_ENA;
620 }
621 else {
622 RxCmd &= ~GM_SMOD_JUMBO_ENA;
623 }
624
625 if (OldRxCmd != RxCmd) {
626 GM_OUT16(IoC, Port, GM_SERIAL_MODE, RxCmd);
627 }
628 }
629}
630
631
632
633
634
635
636
637
638
639
640
641void SkMacSetRxCmd(
642SK_AC *pAC,
643SK_IOC IoC,
644int Port,
645int Mode)
646{
647 if (pAC->GIni.GIGenesis) {
648
649 SkXmSetRxCmd(pAC, IoC, Port, Mode);
650 }
651 else {
652
653 SkGmSetRxCmd(pAC, IoC, Port, Mode);
654 }
655
656}
657
658
659
660
661
662
663
664
665
666
667
668void SkMacCrcGener(
669SK_AC *pAC,
670SK_IOC IoC,
671int Port,
672SK_BOOL Enable)
673{
674 SK_U16 Word;
675
676 if (pAC->GIni.GIGenesis) {
677
678 XM_IN16(IoC, Port, XM_TX_CMD, &Word);
679
680 if (Enable) {
681 Word &= ~XM_TX_NO_CRC;
682 }
683 else {
684 Word |= XM_TX_NO_CRC;
685 }
686
687 XM_OUT16(IoC, Port, XM_TX_CMD, Word);
688 }
689 else {
690
691 GM_IN16(IoC, Port, GM_TX_CTRL, &Word);
692
693 if (Enable) {
694 Word &= ~GM_TXCR_CRC_DIS;
695 }
696 else {
697 Word |= GM_TXCR_CRC_DIS;
698 }
699
700 GM_OUT16(IoC, Port, GM_TX_CTRL, Word);
701 }
702
703}
704
705#endif
706
707
708#ifdef GENESIS
709
710
711
712
713
714
715
716
717
718
719
720
721void SkXmClrExactAddr(
722SK_AC *pAC,
723SK_IOC IoC,
724int Port,
725int StartNum,
726int StopNum)
727{
728 int i;
729 SK_U16 ZeroAddr[3] = {0x0000, 0x0000, 0x0000};
730
731 if ((unsigned)StartNum > 15 || (unsigned)StopNum > 15 ||
732 StartNum > StopNum) {
733
734 SK_ERR_LOG(pAC, SK_ERRCL_SW, SKERR_HWI_E001, SKERR_HWI_E001MSG);
735 return;
736 }
737
738 for (i = StartNum; i <= StopNum; i++) {
739 XM_OUTADDR(IoC, Port, XM_EXM(i), &ZeroAddr[0]);
740 }
741}
742#endif
743
744
745
746
747
748
749
750
751
752
753
754
755void SkMacFlushTxFifo(
756SK_AC *pAC,
757SK_IOC IoC,
758int Port)
759{
760#ifdef GENESIS
761 SK_U32 MdReg;
762
763 if (pAC->GIni.GIGenesis) {
764
765 XM_IN32(IoC, Port, XM_MODE, &MdReg);
766
767 XM_OUT32(IoC, Port, XM_MODE, MdReg | XM_MD_FTF);
768 }
769#endif
770
771#ifdef YUKON
772 if (pAC->GIni.GIYukon) {
773
774
775 }
776#endif
777
778}
779
780
781
782
783
784
785
786
787
788
789
790
791void SkMacFlushRxFifo(
792SK_AC *pAC,
793SK_IOC IoC,
794int Port)
795{
796#ifdef GENESIS
797 SK_U32 MdReg;
798
799 if (pAC->GIni.GIGenesis) {
800
801 XM_IN32(IoC, Port, XM_MODE, &MdReg);
802
803 XM_OUT32(IoC, Port, XM_MODE, MdReg | XM_MD_FRF);
804 }
805#endif
806
807#ifdef YUKON
808 if (pAC->GIni.GIYukon) {
809
810
811 }
812#endif
813
814}
815
816
817#ifdef GENESIS
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853static void SkXmSoftRst(
854SK_AC *pAC,
855SK_IOC IoC,
856int Port)
857{
858 SK_U16 ZeroAddr[4] = {0x0000, 0x0000, 0x0000, 0x0000};
859
860
861 XM_OUT32(IoC, Port, XM_GP_PORT, XM_GP_RES_STAT);
862
863
864 XM_OUT16(IoC, Port, XM_IMSK, 0xffff);
865
866 XM_OUT32(IoC, Port, XM_MODE, 0);
867
868 XM_OUT16(IoC, Port, XM_TX_CMD, 0);
869 XM_OUT16(IoC, Port, XM_RX_CMD, 0);
870
871
872 switch (pAC->GIni.GP[Port].PhyType) {
873 case SK_PHY_BCOM:
874 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_INT_MASK, 0xffff);
875 break;
876#ifdef OTHER_PHY
877 case SK_PHY_LONE:
878 SkXmPhyWrite(pAC, IoC, Port, PHY_LONE_INT_ENAB, 0);
879 break;
880 case SK_PHY_NAT:
881
882
883 break;
884#endif
885 }
886
887
888 XM_OUTHASH(IoC, Port, XM_HSM, &ZeroAddr);
889
890
891 SkXmClrExactAddr(pAC, IoC, Port, 0, 15);
892
893
894 XM_OUTHASH(IoC, Port, XM_SRC_CHK, &ZeroAddr);
895
896}
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916static void SkXmHardRst(
917SK_AC *pAC,
918SK_IOC IoC,
919int Port)
920{
921 SK_U32 Reg;
922 int i;
923 int TOut;
924 SK_U16 Word;
925
926 for (i = 0; i < 4; i++) {
927
928 SK_OUT16(IoC, MR_ADDR(Port, TX_MFF_CTRL1), MFF_CLR_MAC_RST);
929
930 TOut = 0;
931 do {
932 if (TOut++ > 10000) {
933
934
935
936
937 return;
938 }
939
940 SK_OUT16(IoC, MR_ADDR(Port, TX_MFF_CTRL1), MFF_SET_MAC_RST);
941
942 SK_IN16(IoC, MR_ADDR(Port, TX_MFF_CTRL1), &Word);
943
944 } while ((Word & MFF_SET_MAC_RST) == 0);
945 }
946
947
948 if (pAC->GIni.GP[Port].PhyType != SK_PHY_XMAC) {
949
950 SK_IN32(IoC, B2_GP_IO, &Reg);
951
952 if (Port == 0) {
953 Reg |= GP_DIR_0;
954 Reg &= ~GP_IO_0;
955 }
956 else {
957 Reg |= GP_DIR_2;
958 Reg &= ~GP_IO_2;
959 }
960
961 SK_OUT32(IoC, B2_GP_IO, Reg);
962
963
964 SK_IN32(IoC, B2_GP_IO, &Reg);
965 }
966}
967
968
969
970
971
972
973
974
975
976
977
978static void SkXmClearRst(
979SK_AC *pAC,
980SK_IOC IoC,
981int Port)
982{
983 SK_U32 DWord;
984
985
986 SK_OUT16(IoC, MR_ADDR(Port, TX_MFF_CTRL1), MFF_CLR_MAC_RST);
987
988 if (pAC->GIni.GP[Port].PhyType != SK_PHY_XMAC) {
989
990 SK_IN32(IoC, B2_GP_IO, &DWord);
991
992 if (Port == 0) {
993 DWord |= (GP_DIR_0 | GP_IO_0);
994 }
995 else {
996 DWord |= (GP_DIR_2 | GP_IO_2);
997 }
998
999 SK_OUT32(IoC, B2_GP_IO, DWord);
1000
1001
1002 XM_OUT16(IoC, Port, XM_HW_CFG, XM_HW_GMII_MD);
1003 }
1004}
1005#endif
1006
1007
1008#ifdef YUKON
1009
1010
1011
1012
1013
1014
1015
1016
1017
1018
1019
1020static void SkGmSoftRst(
1021SK_AC *pAC,
1022SK_IOC IoC,
1023int Port)
1024{
1025 SK_U16 EmptyHash[4] = {0x0000, 0x0000, 0x0000, 0x0000};
1026 SK_U16 RxCtrl;
1027
1028
1029
1030
1031 SK_OUT8(IoC, GMAC_IRQ_MSK, 0);
1032
1033
1034 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_INT_MASK, 0);
1035
1036
1037 GM_OUTHASH(IoC, Port, GM_MC_ADDR_H1, EmptyHash);
1038
1039
1040 GM_IN16(IoC, Port, GM_RX_CTRL, &RxCtrl);
1041
1042 GM_OUT16(IoC, Port, GM_RX_CTRL,
1043 (SK_U16)(RxCtrl | GM_RXCR_UCF_ENA | GM_RXCR_MCF_ENA));
1044
1045}
1046
1047
1048
1049
1050
1051
1052
1053
1054
1055
1056
1057static void SkGmHardRst(
1058SK_AC *pAC,
1059SK_IOC IoC,
1060int Port)
1061{
1062 SK_U32 DWord;
1063
1064
1065 if (pAC->GIni.GIYukonLite &&
1066 pAC->GIni.GIChipRev == CHIP_REV_YU_LITE_A3) {
1067
1068 SK_IN32(IoC, B2_GP_IO, &DWord);
1069
1070 DWord |= (GP_DIR_9 | GP_IO_9);
1071
1072
1073 SK_OUT32(IoC, B2_GP_IO, DWord);
1074 }
1075
1076
1077 SK_OUT32(IoC, MR_ADDR(Port, GPHY_CTRL), GPC_RST_SET);
1078
1079
1080 SK_OUT32(IoC, MR_ADDR(Port, GMAC_CTRL), GMC_RST_SET);
1081
1082}
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094static void SkGmClearRst(
1095SK_AC *pAC,
1096SK_IOC IoC,
1097int Port)
1098{
1099 SK_U32 DWord;
1100
1101#ifdef XXX
1102
1103 SK_OUT32(IoC, MR_ADDR(Port, GMAC_CTRL), GMC_RST_CLR);
1104
1105
1106 SK_OUT32(IoC, MR_ADDR(Port, GMAC_CTRL), GMC_RST_SET);
1107#endif
1108
1109
1110 if (pAC->GIni.GIYukonLite &&
1111 pAC->GIni.GIChipRev == CHIP_REV_YU_LITE_A3) {
1112
1113 SK_IN32(IoC, B2_GP_IO, &DWord);
1114
1115 DWord |= GP_DIR_9;
1116 DWord &= ~GP_IO_9;
1117
1118
1119 SK_OUT32(IoC, B2_GP_IO, DWord);
1120 }
1121
1122
1123 DWord = GPC_INT_POL_HI | GPC_DIS_FC | GPC_DIS_SLEEP |
1124 GPC_ENA_XC | GPC_ANEG_ADV_ALL_M | GPC_ENA_PAUSE |
1125 (pAC->GIni.GICopperType ? GPC_HWCFG_GMII_COP :
1126 GPC_HWCFG_GMII_FIB);
1127
1128
1129 SK_OUT32(IoC, MR_ADDR(Port, GPHY_CTRL), DWord | GPC_RST_SET);
1130
1131
1132 SK_OUT32(IoC, MR_ADDR(Port, GPHY_CTRL), DWord | GPC_RST_CLR);
1133
1134#ifdef VCPU
1135 VCpuWait(9000);
1136#endif
1137
1138
1139 SK_OUT32(IoC, MR_ADDR(Port, GMAC_CTRL), GMC_PAUSE_ON | GMC_RST_CLR);
1140
1141#ifdef VCPU
1142 VCpuWait(2000);
1143
1144 SK_IN32(IoC, MR_ADDR(Port, GPHY_CTRL), &DWord);
1145
1146 SK_IN32(IoC, B0_ISRC, &DWord);
1147#endif
1148
1149}
1150#endif
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162void SkMacSoftRst(
1163SK_AC *pAC,
1164SK_IOC IoC,
1165int Port)
1166{
1167 SK_GEPORT *pPrt;
1168
1169 pPrt = &pAC->GIni.GP[Port];
1170
1171
1172 SkMacRxTxDisable(pAC, IoC, Port);
1173
1174#ifdef GENESIS
1175 if (pAC->GIni.GIGenesis) {
1176
1177 SkXmSoftRst(pAC, IoC, Port);
1178 }
1179#endif
1180
1181#ifdef YUKON
1182 if (pAC->GIni.GIYukon) {
1183
1184 SkGmSoftRst(pAC, IoC, Port);
1185 }
1186#endif
1187
1188
1189 SkMacFlushTxFifo(pAC, IoC, Port);
1190
1191 SkMacFlushRxFifo(pAC, IoC, Port);
1192
1193 pPrt->PState = SK_PRT_STOP;
1194
1195}
1196
1197
1198
1199
1200
1201
1202
1203
1204
1205
1206
1207void SkMacHardRst(
1208SK_AC *pAC,
1209SK_IOC IoC,
1210int Port)
1211{
1212
1213#ifdef GENESIS
1214 if (pAC->GIni.GIGenesis) {
1215
1216 SkXmHardRst(pAC, IoC, Port);
1217 }
1218#endif
1219
1220#ifdef YUKON
1221 if (pAC->GIni.GIYukon) {
1222
1223 SkGmHardRst(pAC, IoC, Port);
1224 }
1225#endif
1226
1227 pAC->GIni.GP[Port].PState = SK_PRT_RESET;
1228
1229}
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240
1241void SkMacClearRst(
1242SK_AC *pAC,
1243SK_IOC IoC,
1244int Port)
1245{
1246
1247#ifdef GENESIS
1248 if (pAC->GIni.GIGenesis) {
1249
1250 SkXmClearRst(pAC, IoC, Port);
1251 }
1252#endif
1253
1254#ifdef YUKON
1255 if (pAC->GIni.GIYukon) {
1256
1257 SkGmClearRst(pAC, IoC, Port);
1258 }
1259#endif
1260
1261}
1262
1263
1264#ifdef GENESIS
1265
1266
1267
1268
1269
1270
1271
1272
1273
1274
1275
1276
1277
1278
1279void SkXmInitMac(
1280SK_AC *pAC,
1281SK_IOC IoC,
1282int Port)
1283{
1284 SK_GEPORT *pPrt;
1285 int i;
1286 SK_U16 SWord;
1287
1288 pPrt = &pAC->GIni.GP[Port];
1289
1290 if (pPrt->PState == SK_PRT_STOP) {
1291
1292
1293 SK_IN16(IoC, MR_ADDR(Port, TX_MFF_CTRL1), &SWord);
1294
1295 if ((SWord & MFF_SET_MAC_RST) != 0) {
1296
1297 SK_ERR_LOG(pAC, SK_ERRCL_SW, SKERR_HWI_E006, SKERR_HWI_E006MSG);
1298
1299 pPrt->PState = SK_PRT_RESET;
1300 }
1301 }
1302
1303 if (pPrt->PState == SK_PRT_RESET) {
1304
1305 SkXmClearRst(pAC, IoC, Port);
1306
1307 if (pPrt->PhyType != SK_PHY_XMAC) {
1308
1309 SkXmPhyRead(pAC, IoC, Port, PHY_XMAC_ID1, &pPrt->PhyId1);
1310
1311
1312
1313
1314
1315 XM_IN16(IoC, Port, XM_MMU_CMD, &SWord);
1316
1317 XM_OUT16(IoC, Port, XM_MMU_CMD, SWord | XM_MMU_NO_PRE);
1318
1319 if (pPrt->PhyId1 == PHY_BCOM_ID1_C0) {
1320
1321
1322
1323
1324 i = 0;
1325 while (BcomRegC0Hack[i].PhyReg != 0) {
1326 SkXmPhyWrite(pAC, IoC, Port, BcomRegC0Hack[i].PhyReg,
1327 BcomRegC0Hack[i].PhyVal);
1328 i++;
1329 }
1330 }
1331 else if (pPrt->PhyId1 == PHY_BCOM_ID1_A1) {
1332
1333
1334
1335
1336 i = 0;
1337 while (BcomRegA1Hack[i].PhyReg != 0) {
1338 SkXmPhyWrite(pAC, IoC, Port, BcomRegA1Hack[i].PhyReg,
1339 BcomRegA1Hack[i].PhyVal);
1340 i++;
1341 }
1342 }
1343
1344
1345
1346
1347
1348 SkXmPhyRead(pAC, IoC, Port, PHY_BCOM_AUX_CTRL, &SWord);
1349
1350 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_AUX_CTRL,
1351 (SK_U16)(SWord | PHY_B_AC_DIS_PM));
1352
1353
1354 }
1355
1356
1357 XM_IN16(IoC, Port, XM_ISRC, &SWord);
1358
1359
1360
1361
1362
1363
1364 SkMacInitPhy(pAC, IoC, Port, SK_FALSE);
1365
1366#ifdef TEST_ONLY
1367
1368
1369 XM_OUT16(IoC, Port, XM_HW_CFG, XM_HW_COM4SIG);
1370#endif
1371 }
1372
1373
1374
1375
1376
1377
1378 for (i = 0; i < 3; i++) {
1379
1380
1381
1382
1383 SK_IN16(IoC, (B2_MAC_2 + Port * 8 + i * 2), &SWord);
1384
1385 XM_OUT16(IoC, Port, (XM_SA + i * 2), SWord);
1386 }
1387
1388
1389
1390
1391
1392
1393
1394
1395
1396 XM_OUT16(IoC, Port, XM_RX_HI_WM, SK_XM_RX_HI_WM);
1397
1398
1399 SWord = SK_XM_THR_SL;
1400
1401 if (pAC->GIni.GIMacsFound > 1) {
1402 switch (pAC->GIni.GIPortUsage) {
1403 case SK_RED_LINK:
1404 SWord = SK_XM_THR_REDL;
1405 break;
1406 case SK_MUL_LINK:
1407 SWord = SK_XM_THR_MULL;
1408 break;
1409 case SK_JUMBO_LINK:
1410 SWord = SK_XM_THR_JUMBO;
1411 break;
1412 default:
1413 SK_ERR_LOG(pAC, SK_ERRCL_SW, SKERR_HWI_E014, SKERR_HWI_E014MSG);
1414 break;
1415 }
1416 }
1417 XM_OUT16(IoC, Port, XM_TX_THR, SWord);
1418
1419
1420 XM_OUT16(IoC, Port, XM_TX_CMD, XM_TX_AUTO_PAD);
1421
1422
1423 SWord = XM_RX_STRIP_FCS | XM_RX_LENERR_OK;
1424
1425 if (pAC->GIni.GIPortUsage == SK_JUMBO_LINK) {
1426 SWord |= XM_RX_BIG_PK_OK;
1427 }
1428
1429 if (pPrt->PLinkMode == SK_LMODE_HALF) {
1430
1431
1432
1433
1434
1435 SWord |= XM_RX_DIS_CEXT;
1436 }
1437
1438 XM_OUT16(IoC, Port, XM_RX_CMD, SWord);
1439
1440
1441
1442
1443
1444
1445
1446
1447 XM_OUT32(IoC, Port, XM_MODE, XM_DEF_MODE);
1448
1449
1450
1451
1452
1453
1454 XM_OUT32(IoC, Port, XM_RX_EV_MSK, XMR_DEF_MSK);
1455
1456
1457
1458
1459
1460
1461 XM_OUT32(IoC, Port, XM_TX_EV_MSK, XMT_DEF_MSK);
1462
1463
1464
1465
1466
1467
1468
1469
1470
1471
1472
1473
1474}
1475#endif
1476
1477
1478#ifdef YUKON
1479
1480
1481
1482
1483
1484
1485
1486
1487
1488
1489
1490
1491
1492
1493void SkGmInitMac(
1494SK_AC *pAC,
1495SK_IOC IoC,
1496int Port)
1497{
1498 SK_GEPORT *pPrt;
1499 int i;
1500 SK_U16 SWord;
1501 SK_U32 DWord;
1502
1503 pPrt = &pAC->GIni.GP[Port];
1504
1505 if (pPrt->PState == SK_PRT_STOP) {
1506
1507
1508 SK_IN32(IoC, MR_ADDR(Port, GMAC_CTRL), &DWord);
1509
1510 if ((DWord & GMC_RST_SET) != 0) {
1511
1512 SK_ERR_LOG(pAC, SK_ERRCL_SW, SKERR_HWI_E006, SKERR_HWI_E006MSG);
1513
1514 pPrt->PState = SK_PRT_RESET;
1515 }
1516 }
1517
1518 if (pPrt->PState == SK_PRT_RESET) {
1519
1520 SkGmHardRst(pAC, IoC, Port);
1521
1522 SkGmClearRst(pAC, IoC, Port);
1523
1524
1525 if (pPrt->PLinkMode == SK_LMODE_HALF || pPrt->PLinkMode == SK_LMODE_FULL) {
1526
1527
1528
1529 GM_IN16(IoC, Port, GM_GP_CTRL, &SWord);
1530
1531
1532 SWord |= GM_GPCR_AU_ALL_DIS;
1533
1534
1535 GM_OUT16(IoC, Port, GM_GP_CTRL, SWord);
1536
1537 SWord = GM_GPCR_AU_ALL_DIS;
1538 }
1539 else {
1540 SWord = 0;
1541 }
1542
1543
1544 switch (pPrt->PLinkSpeed) {
1545 case SK_LSPEED_AUTO:
1546 case SK_LSPEED_1000MBPS:
1547 SWord |= GM_GPCR_SPEED_1000 | GM_GPCR_SPEED_100;
1548 break;
1549 case SK_LSPEED_100MBPS:
1550 SWord |= GM_GPCR_SPEED_100;
1551 break;
1552 case SK_LSPEED_10MBPS:
1553 break;
1554 }
1555
1556
1557 if (pPrt->PLinkMode != SK_LMODE_HALF) {
1558
1559 SWord |= GM_GPCR_DUP_FULL;
1560 }
1561
1562
1563 switch (pPrt->PFlowCtrlMode) {
1564 case SK_FLOW_MODE_NONE:
1565
1566 SK_OUT32(IoC, MR_ADDR(Port, GMAC_CTRL), GMC_PAUSE_OFF);
1567
1568 SWord |= GM_GPCR_FC_TX_DIS | GM_GPCR_FC_RX_DIS | GM_GPCR_AU_FCT_DIS;
1569 break;
1570 case SK_FLOW_MODE_LOC_SEND:
1571
1572 SWord |= GM_GPCR_FC_RX_DIS | GM_GPCR_AU_FCT_DIS;
1573 break;
1574 case SK_FLOW_MODE_SYMMETRIC:
1575 case SK_FLOW_MODE_SYM_OR_REM:
1576
1577 break;
1578 }
1579
1580
1581 GM_OUT16(IoC, Port, GM_GP_CTRL, SWord);
1582
1583
1584 SK_IN16(IoC, GMAC_IRQ_SRC, &SWord);
1585
1586#ifndef VCPU
1587
1588 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_ID1, &pPrt->PhyId1);
1589
1590 SkGmInitPhyMarv(pAC, IoC, Port, SK_FALSE);
1591#endif
1592 }
1593
1594 (void)SkGmResetCounter(pAC, IoC, Port);
1595
1596
1597 GM_OUT16(IoC, Port, GM_TX_CTRL, TX_COL_THR(pPrt->PMacColThres));
1598
1599
1600 GM_OUT16(IoC, Port, GM_RX_CTRL, GM_RXCR_UCF_ENA | GM_RXCR_MCF_ENA |
1601 GM_RXCR_CRC_DIS);
1602
1603
1604 GM_OUT16(IoC, Port, GM_TX_FLOW_CTRL, 0xffff);
1605
1606
1607#ifdef VCPU
1608 GM_IN16(IoC, Port, GM_TX_PARAM, &SWord);
1609#endif
1610
1611 SWord = TX_JAM_LEN_VAL(pPrt->PMacJamLen) |
1612 TX_JAM_IPG_VAL(pPrt->PMacJamIpgVal) |
1613 TX_IPG_JAM_DATA(pPrt->PMacJamIpgData);
1614
1615 GM_OUT16(IoC, Port, GM_TX_PARAM, SWord);
1616
1617
1618#ifdef VCPU
1619 GM_IN16(IoC, Port, GM_SERIAL_MODE, &SWord);
1620#endif
1621
1622 SWord = GM_SMOD_VLAN_ENA | IPG_DATA_VAL(pPrt->PMacIpgData);
1623
1624 if (pPrt->PMacLimit4) {
1625
1626 SWord |= GM_SMOD_LIMIT_4;
1627 }
1628
1629 if (pAC->GIni.GIPortUsage == SK_JUMBO_LINK) {
1630
1631 SWord |= GM_SMOD_JUMBO_ENA;
1632 }
1633
1634 GM_OUT16(IoC, Port, GM_SERIAL_MODE, SWord);
1635
1636
1637
1638
1639
1640
1641
1642
1643
1644 for (i = 0; i < 3; i++) {
1645
1646
1647
1648
1649
1650 SK_IN16(IoC, (B2_MAC_2 + Port * 8 + i * 2), &SWord);
1651
1652#ifdef WA_DEV_16
1653
1654 if (pAC->GIni.GIChipId == CHIP_ID_YUKON && pAC->GIni.GIChipRev == 0) {
1655
1656 SWord = ((SWord & 0xff00) >> 8) | ((SWord & 0x00ff) << 8);
1657
1658
1659 GM_OUT16(IoC, Port, (GM_SRC_ADDR_1L + (2 - i) * 4), SWord);
1660 }
1661 else {
1662 GM_OUT16(IoC, Port, (GM_SRC_ADDR_1L + i * 4), SWord);
1663 }
1664#else
1665 GM_OUT16(IoC, Port, (GM_SRC_ADDR_1L + i * 4), SWord);
1666#endif
1667
1668
1669 SK_IN16(IoC, (B2_MAC_1 + Port * 8 + i * 2), &SWord);
1670
1671 GM_OUT16(IoC, Port, (GM_SRC_ADDR_2L + i * 4), SWord);
1672
1673
1674 GM_OUT16(IoC, Port, GM_MC_ADDR_H1 + 4*i, 0);
1675 }
1676
1677
1678 GM_OUT16(IoC, Port, GM_MC_ADDR_H4, 0);
1679
1680
1681 GM_OUT16(IoC, Port, GM_TX_IRQ_MSK, 0);
1682 GM_OUT16(IoC, Port, GM_RX_IRQ_MSK, 0);
1683 GM_OUT16(IoC, Port, GM_TR_IRQ_MSK, 0);
1684
1685#if defined(SK_DIAG) || defined(DEBUG)
1686
1687 GM_IN16(IoC, Port, GM_GP_STAT, &SWord);
1688
1689 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
1690 ("MAC Stat Reg.=0x%04X\n", SWord));
1691#endif
1692
1693#ifdef SK_DIAG
1694 c_print("MAC Stat Reg=0x%04X\n", SWord);
1695#endif
1696
1697}
1698#endif
1699
1700
1701#ifdef GENESIS
1702
1703
1704
1705
1706
1707
1708
1709
1710
1711
1712
1713
1714void SkXmInitDupMd(
1715SK_AC *pAC,
1716SK_IOC IoC,
1717int Port)
1718{
1719 switch (pAC->GIni.GP[Port].PLinkModeStatus) {
1720 case SK_LMODE_STAT_AUTOHALF:
1721 case SK_LMODE_STAT_HALF:
1722
1723
1724
1725
1726
1727
1728
1729
1730
1731 break;
1732 case SK_LMODE_STAT_AUTOFULL:
1733 case SK_LMODE_STAT_FULL:
1734
1735
1736
1737
1738
1739
1740 break;
1741 case SK_LMODE_STAT_UNKNOWN:
1742 default:
1743 SK_ERR_LOG(pAC, SK_ERRCL_SW, SKERR_HWI_E007, SKERR_HWI_E007MSG);
1744 break;
1745 }
1746}
1747
1748
1749
1750
1751
1752
1753
1754
1755
1756
1757
1758
1759
1760
1761
1762void SkXmInitPauseMd(
1763SK_AC *pAC,
1764SK_IOC IoC,
1765int Port)
1766{
1767 SK_GEPORT *pPrt;
1768 SK_U32 DWord;
1769 SK_U16 Word;
1770
1771 pPrt = &pAC->GIni.GP[Port];
1772
1773 XM_IN16(IoC, Port, XM_MMU_CMD, &Word);
1774
1775 if (pPrt->PFlowCtrlStatus == SK_FLOW_STAT_NONE ||
1776 pPrt->PFlowCtrlStatus == SK_FLOW_STAT_LOC_SEND) {
1777
1778
1779 Word |= XM_MMU_IGN_PF;
1780 }
1781 else {
1782
1783
1784
1785
1786
1787 Word &= ~XM_MMU_IGN_PF;
1788 }
1789
1790 XM_OUT16(IoC, Port, XM_MMU_CMD, Word);
1791
1792 XM_IN32(IoC, Port, XM_MODE, &DWord);
1793
1794 if (pPrt->PFlowCtrlStatus == SK_FLOW_STAT_SYMMETRIC ||
1795 pPrt->PFlowCtrlStatus == SK_FLOW_STAT_LOC_SEND) {
1796
1797
1798
1799
1800
1801
1802
1803
1804
1805
1806
1807
1808
1809
1810 XM_OUT16(IoC, Port, XM_MAC_PTIME, 0xffff);
1811
1812
1813 DWord |= XM_PAUSE_MODE;
1814
1815
1816 SK_OUT16(IoC, MR_ADDR(Port, RX_MFF_CTRL1), MFF_ENA_PAUSE);
1817 }
1818 else {
1819
1820
1821
1822
1823
1824 DWord &= ~XM_PAUSE_MODE;
1825
1826
1827 SK_OUT16(IoC, MR_ADDR(Port, RX_MFF_CTRL1), MFF_DIS_PAUSE);
1828 }
1829
1830 XM_OUT32(IoC, Port, XM_MODE, DWord);
1831}
1832
1833
1834
1835
1836
1837
1838
1839
1840
1841
1842
1843
1844
1845static void SkXmInitPhyXmac(
1846SK_AC *pAC,
1847SK_IOC IoC,
1848int Port,
1849SK_BOOL DoLoop)
1850{
1851 SK_GEPORT *pPrt;
1852 SK_U16 Ctrl;
1853
1854 pPrt = &pAC->GIni.GP[Port];
1855 Ctrl = 0;
1856
1857
1858 if (pPrt->PLinkMode == SK_LMODE_HALF || pPrt->PLinkMode == SK_LMODE_FULL) {
1859 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
1860 ("InitPhyXmac: no auto-negotiation Port %d\n", Port));
1861
1862 if (pPrt->PLinkMode == SK_LMODE_FULL) {
1863 Ctrl |= PHY_CT_DUP_MD;
1864 }
1865
1866
1867
1868
1869
1870 }
1871 else {
1872 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
1873 ("InitPhyXmac: with auto-negotiation Port %d\n", Port));
1874
1875
1876
1877 switch (pPrt->PLinkMode) {
1878 case SK_LMODE_AUTOHALF:
1879 Ctrl |= PHY_X_AN_HD;
1880 break;
1881 case SK_LMODE_AUTOFULL:
1882 Ctrl |= PHY_X_AN_FD;
1883 break;
1884 case SK_LMODE_AUTOBOTH:
1885 Ctrl |= PHY_X_AN_FD | PHY_X_AN_HD;
1886 break;
1887 default:
1888 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E015,
1889 SKERR_HWI_E015MSG);
1890 }
1891
1892
1893 switch (pPrt->PFlowCtrlMode) {
1894 case SK_FLOW_MODE_NONE:
1895 Ctrl |= PHY_X_P_NO_PAUSE;
1896 break;
1897 case SK_FLOW_MODE_LOC_SEND:
1898 Ctrl |= PHY_X_P_ASYM_MD;
1899 break;
1900 case SK_FLOW_MODE_SYMMETRIC:
1901 Ctrl |= PHY_X_P_SYM_MD;
1902 break;
1903 case SK_FLOW_MODE_SYM_OR_REM:
1904 Ctrl |= PHY_X_P_BOTH_MD;
1905 break;
1906 default:
1907 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E016,
1908 SKERR_HWI_E016MSG);
1909 }
1910
1911
1912 SkXmPhyWrite(pAC, IoC, Port, PHY_XMAC_AUNE_ADV, Ctrl);
1913
1914
1915 Ctrl = PHY_CT_ANE | PHY_CT_RE_CFG;
1916 }
1917
1918 if (DoLoop) {
1919
1920 Ctrl |= PHY_CT_LOOP;
1921 }
1922
1923
1924 SkXmPhyWrite(pAC, IoC, Port, PHY_XMAC_CTRL, Ctrl);
1925}
1926
1927
1928
1929
1930
1931
1932
1933
1934
1935
1936
1937
1938
1939static void SkXmInitPhyBcom(
1940SK_AC *pAC,
1941SK_IOC IoC,
1942int Port,
1943SK_BOOL DoLoop)
1944{
1945 SK_GEPORT *pPrt;
1946 SK_U16 Ctrl1;
1947 SK_U16 Ctrl2;
1948 SK_U16 Ctrl3;
1949 SK_U16 Ctrl4;
1950 SK_U16 Ctrl5;
1951
1952 Ctrl1 = PHY_CT_SP1000;
1953 Ctrl2 = 0;
1954 Ctrl3 = PHY_SEL_TYPE;
1955 Ctrl4 = PHY_B_PEC_EN_LTR;
1956 Ctrl5 = PHY_B_AC_TX_TST;
1957
1958 pPrt = &pAC->GIni.GP[Port];
1959
1960
1961 if (pPrt->PMSMode != SK_MS_MODE_AUTO) {
1962 Ctrl2 |= PHY_B_1000C_MSE;
1963
1964 if (pPrt->PMSMode == SK_MS_MODE_MASTER) {
1965 Ctrl2 |= PHY_B_1000C_MSC;
1966 }
1967 }
1968
1969 if (pPrt->PLinkMode == SK_LMODE_HALF || pPrt->PLinkMode == SK_LMODE_FULL) {
1970 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
1971 ("InitPhyBcom: no auto-negotiation Port %d\n", Port));
1972
1973 if (pPrt->PLinkMode == SK_LMODE_FULL) {
1974 Ctrl1 |= PHY_CT_DUP_MD;
1975 }
1976
1977
1978 if (pPrt->PMSMode == SK_MS_MODE_AUTO) {
1979 Ctrl2 |= PHY_B_1000C_MSE;
1980 }
1981
1982
1983
1984
1985
1986 }
1987 else {
1988 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
1989 ("InitPhyBcom: with auto-negotiation Port %d\n", Port));
1990
1991
1992
1993
1994
1995
1996
1997 Ctrl2 |= PHY_B_1000C_RD;
1998
1999
2000 switch (pPrt->PLinkMode) {
2001 case SK_LMODE_AUTOHALF:
2002 Ctrl2 |= PHY_B_1000C_AHD;
2003 break;
2004 case SK_LMODE_AUTOFULL:
2005 Ctrl2 |= PHY_B_1000C_AFD;
2006 break;
2007 case SK_LMODE_AUTOBOTH:
2008 Ctrl2 |= PHY_B_1000C_AFD | PHY_B_1000C_AHD;
2009 break;
2010 default:
2011 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E015,
2012 SKERR_HWI_E015MSG);
2013 }
2014
2015
2016 switch (pPrt->PFlowCtrlMode) {
2017 case SK_FLOW_MODE_NONE:
2018 Ctrl3 |= PHY_B_P_NO_PAUSE;
2019 break;
2020 case SK_FLOW_MODE_LOC_SEND:
2021 Ctrl3 |= PHY_B_P_ASYM_MD;
2022 break;
2023 case SK_FLOW_MODE_SYMMETRIC:
2024 Ctrl3 |= PHY_B_P_SYM_MD;
2025 break;
2026 case SK_FLOW_MODE_SYM_OR_REM:
2027 Ctrl3 |= PHY_B_P_BOTH_MD;
2028 break;
2029 default:
2030 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E016,
2031 SKERR_HWI_E016MSG);
2032 }
2033
2034
2035 Ctrl1 |= PHY_CT_ANE | PHY_CT_RE_CFG;
2036 }
2037
2038
2039
2040
2041
2042
2043 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_1000T_CTRL, Ctrl2);
2044 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2045 ("Set 1000B-T Ctrl Reg=0x%04X\n", Ctrl2));
2046
2047
2048 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_AUNE_ADV, Ctrl3);
2049 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2050 ("Set Auto-Neg.Adv.Reg=0x%04X\n", Ctrl3));
2051
2052 if (DoLoop) {
2053
2054 Ctrl1 |= PHY_CT_LOOP;
2055 }
2056
2057 if (pAC->GIni.GIPortUsage == SK_JUMBO_LINK) {
2058
2059 Ctrl4 |= PHY_B_PEC_HIGH_LA;
2060
2061
2062 Ctrl5 |= PHY_B_AC_LONG_PACK;
2063
2064 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_AUX_CTRL, Ctrl5);
2065 }
2066
2067
2068 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_P_EXT_CTRL, Ctrl4);
2069
2070
2071 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_CTRL, Ctrl1);
2072 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2073 ("PHY Control Reg=0x%04X\n", Ctrl1));
2074}
2075#endif
2076
2077
2078#ifdef YUKON
2079#ifndef SK_SLIM
2080
2081
2082
2083
2084
2085
2086
2087
2088
2089
2090
2091
2092
2093
2094
2095
2096
2097
2098
2099
2100
2101
2102
2103
2104
2105
2106
2107
2108
2109
2110
2111
2112
2113
2114
2115int SkGmEnterLowPowerMode(
2116SK_AC *pAC,
2117SK_IOC IoC,
2118int Port,
2119SK_U8 Mode)
2120{
2121 SK_U16 Word;
2122 SK_U32 DWord;
2123 SK_U8 LastMode;
2124 int Ret = 0;
2125
2126 if (pAC->GIni.GIYukonLite &&
2127 pAC->GIni.GIChipRev == CHIP_REV_YU_LITE_A3) {
2128
2129
2130 LastMode = pAC->GIni.GP[Port].PPhyPowerState;
2131 pAC->GIni.GP[Port].PPhyPowerState = Mode;
2132
2133 switch (Mode) {
2134
2135 case PHY_PM_DEEP_SLEEP:
2136
2137 GM_OUT16(IoC, 0, GM_GP_CTRL, GM_GPCR_FL_PASS |
2138 GM_GPCR_SPEED_100 | GM_GPCR_AU_ALL_DIS);
2139
2140
2141 SkGmPhyWrite(pAC, IoC, Port, 29, 0x001f);
2142 SkGmPhyWrite(pAC, IoC, Port, 30, 0xfff3);
2143
2144 SK_IN32(IoC, PCI_C(PCI_OUR_REG_1), &DWord);
2145
2146 SK_OUT8(IoC, B2_TST_CTRL1, TST_CFG_WRITE_ON);
2147
2148
2149 SK_OUT32(IoC, PCI_C(PCI_OUR_REG_1), DWord | PCI_PHY_COMA);
2150
2151 SK_OUT8(IoC, B2_TST_CTRL1, TST_CFG_WRITE_OFF);
2152
2153 break;
2154
2155
2156 case PHY_PM_IEEE_POWER_DOWN:
2157
2158
2159
2160
2161 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_PHY_CTRL, &Word);
2162 Word |= PHY_M_PC_DIS_125CLK;
2163 Word &= ~PHY_M_PC_MAC_POW_UP;
2164 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_PHY_CTRL, Word);
2165
2166
2167
2168
2169
2170 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_CTRL, &Word);
2171 Word |= PHY_CT_RESET;
2172 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_CTRL, Word);
2173
2174
2175 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_CTRL, &Word);
2176 Word |= PHY_CT_PDOWN;
2177 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_CTRL, Word);
2178 break;
2179
2180
2181 case PHY_PM_ENERGY_DETECT:
2182 case PHY_PM_ENERGY_DETECT_PLUS:
2183
2184
2185
2186 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_PHY_CTRL, &Word);
2187 Word |= PHY_M_PC_DIS_125CLK;
2188 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_PHY_CTRL, Word);
2189
2190
2191 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_PHY_CTRL, &Word);
2192
2193
2194 if (Mode == PHY_PM_ENERGY_DETECT) {
2195 Word |= PHY_M_PC_EN_DET;
2196 }
2197
2198 else {
2199 Word |= PHY_M_PC_EN_DET_PLUS;
2200 }
2201
2202 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_PHY_CTRL, Word);
2203
2204
2205
2206
2207
2208
2209
2210
2211 SkGmInitPhyMarv(pAC, IoC, Port, SK_FALSE);
2212 break;
2213
2214
2215 default:
2216 pAC->GIni.GP[Port].PPhyPowerState = LastMode;
2217 Ret = 1;
2218 break;
2219 }
2220 }
2221
2222 else {
2223 Ret = 1;
2224 }
2225
2226 return(Ret);
2227
2228}
2229
2230
2231
2232
2233
2234
2235
2236
2237
2238
2239
2240
2241
2242
2243int SkGmLeaveLowPowerMode(
2244SK_AC *pAC,
2245SK_IOC IoC,
2246int Port)
2247{
2248 SK_U32 DWord;
2249 SK_U16 Word;
2250 SK_U8 LastMode;
2251 int Ret = 0;
2252
2253 if (pAC->GIni.GIYukonLite &&
2254 pAC->GIni.GIChipRev == CHIP_REV_YU_LITE_A3) {
2255
2256
2257 LastMode = pAC->GIni.GP[Port].PPhyPowerState;
2258 pAC->GIni.GP[Port].PPhyPowerState = PHY_PM_OPERATIONAL_MODE;
2259
2260 switch (LastMode) {
2261
2262 case PHY_PM_DEEP_SLEEP:
2263 SK_IN32(IoC, PCI_C(PCI_OUR_REG_1), &DWord);
2264
2265 SK_OUT8(IoC, B2_TST_CTRL1, TST_CFG_WRITE_ON);
2266
2267
2268 SK_OUT32(IoC, PCI_C(PCI_OUR_REG_1), DWord & ~PCI_PHY_COMA);
2269
2270 SK_OUT8(IoC, B2_TST_CTRL1, TST_CFG_WRITE_OFF);
2271
2272 SK_IN32(IoC, B2_GP_IO, &DWord);
2273
2274
2275 DWord |= (GP_DIR_9 | GP_IO_9);
2276
2277
2278 SK_OUT32(IoC, B2_GP_IO, DWord);
2279
2280 DWord &= ~GP_IO_9;
2281
2282
2283 SK_OUT32(IoC, B2_GP_IO, DWord);
2284 break;
2285
2286
2287 case PHY_PM_IEEE_POWER_DOWN:
2288
2289
2290
2291
2292 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_PHY_CTRL, &Word);
2293 Word &= ~PHY_M_PC_DIS_125CLK;
2294 Word |= PHY_M_PC_MAC_POW_UP;
2295 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_PHY_CTRL, Word);
2296
2297
2298
2299
2300
2301 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_CTRL, &Word);
2302 Word |= PHY_CT_RESET;
2303 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_CTRL, Word);
2304
2305
2306 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_CTRL, &Word);
2307 Word &= ~PHY_CT_PDOWN;
2308 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_CTRL, Word);
2309 break;
2310
2311
2312 case PHY_PM_ENERGY_DETECT:
2313 case PHY_PM_ENERGY_DETECT_PLUS:
2314
2315
2316
2317 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_PHY_CTRL, &Word);
2318 Word &= ~PHY_M_PC_DIS_125CLK;
2319 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_PHY_CTRL, Word);
2320
2321
2322 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_PHY_CTRL, &Word);
2323 Word &= ~PHY_M_PC_EN_DET_MSK;
2324 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_PHY_CTRL, Word);
2325
2326
2327
2328
2329
2330
2331
2332
2333 SkGmInitPhyMarv(pAC, IoC, Port, SK_FALSE);
2334 break;
2335
2336
2337 default:
2338 pAC->GIni.GP[Port].PPhyPowerState = LastMode;
2339 Ret = 1;
2340 break;
2341 }
2342 }
2343
2344 else {
2345 Ret = 1;
2346 }
2347
2348 return(Ret);
2349
2350}
2351#endif
2352
2353
2354
2355
2356
2357
2358
2359
2360
2361
2362
2363
2364
2365static void SkGmInitPhyMarv(
2366SK_AC *pAC,
2367SK_IOC IoC,
2368int Port,
2369SK_BOOL DoLoop)
2370{
2371 SK_GEPORT *pPrt;
2372 SK_U16 PhyCtrl;
2373 SK_U16 C1000BaseT;
2374 SK_U16 AutoNegAdv;
2375 SK_U16 ExtPhyCtrl;
2376 SK_U16 LedCtrl;
2377 SK_BOOL AutoNeg;
2378#if defined(SK_DIAG) || defined(DEBUG)
2379 SK_U16 PhyStat;
2380 SK_U16 PhyStat1;
2381 SK_U16 PhySpecStat;
2382#endif
2383
2384 pPrt = &pAC->GIni.GP[Port];
2385
2386
2387 if (pPrt->PLinkMode == SK_LMODE_HALF || pPrt->PLinkMode == SK_LMODE_FULL) {
2388 AutoNeg = SK_FALSE;
2389 }
2390 else {
2391 AutoNeg = SK_TRUE;
2392 }
2393
2394 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2395 ("InitPhyMarv: Port %d, auto-negotiation %s\n",
2396 Port, AutoNeg ? "ON" : "OFF"));
2397
2398#ifdef VCPU
2399 VCPUprintf(0, "SkGmInitPhyMarv(), Port=%u, DoLoop=%u\n",
2400 Port, DoLoop);
2401#else
2402 if (DoLoop) {
2403
2404 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_PHY_CTRL,
2405 PHY_M_PC_MAC_POW_UP);
2406 }
2407 else if (AutoNeg && pPrt->PLinkSpeed == SK_LSPEED_AUTO) {
2408
2409 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_EXT_CTRL, &ExtPhyCtrl);
2410
2411 ExtPhyCtrl &= ~(PHY_M_EC_M_DSC_MSK | PHY_M_EC_S_DSC_MSK |
2412 PHY_M_EC_MAC_S_MSK);
2413
2414 ExtPhyCtrl |= PHY_M_EC_MAC_S(MAC_TX_CLK_25_MHZ) |
2415 PHY_M_EC_M_DSC(0) | PHY_M_EC_S_DSC(1);
2416
2417 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_EXT_CTRL, ExtPhyCtrl);
2418 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2419 ("Set Ext. PHY Ctrl=0x%04X\n", ExtPhyCtrl));
2420 }
2421
2422
2423 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_CTRL, &PhyCtrl);
2424
2425 if (!AutoNeg) {
2426
2427 PhyCtrl &= ~PHY_CT_ANE;
2428 }
2429
2430 PhyCtrl |= PHY_CT_RESET;
2431
2432 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_CTRL, PhyCtrl);
2433#endif
2434
2435 PhyCtrl = 0 ;
2436 C1000BaseT = 0;
2437 AutoNegAdv = PHY_SEL_TYPE;
2438
2439
2440 if (pPrt->PMSMode != SK_MS_MODE_AUTO) {
2441
2442 C1000BaseT |= PHY_M_1000C_MSE;
2443
2444 if (pPrt->PMSMode == SK_MS_MODE_MASTER) {
2445 C1000BaseT |= PHY_M_1000C_MSC;
2446 }
2447 }
2448
2449
2450 if (!AutoNeg) {
2451
2452 if (pPrt->PLinkMode == SK_LMODE_FULL) {
2453
2454 PhyCtrl |= PHY_CT_DUP_MD;
2455 }
2456
2457
2458 if (pPrt->PMSMode == SK_MS_MODE_AUTO) {
2459 C1000BaseT |= PHY_M_1000C_MSE;
2460 }
2461
2462
2463 switch (pPrt->PLinkSpeed) {
2464 case SK_LSPEED_AUTO:
2465 case SK_LSPEED_1000MBPS:
2466 PhyCtrl |= PHY_CT_SP1000;
2467 break;
2468 case SK_LSPEED_100MBPS:
2469 PhyCtrl |= PHY_CT_SP100;
2470 break;
2471 case SK_LSPEED_10MBPS:
2472 break;
2473 default:
2474 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E019,
2475 SKERR_HWI_E019MSG);
2476 }
2477
2478 if (!DoLoop) {
2479 PhyCtrl |= PHY_CT_RESET;
2480 }
2481 }
2482 else {
2483
2484
2485 if (pAC->GIni.GICopperType) {
2486
2487 switch (pPrt->PLinkSpeed) {
2488 case SK_LSPEED_AUTO:
2489 C1000BaseT |= PHY_M_1000C_AHD | PHY_M_1000C_AFD;
2490 AutoNegAdv |= PHY_M_AN_100_FD | PHY_M_AN_100_HD |
2491 PHY_M_AN_10_FD | PHY_M_AN_10_HD;
2492 break;
2493 case SK_LSPEED_1000MBPS:
2494 C1000BaseT |= PHY_M_1000C_AHD | PHY_M_1000C_AFD;
2495 break;
2496 case SK_LSPEED_100MBPS:
2497 AutoNegAdv |= PHY_M_AN_100_FD | PHY_M_AN_100_HD |
2498
2499 PHY_M_AN_10_FD | PHY_M_AN_10_HD;
2500 break;
2501 case SK_LSPEED_10MBPS:
2502 AutoNegAdv |= PHY_M_AN_10_FD | PHY_M_AN_10_HD;
2503 break;
2504 default:
2505 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E019,
2506 SKERR_HWI_E019MSG);
2507 }
2508
2509
2510 switch (pPrt->PLinkMode) {
2511 case SK_LMODE_AUTOHALF:
2512 C1000BaseT &= ~PHY_M_1000C_AFD;
2513 AutoNegAdv &= ~(PHY_M_AN_100_FD | PHY_M_AN_10_FD);
2514 break;
2515 case SK_LMODE_AUTOFULL:
2516 C1000BaseT &= ~PHY_M_1000C_AHD;
2517 AutoNegAdv &= ~(PHY_M_AN_100_HD | PHY_M_AN_10_HD);
2518 break;
2519 case SK_LMODE_AUTOBOTH:
2520 break;
2521 default:
2522 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E015,
2523 SKERR_HWI_E015MSG);
2524 }
2525
2526
2527 switch (pPrt->PFlowCtrlMode) {
2528 case SK_FLOW_MODE_NONE:
2529 AutoNegAdv |= PHY_B_P_NO_PAUSE;
2530 break;
2531 case SK_FLOW_MODE_LOC_SEND:
2532 AutoNegAdv |= PHY_B_P_ASYM_MD;
2533 break;
2534 case SK_FLOW_MODE_SYMMETRIC:
2535 AutoNegAdv |= PHY_B_P_SYM_MD;
2536 break;
2537 case SK_FLOW_MODE_SYM_OR_REM:
2538 AutoNegAdv |= PHY_B_P_BOTH_MD;
2539 break;
2540 default:
2541 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E016,
2542 SKERR_HWI_E016MSG);
2543 }
2544 }
2545 else {
2546
2547
2548 switch (pPrt->PLinkMode) {
2549 case SK_LMODE_AUTOHALF:
2550 AutoNegAdv |= PHY_M_AN_1000X_AHD;
2551 break;
2552 case SK_LMODE_AUTOFULL:
2553 AutoNegAdv |= PHY_M_AN_1000X_AFD;
2554 break;
2555 case SK_LMODE_AUTOBOTH:
2556 AutoNegAdv |= PHY_M_AN_1000X_AHD | PHY_M_AN_1000X_AFD;
2557 break;
2558 default:
2559 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E015,
2560 SKERR_HWI_E015MSG);
2561 }
2562
2563
2564 switch (pPrt->PFlowCtrlMode) {
2565 case SK_FLOW_MODE_NONE:
2566 AutoNegAdv |= PHY_M_P_NO_PAUSE_X;
2567 break;
2568 case SK_FLOW_MODE_LOC_SEND:
2569 AutoNegAdv |= PHY_M_P_ASYM_MD_X;
2570 break;
2571 case SK_FLOW_MODE_SYMMETRIC:
2572 AutoNegAdv |= PHY_M_P_SYM_MD_X;
2573 break;
2574 case SK_FLOW_MODE_SYM_OR_REM:
2575 AutoNegAdv |= PHY_M_P_BOTH_MD_X;
2576 break;
2577 default:
2578 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E016,
2579 SKERR_HWI_E016MSG);
2580 }
2581 }
2582
2583 if (!DoLoop) {
2584
2585 PhyCtrl |= PHY_CT_ANE | PHY_CT_RE_CFG;
2586 }
2587 }
2588
2589#ifdef VCPU
2590
2591
2592
2593
2594
2595 SkGmPhyWrite(pAC, IoC, Port, 30, 0x0700 );
2596
2597 VCpuWait(2000);
2598
2599#else
2600
2601
2602 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_1000T_CTRL, C1000BaseT);
2603 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2604 ("Set 1000B-T Ctrl =0x%04X\n", C1000BaseT));
2605
2606
2607 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_AUNE_ADV, AutoNegAdv);
2608 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2609 ("Set Auto-Neg.Adv.=0x%04X\n", AutoNegAdv));
2610#endif
2611
2612 if (DoLoop) {
2613
2614 PhyCtrl |= PHY_CT_LOOP;
2615
2616#ifdef XXX
2617
2618 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_PHY_CTRL, PHY_M_PC_FL_GOOD);
2619#endif
2620
2621#ifndef VCPU
2622 if (pPrt->PLinkSpeed != SK_LSPEED_AUTO) {
2623
2624 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_EXT_CTRL,
2625 (SK_U16)((pPrt->PLinkSpeed + 2) << 4));
2626 }
2627#endif
2628 }
2629#ifdef TEST_ONLY
2630 else if (pPrt->PLinkSpeed == SK_LSPEED_10MBPS) {
2631
2632 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_PHY_CTRL,
2633 PHY_M_PC_EN_DET_MSK);
2634 }
2635#endif
2636
2637
2638 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_CTRL, PhyCtrl);
2639 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2640 ("Set PHY Ctrl Reg.=0x%04X\n", PhyCtrl));
2641
2642#ifdef VCPU
2643 VCpuWait(2000);
2644#else
2645
2646 LedCtrl = PHY_M_LED_PULS_DUR(PULS_170MS) | PHY_M_LED_BLINK_RT(BLINK_84MS);
2647
2648 if ((pAC->GIni.GILedBlinkCtrl & SK_ACT_LED_BLINK) != 0) {
2649 LedCtrl |= PHY_M_LEDC_RX_CTRL | PHY_M_LEDC_TX_CTRL;
2650 }
2651
2652 if ((pAC->GIni.GILedBlinkCtrl & SK_DUP_LED_NORMAL) != 0) {
2653 LedCtrl |= PHY_M_LEDC_DP_CTRL;
2654 }
2655
2656 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_LED_CTRL, LedCtrl);
2657
2658 if ((pAC->GIni.GILedBlinkCtrl & SK_LED_LINK100_ON) != 0) {
2659
2660 if (!AutoNeg && pPrt->PLinkSpeed == SK_LSPEED_100MBPS) {
2661
2662 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_LED_OVER,
2663 PHY_M_LED_MO_100(MO_LED_ON));
2664 }
2665 }
2666
2667#ifdef SK_DIAG
2668 c_print("Set PHY Ctrl=0x%04X\n", PhyCtrl);
2669 c_print("Set 1000 B-T=0x%04X\n", C1000BaseT);
2670 c_print("Set Auto-Neg=0x%04X\n", AutoNegAdv);
2671 c_print("Set Ext Ctrl=0x%04X\n", ExtPhyCtrl);
2672#endif
2673
2674#if defined(SK_DIAG) || defined(DEBUG)
2675
2676 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_CTRL, &PhyCtrl);
2677 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2678 ("PHY Ctrl Reg.=0x%04X\n", PhyCtrl));
2679
2680
2681 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_1000T_CTRL, &C1000BaseT);
2682 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2683 ("1000B-T Ctrl =0x%04X\n", C1000BaseT));
2684
2685
2686 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_AUNE_ADV, &AutoNegAdv);
2687 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2688 ("Auto-Neg.Adv.=0x%04X\n", AutoNegAdv));
2689
2690
2691 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_EXT_CTRL, &ExtPhyCtrl);
2692 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2693 ("Ext. PHY Ctrl=0x%04X\n", ExtPhyCtrl));
2694
2695
2696 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_STAT, &PhyStat);
2697 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2698 ("PHY Stat Reg.=0x%04X\n", PhyStat));
2699 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_STAT, &PhyStat1);
2700 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2701 ("PHY Stat Reg.=0x%04X\n", PhyStat1));
2702
2703
2704 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_PHY_STAT, &PhySpecStat);
2705 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2706 ("PHY Spec Stat=0x%04X\n", PhySpecStat));
2707#endif
2708
2709#ifdef SK_DIAG
2710 c_print("PHY Ctrl Reg=0x%04X\n", PhyCtrl);
2711 c_print("PHY 1000 Reg=0x%04X\n", C1000BaseT);
2712 c_print("PHY AnAd Reg=0x%04X\n", AutoNegAdv);
2713 c_print("Ext Ctrl Reg=0x%04X\n", ExtPhyCtrl);
2714 c_print("PHY Stat Reg=0x%04X\n", PhyStat);
2715 c_print("PHY Stat Reg=0x%04X\n", PhyStat1);
2716 c_print("PHY Spec Reg=0x%04X\n", PhySpecStat);
2717#endif
2718
2719#endif
2720
2721}
2722#endif
2723
2724
2725#ifdef OTHER_PHY
2726
2727
2728
2729
2730
2731
2732
2733
2734
2735
2736
2737static void SkXmInitPhyLone(
2738SK_AC *pAC,
2739SK_IOC IoC,
2740int Port,
2741SK_BOOL DoLoop)
2742{
2743 SK_GEPORT *pPrt;
2744 SK_U16 Ctrl1;
2745 SK_U16 Ctrl2;
2746 SK_U16 Ctrl3;
2747
2748 Ctrl1 = PHY_CT_SP1000;
2749 Ctrl2 = 0;
2750 Ctrl3 = PHY_SEL_TYPE;
2751
2752 pPrt = &pAC->GIni.GP[Port];
2753
2754
2755 if (pPrt->PMSMode != SK_MS_MODE_AUTO) {
2756 Ctrl2 |= PHY_L_1000C_MSE;
2757
2758 if (pPrt->PMSMode == SK_MS_MODE_MASTER) {
2759 Ctrl2 |= PHY_L_1000C_MSC;
2760 }
2761 }
2762
2763 if (pPrt->PLinkMode == SK_LMODE_HALF || pPrt->PLinkMode == SK_LMODE_FULL) {
2764
2765
2766
2767
2768 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2769 ("InitPhyLone: no auto-negotiation Port %d\n", Port));
2770
2771 if (pPrt->PLinkMode == SK_LMODE_FULL) {
2772 Ctrl1 |= PHY_CT_DUP_MD;
2773 }
2774
2775
2776 if (pPrt->PMSMode == SK_MS_MODE_AUTO) {
2777 Ctrl2 |= PHY_L_1000C_MSE;
2778 }
2779
2780
2781
2782
2783
2784 }
2785 else {
2786 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2787 ("InitPhyLone: with auto-negotiation Port %d\n", Port));
2788
2789
2790
2791 switch (pPrt->PLinkMode) {
2792 case SK_LMODE_AUTOHALF:
2793 Ctrl2 |= PHY_L_1000C_AHD;
2794 break;
2795 case SK_LMODE_AUTOFULL:
2796 Ctrl2 |= PHY_L_1000C_AFD;
2797 break;
2798 case SK_LMODE_AUTOBOTH:
2799 Ctrl2 |= PHY_L_1000C_AFD | PHY_L_1000C_AHD;
2800 break;
2801 default:
2802 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E015,
2803 SKERR_HWI_E015MSG);
2804 }
2805
2806
2807 switch (pPrt->PFlowCtrlMode) {
2808 case SK_FLOW_MODE_NONE:
2809 Ctrl3 |= PHY_L_P_NO_PAUSE;
2810 break;
2811 case SK_FLOW_MODE_LOC_SEND:
2812 Ctrl3 |= PHY_L_P_ASYM_MD;
2813 break;
2814 case SK_FLOW_MODE_SYMMETRIC:
2815 Ctrl3 |= PHY_L_P_SYM_MD;
2816 break;
2817 case SK_FLOW_MODE_SYM_OR_REM:
2818 Ctrl3 |= PHY_L_P_BOTH_MD;
2819 break;
2820 default:
2821 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E016,
2822 SKERR_HWI_E016MSG);
2823 }
2824
2825
2826 Ctrl1 = PHY_CT_ANE | PHY_CT_RE_CFG;
2827 }
2828
2829
2830 SkXmPhyWrite(pAC, IoC, Port, PHY_LONE_1000T_CTRL, Ctrl2);
2831 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2832 ("1000B-T Ctrl Reg=0x%04X\n", Ctrl2));
2833
2834
2835 SkXmPhyWrite(pAC, IoC, Port, PHY_LONE_AUNE_ADV, Ctrl3);
2836 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2837 ("Auto-Neg.Adv.Reg=0x%04X\n", Ctrl3));
2838
2839 if (DoLoop) {
2840
2841 Ctrl1 |= PHY_CT_LOOP;
2842 }
2843
2844
2845 SkXmPhyWrite(pAC, IoC, Port, PHY_LONE_CTRL, Ctrl1);
2846 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2847 ("PHY Control Reg=0x%04X\n", Ctrl1));
2848}
2849
2850
2851
2852
2853
2854
2855
2856
2857
2858
2859
2860
2861
2862static void SkXmInitPhyNat(
2863SK_AC *pAC,
2864SK_IOC IoC,
2865int Port,
2866SK_BOOL DoLoop)
2867{
2868
2869}
2870#endif
2871
2872
2873
2874
2875
2876
2877
2878
2879
2880
2881
2882
2883
2884void SkMacInitPhy(
2885SK_AC *pAC,
2886SK_IOC IoC,
2887int Port,
2888SK_BOOL DoLoop)
2889{
2890 SK_GEPORT *pPrt;
2891
2892 pPrt = &pAC->GIni.GP[Port];
2893
2894#ifdef GENESIS
2895 if (pAC->GIni.GIGenesis) {
2896
2897 switch (pPrt->PhyType) {
2898 case SK_PHY_XMAC:
2899 SkXmInitPhyXmac(pAC, IoC, Port, DoLoop);
2900 break;
2901 case SK_PHY_BCOM:
2902 SkXmInitPhyBcom(pAC, IoC, Port, DoLoop);
2903 break;
2904#ifdef OTHER_PHY
2905 case SK_PHY_LONE:
2906 SkXmInitPhyLone(pAC, IoC, Port, DoLoop);
2907 break;
2908 case SK_PHY_NAT:
2909 SkXmInitPhyNat(pAC, IoC, Port, DoLoop);
2910 break;
2911#endif
2912 }
2913 }
2914#endif
2915
2916#ifdef YUKON
2917 if (pAC->GIni.GIYukon) {
2918
2919 SkGmInitPhyMarv(pAC, IoC, Port, DoLoop);
2920 }
2921#endif
2922
2923}
2924
2925
2926#ifdef GENESIS
2927
2928
2929
2930
2931
2932
2933
2934
2935
2936
2937
2938
2939static int SkXmAutoNegDoneXmac(
2940SK_AC *pAC,
2941SK_IOC IoC,
2942int Port)
2943{
2944 SK_GEPORT *pPrt;
2945 SK_U16 ResAb;
2946 SK_U16 LPAb;
2947
2948 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2949 ("AutoNegDoneXmac, Port %d\n", Port));
2950
2951 pPrt = &pAC->GIni.GP[Port];
2952
2953
2954 SkXmPhyRead(pAC, IoC, Port, PHY_XMAC_AUNE_LP, &LPAb);
2955 SkXmPhyRead(pAC, IoC, Port, PHY_XMAC_RES_ABI, &ResAb);
2956
2957 if ((LPAb & PHY_X_AN_RFB) != 0) {
2958
2959
2960 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2961 ("AutoNegFail: Remote fault bit set Port %d\n", Port));
2962 pPrt->PAutoNegFail = SK_TRUE;
2963 return(SK_AND_OTHER);
2964 }
2965
2966
2967 if ((ResAb & (PHY_X_RS_HD | PHY_X_RS_FD)) == PHY_X_RS_FD) {
2968 pPrt->PLinkModeStatus = (SK_U8)SK_LMODE_STAT_AUTOFULL;
2969 }
2970 else if ((ResAb & (PHY_X_RS_HD | PHY_X_RS_FD)) == PHY_X_RS_HD) {
2971 pPrt->PLinkModeStatus = (SK_U8)SK_LMODE_STAT_AUTOHALF;
2972 }
2973 else {
2974
2975 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
2976 ("AutoNegFail: Duplex mode mismatch Port %d\n", Port));
2977 pPrt->PAutoNegFail = SK_TRUE;
2978 return(SK_AND_DUP_CAP);
2979 }
2980
2981
2982
2983
2984 if ((pPrt->PFlowCtrlMode == SK_FLOW_MODE_SYMMETRIC ||
2985 pPrt->PFlowCtrlMode == SK_FLOW_MODE_SYM_OR_REM) &&
2986 (LPAb & PHY_X_P_SYM_MD) != 0) {
2987
2988 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_SYMMETRIC;
2989 }
2990 else if (pPrt->PFlowCtrlMode == SK_FLOW_MODE_SYM_OR_REM &&
2991 (LPAb & PHY_X_RS_PAUSE) == PHY_X_P_ASYM_MD) {
2992
2993 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_REM_SEND;
2994 }
2995 else if (pPrt->PFlowCtrlMode == SK_FLOW_MODE_LOC_SEND &&
2996 (LPAb & PHY_X_RS_PAUSE) == PHY_X_P_BOTH_MD) {
2997
2998 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_LOC_SEND;
2999 }
3000 else {
3001
3002 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_NONE;
3003 }
3004 pPrt->PLinkSpeedUsed = (SK_U8)SK_LSPEED_STAT_1000MBPS;
3005
3006 return(SK_AND_OK);
3007}
3008
3009
3010
3011
3012
3013
3014
3015
3016
3017
3018
3019
3020
3021
3022static int SkXmAutoNegDoneBcom(
3023SK_AC *pAC,
3024SK_IOC IoC,
3025int Port)
3026{
3027 SK_GEPORT *pPrt;
3028 SK_U16 LPAb;
3029 SK_U16 AuxStat;
3030
3031#ifdef TEST_ONLY
303201-Sep-2000 RA;:;:
3033 SK_U16 ResAb;
3034#endif
3035
3036 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3037 ("AutoNegDoneBcom, Port %d\n", Port));
3038 pPrt = &pAC->GIni.GP[Port];
3039
3040
3041 SkXmPhyRead(pAC, IoC, Port, PHY_BCOM_AUNE_LP, &LPAb);
3042#ifdef TEST_ONLY
304301-Sep-2000 RA;:;:
3044 SkXmPhyRead(pAC, IoC, Port, PHY_BCOM_1000T_STAT, &ResAb);
3045#endif
3046
3047 SkXmPhyRead(pAC, IoC, Port, PHY_BCOM_AUX_STAT, &AuxStat);
3048
3049 if ((LPAb & PHY_B_AN_RF) != 0) {
3050
3051 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3052 ("AutoNegFail: Remote fault bit set Port %d\n", Port));
3053 pPrt->PAutoNegFail = SK_TRUE;
3054 return(SK_AND_OTHER);
3055 }
3056
3057
3058 if ((AuxStat & PHY_B_AS_AN_RES_MSK) == PHY_B_RES_1000FD) {
3059 pPrt->PLinkModeStatus = (SK_U8)SK_LMODE_STAT_AUTOFULL;
3060 }
3061 else if ((AuxStat & PHY_B_AS_AN_RES_MSK) == PHY_B_RES_1000HD) {
3062 pPrt->PLinkModeStatus = (SK_U8)SK_LMODE_STAT_AUTOHALF;
3063 }
3064 else {
3065
3066 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3067 ("AutoNegFail: Duplex mode mismatch Port %d\n", Port));
3068 pPrt->PAutoNegFail = SK_TRUE;
3069 return(SK_AND_DUP_CAP);
3070 }
3071
3072#ifdef TEST_ONLY
307301-Sep-2000 RA;:;:
3074
3075 if ((ResAb & PHY_B_1000S_MSF) != 0) {
3076 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3077 ("Master/Slave Fault Port %d\n", Port));
3078 pPrt->PAutoNegFail = SK_TRUE;
3079 pPrt->PMSStatus = SK_MS_STAT_FAULT;
3080 return(SK_AND_OTHER);
3081 }
3082
3083 pPrt->PMSStatus = ((ResAb & PHY_B_1000S_MSR) != 0) ?
3084 SK_MS_STAT_MASTER : SK_MS_STAT_SLAVE;
3085#endif
3086
3087
3088
3089 if ((AuxStat & PHY_B_AS_PAUSE_MSK) == PHY_B_AS_PAUSE_MSK) {
3090
3091 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_SYMMETRIC;
3092 }
3093 else if ((AuxStat & PHY_B_AS_PAUSE_MSK) == PHY_B_AS_PRR) {
3094
3095 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_REM_SEND;
3096 }
3097 else if ((AuxStat & PHY_B_AS_PAUSE_MSK) == PHY_B_AS_PRT) {
3098
3099 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_LOC_SEND;
3100 }
3101 else {
3102
3103 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_NONE;
3104 }
3105 pPrt->PLinkSpeedUsed = (SK_U8)SK_LSPEED_STAT_1000MBPS;
3106
3107 return(SK_AND_OK);
3108}
3109#endif
3110
3111
3112#ifdef YUKON
3113
3114
3115
3116
3117
3118
3119
3120
3121
3122
3123
3124
3125static int SkGmAutoNegDoneMarv(
3126SK_AC *pAC,
3127SK_IOC IoC,
3128int Port)
3129{
3130 SK_GEPORT *pPrt;
3131 SK_U16 LPAb;
3132 SK_U16 ResAb;
3133 SK_U16 AuxStat;
3134
3135 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3136 ("AutoNegDoneMarv, Port %d\n", Port));
3137 pPrt = &pAC->GIni.GP[Port];
3138
3139
3140 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_AUNE_LP, &LPAb);
3141 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3142 ("Link P.Abil.=0x%04X\n", LPAb));
3143
3144 if ((LPAb & PHY_M_AN_RF) != 0) {
3145 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3146 ("AutoNegFail: Remote fault bit set Port %d\n", Port));
3147 pPrt->PAutoNegFail = SK_TRUE;
3148 return(SK_AND_OTHER);
3149 }
3150
3151 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_1000T_STAT, &ResAb);
3152
3153
3154 if ((ResAb & PHY_B_1000S_MSF) != 0) {
3155 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3156 ("Master/Slave Fault Port %d\n", Port));
3157 pPrt->PAutoNegFail = SK_TRUE;
3158 pPrt->PMSStatus = SK_MS_STAT_FAULT;
3159 return(SK_AND_OTHER);
3160 }
3161
3162 pPrt->PMSStatus = ((ResAb & PHY_B_1000S_MSR) != 0) ?
3163 (SK_U8)SK_MS_STAT_MASTER : (SK_U8)SK_MS_STAT_SLAVE;
3164
3165
3166 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_PHY_STAT, &AuxStat);
3167
3168
3169 if ((AuxStat & PHY_M_PS_SPDUP_RES) == 0) {
3170 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3171 ("AutoNegFail: Speed & Duplex not resolved, Port %d\n", Port));
3172 pPrt->PAutoNegFail = SK_TRUE;
3173 pPrt->PLinkModeStatus = (SK_U8)SK_LMODE_STAT_UNKNOWN;
3174 return(SK_AND_DUP_CAP);
3175 }
3176
3177 if ((AuxStat & PHY_M_PS_FULL_DUP) != 0) {
3178 pPrt->PLinkModeStatus = (SK_U8)SK_LMODE_STAT_AUTOFULL;
3179 }
3180 else {
3181 pPrt->PLinkModeStatus = (SK_U8)SK_LMODE_STAT_AUTOHALF;
3182 }
3183
3184
3185
3186 if ((AuxStat & PHY_M_PS_PAUSE_MSK) == PHY_M_PS_PAUSE_MSK) {
3187
3188 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_SYMMETRIC;
3189 }
3190 else if ((AuxStat & PHY_M_PS_PAUSE_MSK) == PHY_M_PS_RX_P_EN) {
3191
3192 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_REM_SEND;
3193 }
3194 else if ((AuxStat & PHY_M_PS_PAUSE_MSK) == PHY_M_PS_TX_P_EN) {
3195
3196 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_LOC_SEND;
3197 }
3198 else {
3199
3200 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_NONE;
3201 }
3202
3203
3204 switch ((unsigned)(AuxStat & PHY_M_PS_SPEED_MSK)) {
3205 case (unsigned)PHY_M_PS_SPEED_1000:
3206 pPrt->PLinkSpeedUsed = (SK_U8)SK_LSPEED_STAT_1000MBPS;
3207 break;
3208 case PHY_M_PS_SPEED_100:
3209 pPrt->PLinkSpeedUsed = (SK_U8)SK_LSPEED_STAT_100MBPS;
3210 break;
3211 default:
3212 pPrt->PLinkSpeedUsed = (SK_U8)SK_LSPEED_STAT_10MBPS;
3213 }
3214
3215 return(SK_AND_OK);
3216}
3217#endif
3218
3219
3220#ifdef OTHER_PHY
3221
3222
3223
3224
3225
3226
3227
3228
3229
3230
3231
3232
3233static int SkXmAutoNegDoneLone(
3234SK_AC *pAC,
3235SK_IOC IoC,
3236int Port)
3237{
3238 SK_GEPORT *pPrt;
3239 SK_U16 ResAb;
3240 SK_U16 LPAb;
3241 SK_U16 QuickStat;
3242
3243 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3244 ("AutoNegDoneLone, Port %d\n", Port));
3245 pPrt = &pAC->GIni.GP[Port];
3246
3247
3248 SkXmPhyRead(pAC, IoC, Port, PHY_LONE_AUNE_LP, &LPAb);
3249 SkXmPhyRead(pAC, IoC, Port, PHY_LONE_1000T_STAT, &ResAb);
3250 SkXmPhyRead(pAC, IoC, Port, PHY_LONE_Q_STAT, &QuickStat);
3251
3252 if ((LPAb & PHY_L_AN_RF) != 0) {
3253
3254
3255 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3256 ("AutoNegFail: Remote fault bit set Port %d\n", Port));
3257 pPrt->PAutoNegFail = SK_TRUE;
3258 return(SK_AND_OTHER);
3259 }
3260
3261
3262 if ((QuickStat & PHY_L_QS_DUP_MOD) != 0) {
3263 pPrt->PLinkModeStatus = (SK_U8)SK_LMODE_STAT_AUTOFULL;
3264 }
3265 else {
3266 pPrt->PLinkModeStatus = (SK_U8)SK_LMODE_STAT_AUTOHALF;
3267 }
3268
3269
3270 if ((ResAb & PHY_L_1000S_MSF) != 0) {
3271
3272 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3273 ("Master/Slave Fault Port %d\n", Port));
3274 pPrt->PAutoNegFail = SK_TRUE;
3275 pPrt->PMSStatus = SK_MS_STAT_FAULT;
3276 return(SK_AND_OTHER);
3277 }
3278 else if (ResAb & PHY_L_1000S_MSR) {
3279 pPrt->PMSStatus = SK_MS_STAT_MASTER;
3280 }
3281 else {
3282 pPrt->PMSStatus = SK_MS_STAT_SLAVE;
3283 }
3284
3285
3286
3287
3288 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_NONE;
3289
3290 switch (pPrt->PFlowCtrlMode) {
3291 case SK_FLOW_MODE_NONE:
3292
3293 break;
3294 case SK_FLOW_MODE_LOC_SEND:
3295 if ((QuickStat & (PHY_L_QS_PAUSE | PHY_L_QS_AS_PAUSE)) ==
3296 (PHY_L_QS_PAUSE | PHY_L_QS_AS_PAUSE)) {
3297
3298 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_LOC_SEND;
3299 }
3300 break;
3301 case SK_FLOW_MODE_SYMMETRIC:
3302 if ((QuickStat & PHY_L_QS_PAUSE) != 0) {
3303
3304 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_SYMMETRIC;
3305 }
3306 break;
3307 case SK_FLOW_MODE_SYM_OR_REM:
3308 if ((QuickStat & (PHY_L_QS_PAUSE | PHY_L_QS_AS_PAUSE)) ==
3309 PHY_L_QS_AS_PAUSE) {
3310
3311 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_REM_SEND;
3312 }
3313 else if ((QuickStat & PHY_L_QS_PAUSE) != 0) {
3314
3315 pPrt->PFlowCtrlStatus = SK_FLOW_STAT_SYMMETRIC;
3316 }
3317 break;
3318 default:
3319 SK_ERR_LOG(pAC, SK_ERRCL_SW | SK_ERRCL_INIT, SKERR_HWI_E016,
3320 SKERR_HWI_E016MSG);
3321 }
3322
3323 return(SK_AND_OK);
3324}
3325
3326
3327
3328
3329
3330
3331
3332
3333
3334
3335
3336
3337
3338
3339static int SkXmAutoNegDoneNat(
3340SK_AC *pAC,
3341SK_IOC IoC,
3342int Port)
3343{
3344
3345 return(SK_AND_OK);
3346}
3347#endif
3348
3349
3350
3351
3352
3353
3354
3355
3356
3357
3358
3359
3360
3361int SkMacAutoNegDone(
3362SK_AC *pAC,
3363SK_IOC IoC,
3364int Port)
3365{
3366 SK_GEPORT *pPrt;
3367 int Rtv;
3368
3369 Rtv = SK_AND_OK;
3370
3371 pPrt = &pAC->GIni.GP[Port];
3372
3373#ifdef GENESIS
3374 if (pAC->GIni.GIGenesis) {
3375
3376 switch (pPrt->PhyType) {
3377
3378 case SK_PHY_XMAC:
3379 Rtv = SkXmAutoNegDoneXmac(pAC, IoC, Port);
3380 break;
3381 case SK_PHY_BCOM:
3382 Rtv = SkXmAutoNegDoneBcom(pAC, IoC, Port);
3383 break;
3384#ifdef OTHER_PHY
3385 case SK_PHY_LONE:
3386 Rtv = SkXmAutoNegDoneLone(pAC, IoC, Port);
3387 break;
3388 case SK_PHY_NAT:
3389 Rtv = SkXmAutoNegDoneNat(pAC, IoC, Port);
3390 break;
3391#endif
3392 default:
3393 return(SK_AND_OTHER);
3394 }
3395 }
3396#endif
3397
3398#ifdef YUKON
3399 if (pAC->GIni.GIYukon) {
3400
3401 Rtv = SkGmAutoNegDoneMarv(pAC, IoC, Port);
3402 }
3403#endif
3404
3405 if (Rtv != SK_AND_OK) {
3406 return(Rtv);
3407 }
3408
3409 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3410 ("AutoNeg done Port %d\n", Port));
3411
3412
3413 pPrt->PAutoNegFail = SK_FALSE;
3414
3415 SkMacRxTxEnable(pAC, IoC, Port);
3416
3417 return(SK_AND_OK);
3418}
3419
3420
3421#ifdef GENESIS
3422
3423
3424
3425
3426
3427
3428
3429
3430
3431
3432static void SkXmSetRxTxEn(
3433SK_AC *pAC,
3434SK_IOC IoC,
3435int Port,
3436int Para)
3437{
3438 SK_U16 Word;
3439
3440 XM_IN16(IoC, Port, XM_MMU_CMD, &Word);
3441
3442 switch (Para & (SK_MAC_LOOPB_ON | SK_MAC_LOOPB_OFF)) {
3443 case SK_MAC_LOOPB_ON:
3444 Word |= XM_MMU_MAC_LB;
3445 break;
3446 case SK_MAC_LOOPB_OFF:
3447 Word &= ~XM_MMU_MAC_LB;
3448 break;
3449 }
3450
3451 switch (Para & (SK_PHY_LOOPB_ON | SK_PHY_LOOPB_OFF)) {
3452 case SK_PHY_LOOPB_ON:
3453 Word |= XM_MMU_GMII_LOOP;
3454 break;
3455 case SK_PHY_LOOPB_OFF:
3456 Word &= ~XM_MMU_GMII_LOOP;
3457 break;
3458 }
3459
3460 switch (Para & (SK_PHY_FULLD_ON | SK_PHY_FULLD_OFF)) {
3461 case SK_PHY_FULLD_ON:
3462 Word |= XM_MMU_GMII_FD;
3463 break;
3464 case SK_PHY_FULLD_OFF:
3465 Word &= ~XM_MMU_GMII_FD;
3466 break;
3467 }
3468
3469 XM_OUT16(IoC, Port, XM_MMU_CMD, Word | XM_MMU_ENA_RX | XM_MMU_ENA_TX);
3470
3471
3472 XM_IN16(IoC, Port, XM_MMU_CMD, &Word);
3473
3474}
3475#endif
3476
3477
3478#ifdef YUKON
3479
3480
3481
3482
3483
3484
3485
3486
3487
3488
3489static void SkGmSetRxTxEn(
3490SK_AC *pAC,
3491SK_IOC IoC,
3492int Port,
3493int Para)
3494{
3495 SK_U16 Ctrl;
3496
3497 GM_IN16(IoC, Port, GM_GP_CTRL, &Ctrl);
3498
3499 switch (Para & (SK_MAC_LOOPB_ON | SK_MAC_LOOPB_OFF)) {
3500 case SK_MAC_LOOPB_ON:
3501 Ctrl |= GM_GPCR_LOOP_ENA;
3502 break;
3503 case SK_MAC_LOOPB_OFF:
3504 Ctrl &= ~GM_GPCR_LOOP_ENA;
3505 break;
3506 }
3507
3508 switch (Para & (SK_PHY_FULLD_ON | SK_PHY_FULLD_OFF)) {
3509 case SK_PHY_FULLD_ON:
3510 Ctrl |= GM_GPCR_DUP_FULL;
3511 break;
3512 case SK_PHY_FULLD_OFF:
3513 Ctrl &= ~GM_GPCR_DUP_FULL;
3514 break;
3515 }
3516
3517 GM_OUT16(IoC, Port, GM_GP_CTRL, (SK_U16)(Ctrl | GM_GPCR_RX_ENA |
3518 GM_GPCR_TX_ENA));
3519
3520
3521 GM_IN16(IoC, Port, GM_GP_CTRL, &Ctrl);
3522
3523}
3524#endif
3525
3526
3527#ifndef SK_SLIM
3528
3529
3530
3531
3532
3533
3534
3535
3536void SkMacSetRxTxEn(
3537SK_AC *pAC,
3538SK_IOC IoC,
3539int Port,
3540int Para)
3541{
3542#ifdef GENESIS
3543 if (pAC->GIni.GIGenesis) {
3544
3545 SkXmSetRxTxEn(pAC, IoC, Port, Para);
3546 }
3547#endif
3548
3549#ifdef YUKON
3550 if (pAC->GIni.GIYukon) {
3551
3552 SkGmSetRxTxEn(pAC, IoC, Port, Para);
3553 }
3554#endif
3555
3556}
3557#endif
3558
3559
3560
3561
3562
3563
3564
3565
3566
3567
3568
3569
3570int SkMacRxTxEnable(
3571SK_AC *pAC,
3572SK_IOC IoC,
3573int Port)
3574{
3575 SK_GEPORT *pPrt;
3576 SK_U16 Reg;
3577 SK_U16 IntMask;
3578#ifdef GENESIS
3579 SK_U16 SWord;
3580#endif
3581
3582 pPrt = &pAC->GIni.GP[Port];
3583
3584 if (!pPrt->PHWLinkUp) {
3585
3586 return(0);
3587 }
3588
3589 if ((pPrt->PLinkMode == SK_LMODE_AUTOHALF ||
3590 pPrt->PLinkMode == SK_LMODE_AUTOFULL ||
3591 pPrt->PLinkMode == SK_LMODE_AUTOBOTH) &&
3592 pPrt->PAutoNegFail) {
3593
3594 return(0);
3595 }
3596
3597#ifdef GENESIS
3598 if (pAC->GIni.GIGenesis) {
3599
3600 SkXmInitDupMd(pAC, IoC, Port);
3601
3602 SkXmInitPauseMd(pAC, IoC, Port);
3603
3604
3605
3606
3607
3608
3609
3610
3611
3612
3613 IntMask = XM_DEF_MSK;
3614
3615#ifdef DEBUG
3616
3617 IntMask &= ~XM_IS_RXF_OV;
3618#endif
3619
3620 if (pPrt->PhyType != SK_PHY_XMAC) {
3621
3622 IntMask |= XM_IS_INP_ASS;
3623 }
3624 XM_OUT16(IoC, Port, XM_IMSK, IntMask);
3625
3626
3627 XM_IN16(IoC, Port, XM_MMU_CMD, &Reg);
3628
3629 if (pPrt->PhyType != SK_PHY_XMAC &&
3630 (pPrt->PLinkModeStatus == SK_LMODE_STAT_FULL ||
3631 pPrt->PLinkModeStatus == SK_LMODE_STAT_AUTOFULL)) {
3632
3633 Reg |= XM_MMU_GMII_FD;
3634 }
3635
3636 switch (pPrt->PhyType) {
3637 case SK_PHY_BCOM:
3638
3639
3640
3641
3642 SkXmPhyRead(pAC, IoC, Port, PHY_BCOM_AUX_CTRL, &SWord);
3643 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_AUX_CTRL,
3644 (SK_U16)(SWord & ~PHY_B_AC_DIS_PM));
3645 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_INT_MASK,
3646 (SK_U16)PHY_B_DEF_MSK);
3647 break;
3648#ifdef OTHER_PHY
3649 case SK_PHY_LONE:
3650 SkXmPhyWrite(pAC, IoC, Port, PHY_LONE_INT_ENAB, PHY_L_DEF_MSK);
3651 break;
3652 case SK_PHY_NAT:
3653
3654
3655
3656 break;
3657#endif
3658 }
3659
3660
3661 XM_OUT16(IoC, Port, XM_MMU_CMD, Reg | XM_MMU_ENA_RX | XM_MMU_ENA_TX);
3662 }
3663#endif
3664
3665#ifdef YUKON
3666 if (pAC->GIni.GIYukon) {
3667
3668
3669
3670
3671
3672
3673 IntMask = GMAC_DEF_MSK;
3674
3675#ifdef DEBUG
3676
3677 IntMask |= GM_IS_RX_FF_OR;
3678#endif
3679
3680 SK_OUT8(IoC, GMAC_IRQ_MSK, (SK_U8)IntMask);
3681
3682
3683 GM_IN16(IoC, Port, GM_GP_CTRL, &Reg);
3684
3685 if (pPrt->PLinkModeStatus == SK_LMODE_STAT_FULL ||
3686 pPrt->PLinkModeStatus == SK_LMODE_STAT_AUTOFULL) {
3687
3688 Reg |= GM_GPCR_DUP_FULL;
3689 }
3690
3691
3692 GM_OUT16(IoC, Port, GM_GP_CTRL, (SK_U16)(Reg | GM_GPCR_RX_ENA |
3693 GM_GPCR_TX_ENA));
3694
3695#ifndef VCPU
3696
3697 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_INT_MASK,
3698 (SK_U16)PHY_M_DEF_MSK);
3699#endif
3700 }
3701#endif
3702
3703 return(0);
3704
3705}
3706
3707
3708
3709
3710
3711
3712
3713
3714
3715
3716void SkMacRxTxDisable(
3717SK_AC *pAC,
3718SK_IOC IoC,
3719int Port)
3720{
3721 SK_U16 Word;
3722
3723#ifdef GENESIS
3724 if (pAC->GIni.GIGenesis) {
3725
3726 XM_IN16(IoC, Port, XM_MMU_CMD, &Word);
3727
3728 XM_OUT16(IoC, Port, XM_MMU_CMD, Word & ~(XM_MMU_ENA_RX | XM_MMU_ENA_TX));
3729
3730
3731 XM_IN16(IoC, Port, XM_MMU_CMD, &Word);
3732 }
3733#endif
3734
3735#ifdef YUKON
3736 if (pAC->GIni.GIYukon) {
3737
3738 GM_IN16(IoC, Port, GM_GP_CTRL, &Word);
3739
3740 GM_OUT16(IoC, Port, GM_GP_CTRL, (SK_U16)(Word & ~(GM_GPCR_RX_ENA |
3741 GM_GPCR_TX_ENA)));
3742
3743
3744 GM_IN16(IoC, Port, GM_GP_CTRL, &Word);
3745 }
3746#endif
3747
3748}
3749
3750
3751
3752
3753
3754
3755
3756
3757
3758
3759void SkMacIrqDisable(
3760SK_AC *pAC,
3761SK_IOC IoC,
3762int Port)
3763{
3764 SK_GEPORT *pPrt;
3765#ifdef GENESIS
3766 SK_U16 Word;
3767#endif
3768
3769 pPrt = &pAC->GIni.GP[Port];
3770
3771#ifdef GENESIS
3772 if (pAC->GIni.GIGenesis) {
3773
3774
3775 XM_OUT16(IoC, Port, XM_IMSK, 0xffff);
3776
3777
3778 switch (pPrt->PhyType) {
3779 case SK_PHY_BCOM:
3780
3781 if (pPrt->PState != SK_PRT_RESET) {
3782
3783
3784
3785 SkXmPhyRead(pAC, IoC, Port, PHY_BCOM_AUX_CTRL, &Word);
3786 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_AUX_CTRL,
3787 (SK_U16)(Word | PHY_B_AC_DIS_PM));
3788 SkXmPhyWrite(pAC, IoC, Port, PHY_BCOM_INT_MASK, 0xffff);
3789 }
3790 break;
3791#ifdef OTHER_PHY
3792 case SK_PHY_LONE:
3793 SkXmPhyWrite(pAC, IoC, Port, PHY_LONE_INT_ENAB, 0);
3794 break;
3795 case SK_PHY_NAT:
3796
3797
3798 break;
3799#endif
3800 }
3801 }
3802#endif
3803
3804#ifdef YUKON
3805 if (pAC->GIni.GIYukon) {
3806
3807 SK_OUT8(IoC, GMAC_IRQ_MSK, 0);
3808
3809#ifndef VCPU
3810
3811 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_INT_MASK, 0);
3812#endif
3813 }
3814#endif
3815
3816}
3817
3818
3819#ifdef SK_DIAG
3820
3821
3822
3823
3824
3825
3826
3827
3828
3829void SkXmSendCont(
3830SK_AC *pAC,
3831SK_IOC IoC,
3832int Port,
3833SK_BOOL Enable)
3834{
3835 SK_U32 MdReg;
3836
3837 XM_IN32(IoC, Port, XM_MODE, &MdReg);
3838
3839 if (Enable) {
3840 MdReg |= XM_MD_TX_CONT;
3841 }
3842 else {
3843 MdReg &= ~XM_MD_TX_CONT;
3844 }
3845
3846 XM_OUT32(IoC, Port, XM_MODE, MdReg);
3847
3848}
3849
3850
3851
3852
3853
3854
3855
3856
3857
3858
3859
3860void SkMacTimeStamp(
3861SK_AC *pAC,
3862SK_IOC IoC,
3863int Port,
3864SK_BOOL Enable)
3865{
3866 SK_U32 MdReg;
3867 SK_U8 TimeCtrl;
3868
3869 if (pAC->GIni.GIGenesis) {
3870
3871 XM_IN32(IoC, Port, XM_MODE, &MdReg);
3872
3873 if (Enable) {
3874 MdReg |= XM_MD_ATS;
3875 }
3876 else {
3877 MdReg &= ~XM_MD_ATS;
3878 }
3879
3880 XM_OUT32(IoC, Port, XM_MODE, MdReg);
3881 }
3882 else {
3883 if (Enable) {
3884 TimeCtrl = GMT_ST_START | GMT_ST_CLR_IRQ;
3885 }
3886 else {
3887 TimeCtrl = GMT_ST_STOP | GMT_ST_CLR_IRQ;
3888 }
3889
3890 SK_OUT8(IoC, GMAC_TI_ST_CTRL, TimeCtrl);
3891 }
3892
3893}
3894
3895#else
3896
3897#ifdef GENESIS
3898
3899
3900
3901
3902
3903
3904
3905
3906void SkXmAutoNegLipaXmac(
3907SK_AC *pAC,
3908SK_IOC IoC,
3909int Port,
3910SK_U16 IStatus)
3911{
3912 SK_GEPORT *pPrt;
3913
3914 pPrt = &pAC->GIni.GP[Port];
3915
3916 if (pPrt->PLipaAutoNeg != SK_LIPA_AUTO &&
3917 (IStatus & (XM_IS_LIPA_RC | XM_IS_RX_PAGE | XM_IS_AND)) != 0) {
3918
3919 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3920 ("AutoNegLipa: AutoNeg detected on Port %d, IStatus=0x%04X\n",
3921 Port, IStatus));
3922 pPrt->PLipaAutoNeg = SK_LIPA_AUTO;
3923 }
3924}
3925#endif
3926
3927
3928
3929
3930
3931
3932
3933
3934
3935
3936void SkMacAutoNegLipaPhy(
3937SK_AC *pAC,
3938SK_IOC IoC,
3939int Port,
3940SK_U16 PhyStat)
3941{
3942 SK_GEPORT *pPrt;
3943
3944 pPrt = &pAC->GIni.GP[Port];
3945
3946 if (pPrt->PLipaAutoNeg != SK_LIPA_AUTO &&
3947 (PhyStat & PHY_ST_AN_OVER) != 0) {
3948
3949 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
3950 ("AutoNegLipa: AutoNeg detected on Port %d, PhyStat=0x%04X\n",
3951 Port, PhyStat));
3952 pPrt->PLipaAutoNeg = SK_LIPA_AUTO;
3953 }
3954}
3955
3956
3957#ifdef GENESIS
3958
3959
3960
3961
3962
3963
3964
3965
3966
3967
3968
3969
3970
3971
3972
3973
3974
3975
3976
3977void SkXmIrq(
3978SK_AC *pAC,
3979SK_IOC IoC,
3980int Port)
3981{
3982 SK_GEPORT *pPrt;
3983 SK_EVPARA Para;
3984 SK_U16 IStatus;
3985 SK_U16 IStatus2;
3986#ifdef SK_SLIM
3987 SK_U64 OverflowStatus;
3988#endif
3989
3990 pPrt = &pAC->GIni.GP[Port];
3991
3992 XM_IN16(IoC, Port, XM_ISRC, &IStatus);
3993
3994
3995 if (pPrt->PhyType == SK_PHY_XMAC) {
3996 SkXmAutoNegLipaXmac(pAC, IoC, Port, IStatus);
3997 }
3998 else {
3999
4000 IStatus &= ~(XM_IS_LNK_AE | XM_IS_LIPA_RC |
4001 XM_IS_RX_PAGE | XM_IS_TX_PAGE |
4002 XM_IS_AND | XM_IS_INP_ASS);
4003 }
4004
4005 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_IRQ,
4006 ("XmacIrq Port %d Isr 0x%04X\n", Port, IStatus));
4007
4008 if (!pPrt->PHWLinkUp) {
4009
4010 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_IRQ,
4011 ("SkXmIrq: spurious interrupt on Port %d\n", Port));
4012 return;
4013 }
4014
4015 if ((IStatus & XM_IS_INP_ASS) != 0) {
4016
4017 XM_IN16(IoC, Port, XM_ISRC, &IStatus2);
4018
4019 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_IRQ,
4020 ("SkXmIrq: Link async. Double check Port %d 0x%04X 0x%04X\n",
4021 Port, IStatus, IStatus2));
4022 IStatus &= ~XM_IS_INP_ASS;
4023 IStatus |= IStatus2;
4024 }
4025
4026 if ((IStatus & XM_IS_LNK_AE) != 0) {
4027
4028 }
4029
4030 if ((IStatus & XM_IS_TX_ABORT) != 0) {
4031
4032 }
4033
4034 if ((IStatus & XM_IS_FRC_INT) != 0) {
4035
4036 }
4037
4038 if ((IStatus & (XM_IS_INP_ASS | XM_IS_LIPA_RC | XM_IS_RX_PAGE)) != 0) {
4039 SkHWLinkDown(pAC, IoC, Port);
4040
4041
4042 Para.Para32[0] = (SK_U32)Port;
4043 SkEventQueue(pAC, SKGE_RLMT, SK_RLMT_LINK_DOWN, Para);
4044
4045
4046 SkTimerStart(pAC, IoC, &pPrt->PWaTimer, SK_WA_INA_TIME,
4047 SKGE_HWAC, SK_HWEV_WATIM, Para);
4048 }
4049
4050 if ((IStatus & XM_IS_RX_PAGE) != 0) {
4051
4052 }
4053
4054 if ((IStatus & XM_IS_TX_PAGE) != 0) {
4055
4056 }
4057
4058 if ((IStatus & XM_IS_AND) != 0) {
4059 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_IRQ,
4060 ("SkXmIrq: AND on link that is up Port %d\n", Port));
4061 }
4062
4063 if ((IStatus & XM_IS_TSC_OV) != 0) {
4064
4065 }
4066
4067
4068 if ((IStatus & (XM_IS_RXC_OV | XM_IS_TXC_OV)) != 0) {
4069#ifdef SK_SLIM
4070 SkXmOverflowStatus(pAC, IoC, Port, IStatus, &OverflowStatus);
4071#else
4072 Para.Para32[0] = (SK_U32)Port;
4073 Para.Para32[1] = (SK_U32)IStatus;
4074 SkPnmiEvent(pAC, IoC, SK_PNMI_EVT_SIRQ_OVERFLOW, Para);
4075#endif
4076 }
4077
4078 if ((IStatus & XM_IS_RXF_OV) != 0) {
4079
4080#ifdef DEBUG
4081 pPrt->PRxOverCnt++;
4082#endif
4083 }
4084
4085 if ((IStatus & XM_IS_TXF_UR) != 0) {
4086
4087 SK_ERR_LOG(pAC, SK_ERRCL_HW, SKERR_SIRQ_E020, SKERR_SIRQ_E020MSG);
4088 }
4089
4090 if ((IStatus & XM_IS_TX_COMP) != 0) {
4091
4092 }
4093
4094 if ((IStatus & XM_IS_RX_COMP) != 0) {
4095
4096 }
4097}
4098#endif
4099
4100
4101#ifdef YUKON
4102
4103
4104
4105
4106
4107
4108
4109
4110
4111
4112
4113void SkGmIrq(
4114SK_AC *pAC,
4115SK_IOC IoC,
4116int Port)
4117{
4118 SK_GEPORT *pPrt;
4119 SK_U8 IStatus;
4120#ifdef SK_SLIM
4121 SK_U64 OverflowStatus;
4122#else
4123 SK_EVPARA Para;
4124#endif
4125
4126 pPrt = &pAC->GIni.GP[Port];
4127
4128 SK_IN8(IoC, GMAC_IRQ_SRC, &IStatus);
4129
4130#ifdef XXX
4131
4132 SkMacAutoNegLipaPhy(pAC, IoC, Port, IStatus);
4133#endif
4134
4135 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_IRQ,
4136 ("GmacIrq Port %d Isr 0x%04X\n", Port, IStatus));
4137
4138
4139 if (IStatus & (GM_IS_RX_CO_OV | GM_IS_TX_CO_OV)) {
4140
4141#ifdef SK_SLIM
4142 SkGmOverflowStatus(pAC, IoC, Port, IStatus, &OverflowStatus);
4143#else
4144 Para.Para32[0] = (SK_U32)Port;
4145 Para.Para32[1] = (SK_U32)IStatus;
4146 SkPnmiEvent(pAC, IoC, SK_PNMI_EVT_SIRQ_OVERFLOW, Para);
4147#endif
4148 }
4149
4150 if (IStatus & GM_IS_RX_FF_OR) {
4151
4152 SK_OUT8(IoC, MR_ADDR(Port, RX_GMF_CTRL_T), (SK_U8)GMF_CLI_RX_FO);
4153#ifdef DEBUG
4154 pPrt->PRxOverCnt++;
4155#endif
4156 }
4157
4158 if (IStatus & GM_IS_TX_FF_UR) {
4159
4160 SK_OUT8(IoC, MR_ADDR(Port, TX_GMF_CTRL_T), (SK_U8)GMF_CLI_TX_FU);
4161
4162 SK_ERR_LOG(pAC, SK_ERRCL_HW, SKERR_SIRQ_E020, SKERR_SIRQ_E020MSG);
4163 }
4164
4165 if (IStatus & GM_IS_TX_COMPL) {
4166
4167 }
4168
4169 if (IStatus & GM_IS_RX_COMPL) {
4170
4171 }
4172}
4173#endif
4174
4175
4176
4177
4178
4179
4180
4181
4182
4183
4184
4185void SkMacIrq(
4186SK_AC *pAC,
4187SK_IOC IoC,
4188int Port)
4189{
4190#ifdef GENESIS
4191 if (pAC->GIni.GIGenesis) {
4192
4193 SkXmIrq(pAC, IoC, Port);
4194 }
4195#endif
4196
4197#ifdef YUKON
4198 if (pAC->GIni.GIYukon) {
4199
4200 SkGmIrq(pAC, IoC, Port);
4201 }
4202#endif
4203
4204}
4205
4206#endif
4207
4208#ifdef GENESIS
4209
4210
4211
4212
4213
4214
4215
4216
4217
4218
4219
4220
4221
4222int SkXmUpdateStats(
4223SK_AC *pAC,
4224SK_IOC IoC,
4225unsigned int Port)
4226{
4227 SK_GEPORT *pPrt;
4228 SK_U16 StatReg;
4229 int WaitIndex;
4230
4231 pPrt = &pAC->GIni.GP[Port];
4232 WaitIndex = 0;
4233
4234
4235 XM_OUT16(IoC, Port, XM_STAT_CMD, XM_SC_SNP_TXC | XM_SC_SNP_RXC);
4236
4237
4238
4239
4240
4241
4242
4243 do {
4244
4245 XM_IN16(IoC, Port, XM_STAT_CMD, &StatReg);
4246
4247 if (++WaitIndex > 10) {
4248
4249 SK_ERR_LOG(pAC, SK_ERRCL_HW, SKERR_HWI_E021, SKERR_HWI_E021MSG);
4250
4251 return(1);
4252 }
4253 } while ((StatReg & (XM_SC_SNP_TXC | XM_SC_SNP_RXC)) != 0);
4254
4255 return(0);
4256}
4257
4258
4259
4260
4261
4262
4263
4264
4265
4266
4267
4268
4269
4270
4271
4272int SkXmMacStatistic(
4273SK_AC *pAC,
4274SK_IOC IoC,
4275unsigned int Port,
4276SK_U16 StatAddr,
4277SK_U32 SK_FAR *pVal)
4278{
4279 if ((StatAddr < XM_TXF_OK) || (StatAddr > XM_RXF_MAX_SZ)) {
4280
4281 SK_ERR_LOG(pAC, SK_ERRCL_SW, SKERR_HWI_E022, SKERR_HWI_E022MSG);
4282
4283 return(1);
4284 }
4285
4286 XM_IN32(IoC, Port, StatAddr, pVal);
4287
4288 return(0);
4289}
4290
4291
4292
4293
4294
4295
4296
4297
4298
4299
4300
4301
4302
4303int SkXmResetCounter(
4304SK_AC *pAC,
4305SK_IOC IoC,
4306unsigned int Port)
4307{
4308 XM_OUT16(IoC, Port, XM_STAT_CMD, XM_SC_CLR_RXC | XM_SC_CLR_TXC);
4309
4310 XM_OUT16(IoC, Port, XM_STAT_CMD, XM_SC_CLR_RXC | XM_SC_CLR_TXC);
4311
4312 return(0);
4313}
4314
4315
4316
4317
4318
4319
4320
4321
4322
4323
4324
4325
4326
4327
4328
4329
4330
4331
4332
4333
4334
4335int SkXmOverflowStatus(
4336SK_AC *pAC,
4337SK_IOC IoC,
4338unsigned int Port,
4339SK_U16 IStatus,
4340SK_U64 SK_FAR *pStatus)
4341{
4342 SK_U64 Status;
4343 SK_U32 RegVal;
4344
4345 Status = 0;
4346
4347 if ((IStatus & XM_IS_RXC_OV) != 0) {
4348
4349 XM_IN32(IoC, Port, XM_RX_CNT_EV, &RegVal);
4350 Status |= (SK_U64)RegVal << 32;
4351 }
4352
4353 if ((IStatus & XM_IS_TXC_OV) != 0) {
4354
4355 XM_IN32(IoC, Port, XM_TX_CNT_EV, &RegVal);
4356 Status |= (SK_U64)RegVal;
4357 }
4358
4359 *pStatus = Status;
4360
4361 return(0);
4362}
4363#endif
4364
4365
4366#ifdef YUKON
4367
4368
4369
4370
4371
4372
4373
4374
4375
4376
4377
4378int SkGmUpdateStats(
4379SK_AC *pAC,
4380SK_IOC IoC,
4381unsigned int Port)
4382{
4383 return(0);
4384}
4385
4386
4387
4388
4389
4390
4391
4392
4393
4394
4395
4396
4397
4398
4399
4400int SkGmMacStatistic(
4401SK_AC *pAC,
4402SK_IOC IoC,
4403unsigned int Port,
4404SK_U16 StatAddr,
4405SK_U32 SK_FAR *pVal)
4406{
4407
4408 if ((StatAddr < GM_RXF_UC_OK) || (StatAddr > GM_TXE_FIFO_UR)) {
4409
4410 SK_ERR_LOG(pAC, SK_ERRCL_SW, SKERR_HWI_E022, SKERR_HWI_E022MSG);
4411
4412 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
4413 ("SkGmMacStat: wrong MIB counter 0x%04X\n", StatAddr));
4414 return(1);
4415 }
4416
4417 GM_IN32(IoC, Port, StatAddr, pVal);
4418
4419 return(0);
4420}
4421
4422
4423
4424
4425
4426
4427
4428
4429
4430
4431
4432
4433
4434int SkGmResetCounter(
4435SK_AC *pAC,
4436SK_IOC IoC,
4437unsigned int Port)
4438{
4439 SK_U16 Reg;
4440 SK_U16 Word;
4441 int i;
4442
4443 GM_IN16(IoC, Port, GM_PHY_ADDR, &Reg);
4444
4445
4446 GM_OUT16(IoC, Port, GM_PHY_ADDR, Reg | GM_PAR_MIB_CLR);
4447
4448
4449 for (i = 0; i < GM_MIB_CNT_SIZE; i++) {
4450
4451 GM_IN16(IoC, Port, GM_MIB_CNT_BASE + 8*i, &Word);
4452 }
4453
4454
4455 GM_OUT16(IoC, Port, GM_PHY_ADDR, Reg);
4456
4457 return(0);
4458}
4459
4460
4461
4462
4463
4464
4465
4466
4467
4468
4469
4470
4471
4472
4473
4474
4475
4476
4477
4478
4479
4480int SkGmOverflowStatus(
4481SK_AC *pAC,
4482SK_IOC IoC,
4483unsigned int Port,
4484SK_U16 IStatus,
4485SK_U64 SK_FAR *pStatus)
4486{
4487 SK_U64 Status;
4488 SK_U16 RegVal;
4489
4490 Status = 0;
4491
4492 if ((IStatus & GM_IS_RX_CO_OV) != 0) {
4493
4494 GM_IN16(IoC, Port, GM_RX_IRQ_SRC, &RegVal);
4495 Status |= (SK_U64)RegVal << 32;
4496 }
4497
4498 if ((IStatus & GM_IS_TX_CO_OV) != 0) {
4499
4500 GM_IN16(IoC, Port, GM_TX_IRQ_SRC, &RegVal);
4501 Status |= (SK_U64)RegVal;
4502 }
4503
4504
4505 GM_IN16(IoC, Port, GM_TR_IRQ_SRC, &RegVal);
4506
4507 Status |= (SK_U64)((SK_U8)RegVal) << 48;
4508
4509 Status |= (SK_U64)(RegVal >> 8) << 16;
4510
4511 *pStatus = Status;
4512
4513 return(0);
4514}
4515
4516
4517#ifndef SK_SLIM
4518
4519
4520
4521
4522
4523
4524
4525
4526
4527
4528
4529
4530
4531
4532
4533int SkGmCableDiagStatus(
4534SK_AC *pAC,
4535SK_IOC IoC,
4536int Port,
4537SK_BOOL StartTest)
4538{
4539 int i;
4540 SK_U16 RegVal;
4541 SK_GEPORT *pPrt;
4542
4543 pPrt = &pAC->GIni.GP[Port];
4544
4545 if (pPrt->PhyType != SK_PHY_MARV_COPPER) {
4546
4547 return(1);
4548 }
4549
4550 if (StartTest) {
4551
4552 if ((pPrt->PhyId1 & PHY_I1_REV_MSK) < 4) {
4553
4554 SkGmPhyWrite(pAC, IoC, Port, 29, 0x001e);
4555
4556 SkGmPhyWrite(pAC, IoC, Port, 30, 0xcc00);
4557 SkGmPhyWrite(pAC, IoC, Port, 30, 0xc800);
4558 SkGmPhyWrite(pAC, IoC, Port, 30, 0xc400);
4559 SkGmPhyWrite(pAC, IoC, Port, 30, 0xc000);
4560 SkGmPhyWrite(pAC, IoC, Port, 30, 0xc100);
4561 }
4562
4563
4564 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_EXT_ADR, 0);
4565
4566
4567 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_CABLE_DIAG, &RegVal);
4568
4569
4570 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_CABLE_DIAG,
4571 (SK_U16)(RegVal | PHY_M_CABD_ENA_TEST));
4572
4573 return(0);
4574 }
4575
4576
4577 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_CABLE_DIAG, &RegVal);
4578
4579 SK_DBG_MSG(pAC, SK_DBGMOD_HWM, SK_DBGCAT_CTRL,
4580 ("PHY Cable Diag.=0x%04X\n", RegVal));
4581
4582 if ((RegVal & PHY_M_CABD_ENA_TEST) != 0) {
4583
4584 return(2);
4585 }
4586
4587
4588 for (i = 0; i < 4; i++) {
4589
4590 SkGmPhyWrite(pAC, IoC, Port, PHY_MARV_EXT_ADR, (SK_U16)i);
4591
4592
4593 SkGmPhyRead(pAC, IoC, Port, PHY_MARV_CABLE_DIAG, &RegVal);
4594
4595 pPrt->PMdiPairLen[i] = (SK_U8)(RegVal & PHY_M_CABD_DIST_MSK);
4596
4597 pPrt->PMdiPairSts[i] = (SK_U8)((RegVal & PHY_M_CABD_STAT_MSK) >> 13);
4598 }
4599
4600 return(0);
4601}
4602#endif
4603#endif
4604
4605
4606