1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53#include <common.h>
54#include <malloc.h>
55#include <net.h>
56#include <netdev.h>
57#include <asm/io.h>
58#include <pci.h>
59#include <linux/delay.h>
60
61
62#define EEPROM_SIZE 0xb
63
64#define DSIZE 0x00000FFF
65#define CRC_SIZE 4
66#define TOUT_LOOP 500000
67#define TX_BUF_SIZE 1536
68#define RX_BUF_SIZE 1536
69#define NUM_RX_DESC 4
70
71
72
73
74
75enum register_offsets {
76 ChipCmd = 0x00,
77 ChipConfig = 0x04,
78 EECtrl = 0x08,
79 IntrMask = 0x14,
80 IntrEnable = 0x18,
81 TxRingPtr = 0x20,
82 TxConfig = 0x24,
83 RxRingPtr = 0x30,
84 RxConfig = 0x34,
85 ClkRun = 0x3C,
86 RxFilterAddr = 0x48,
87 RxFilterData = 0x4C,
88 SiliconRev = 0x58,
89 PCIPM = 0x44,
90 BasicControl = 0x80,
91 BasicStatus = 0x84,
92
93 PGSEL = 0xCC,
94 PMDCSR = 0xE4,
95 TSTDAT = 0xFC,
96 DSPCFG = 0xF4,
97 SDCFG = 0x8C
98};
99
100
101enum ChipCmdBits {
102 ChipReset = 0x100,
103 RxReset = 0x20,
104 TxReset = 0x10,
105 RxOff = 0x08,
106 RxOn = 0x04,
107 TxOff = 0x02,
108 TxOn = 0x01
109};
110
111enum ChipConfigBits {
112 LinkSts = 0x80000000,
113 HundSpeed = 0x40000000,
114 FullDuplex = 0x20000000,
115 TenPolarity = 0x10000000,
116 AnegDone = 0x08000000,
117 AnegEnBothBoth = 0x0000E000,
118 AnegDis100Full = 0x0000C000,
119 AnegEn100Both = 0x0000A000,
120 AnegDis100Half = 0x00008000,
121 AnegEnBothHalf = 0x00006000,
122 AnegDis10Full = 0x00004000,
123 AnegEn10Both = 0x00002000,
124 DuplexMask = 0x00008000,
125 SpeedMask = 0x00004000,
126 AnegMask = 0x00002000,
127 AnegDis10Half = 0x00000000,
128 ExtPhy = 0x00001000,
129 PhyRst = 0x00000400,
130 PhyDis = 0x00000200,
131 BootRomDisable = 0x00000004,
132 BEMode = 0x00000001,
133};
134
135enum TxConfig_bits {
136 TxDrthMask = 0x3f,
137 TxFlthMask = 0x3f00,
138 TxMxdmaMask = 0x700000,
139 TxMxdma_512 = 0x0,
140 TxMxdma_4 = 0x100000,
141 TxMxdma_8 = 0x200000,
142 TxMxdma_16 = 0x300000,
143 TxMxdma_32 = 0x400000,
144 TxMxdma_64 = 0x500000,
145 TxMxdma_128 = 0x600000,
146 TxMxdma_256 = 0x700000,
147 TxCollRetry = 0x800000,
148 TxAutoPad = 0x10000000,
149 TxMacLoop = 0x20000000,
150 TxHeartIgn = 0x40000000,
151 TxCarrierIgn = 0x80000000
152};
153
154enum RxConfig_bits {
155 RxDrthMask = 0x3e,
156 RxMxdmaMask = 0x700000,
157 RxMxdma_512 = 0x0,
158 RxMxdma_4 = 0x100000,
159 RxMxdma_8 = 0x200000,
160 RxMxdma_16 = 0x300000,
161 RxMxdma_32 = 0x400000,
162 RxMxdma_64 = 0x500000,
163 RxMxdma_128 = 0x600000,
164 RxMxdma_256 = 0x700000,
165 RxAcceptLong = 0x8000000,
166 RxAcceptTx = 0x10000000,
167 RxAcceptRunt = 0x40000000,
168 RxAcceptErr = 0x80000000
169};
170
171
172enum rx_mode_bits {
173 AcceptErr = 0x20,
174 AcceptRunt = 0x10,
175 AcceptBroadcast = 0xC0000000,
176 AcceptMulticast = 0x00200000,
177 AcceptAllMulticast = 0x20000000,
178 AcceptAllPhys = 0x10000000,
179 AcceptMyPhys = 0x08000000
180};
181
182typedef struct _BufferDesc {
183 u32 link;
184 vu_long cmdsts;
185 u32 bufptr;
186 u32 software_use;
187} BufferDesc;
188
189
190enum desc_status_bits {
191 DescOwn = 0x80000000, DescMore = 0x40000000, DescIntr = 0x20000000,
192 DescNoCRC = 0x10000000, DescPktOK = 0x08000000,
193 DescSizeMask = 0xfff,
194
195 DescTxAbort = 0x04000000, DescTxFIFO = 0x02000000,
196 DescTxCarrier = 0x01000000, DescTxDefer = 0x00800000,
197 DescTxExcDefer = 0x00400000, DescTxOOWCol = 0x00200000,
198 DescTxExcColl = 0x00100000, DescTxCollCount = 0x000f0000,
199
200 DescRxAbort = 0x04000000, DescRxOver = 0x02000000,
201 DescRxDest = 0x01800000, DescRxLong = 0x00400000,
202 DescRxRunt = 0x00200000, DescRxInvalid = 0x00100000,
203 DescRxCRC = 0x00080000, DescRxAlign = 0x00040000,
204 DescRxLoop = 0x00020000, DesRxColl = 0x00010000,
205};
206
207
208#ifdef NATSEMI_DEBUG
209static int natsemi_debug = 0;
210#endif
211static u32 SavedClkRun;
212static unsigned int cur_rx;
213static unsigned int advertising;
214static unsigned int rx_config;
215static unsigned int tx_config;
216
217
218
219static BufferDesc txd __attribute__ ((aligned(4)));
220static BufferDesc rxd[NUM_RX_DESC] __attribute__ ((aligned(4)));
221
222static unsigned char txb[TX_BUF_SIZE] __attribute__ ((aligned(4)));
223static unsigned char rxb[NUM_RX_DESC * RX_BUF_SIZE]
224 __attribute__ ((aligned(4)));
225
226
227#if 0
228static void write_eeprom(struct eth_device *dev, long addr, int location,
229 short value);
230#endif
231static int read_eeprom(struct eth_device *dev, long addr, int location);
232static int mdio_read(struct eth_device *dev, int phy_id, int location);
233static int natsemi_init(struct eth_device *dev, struct bd_info * bis);
234static void natsemi_reset(struct eth_device *dev);
235static void natsemi_init_rxfilter(struct eth_device *dev);
236static void natsemi_init_txd(struct eth_device *dev);
237static void natsemi_init_rxd(struct eth_device *dev);
238static void natsemi_set_rx_mode(struct eth_device *dev);
239static void natsemi_check_duplex(struct eth_device *dev);
240static int natsemi_send(struct eth_device *dev, void *packet, int length);
241static int natsemi_poll(struct eth_device *dev);
242static void natsemi_disable(struct eth_device *dev);
243
244static struct pci_device_id supported[] = {
245 {PCI_VENDOR_ID_NS, PCI_DEVICE_ID_NS_83815},
246 {}
247};
248
249#define bus_to_phys(a) pci_mem_to_phys((pci_dev_t)dev->priv, a)
250#define phys_to_bus(a) pci_phys_to_mem((pci_dev_t)dev->priv, a)
251
252static inline int
253INW(struct eth_device *dev, u_long addr)
254{
255 return le16_to_cpu(*(vu_short *) (addr + dev->iobase));
256}
257
258static int
259INL(struct eth_device *dev, u_long addr)
260{
261 return le32_to_cpu(*(vu_long *) (addr + dev->iobase));
262}
263
264static inline void
265OUTW(struct eth_device *dev, int command, u_long addr)
266{
267 *(vu_short *) ((addr + dev->iobase)) = cpu_to_le16(command);
268}
269
270static inline void
271OUTL(struct eth_device *dev, int command, u_long addr)
272{
273 *(vu_long *) ((addr + dev->iobase)) = cpu_to_le32(command);
274}
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289int
290natsemi_initialize(struct bd_info * bis)
291{
292 pci_dev_t devno;
293 int card_number = 0;
294 struct eth_device *dev;
295 u32 iobase, status, chip_config;
296 int i, idx = 0;
297 int prev_eedata;
298 u32 tmp;
299
300 while (1) {
301
302 if ((devno = pci_find_devices(supported, idx++)) < 0) {
303 break;
304 }
305
306 pci_read_config_dword(devno, PCI_BASE_ADDRESS_0, &iobase);
307 iobase &= ~0x3;
308
309 pci_write_config_dword(devno, PCI_COMMAND,
310 PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER);
311
312
313 pci_read_config_dword(devno, PCI_COMMAND, &status);
314 if (!(status & PCI_COMMAND_MEMORY)) {
315 printf("Error: Can not enable MEM access.\n");
316 continue;
317 } else if (!(status & PCI_COMMAND_MASTER)) {
318 printf("Error: Can not enable Bus Mastering.\n");
319 continue;
320 }
321
322 dev = (struct eth_device *) malloc(sizeof *dev);
323 if (!dev) {
324 printf("natsemi: Can not allocate memory\n");
325 break;
326 }
327 memset(dev, 0, sizeof(*dev));
328
329 sprintf(dev->name, "dp83815#%d", card_number);
330 dev->iobase = bus_to_phys(iobase);
331#ifdef NATSEMI_DEBUG
332 printf("natsemi: NatSemi ns8381[56] @ %#x\n", dev->iobase);
333#endif
334 dev->priv = (void *) devno;
335 dev->init = natsemi_init;
336 dev->halt = natsemi_disable;
337 dev->send = natsemi_send;
338 dev->recv = natsemi_poll;
339
340 eth_register(dev);
341
342 card_number++;
343
344
345 pci_write_config_byte(devno, PCI_LATENCY_TIMER, 0x20);
346
347 udelay(10 * 1000);
348
349
350
351
352 pci_read_config_dword(devno, PCIPM, &tmp);
353 if (tmp & (0x03 | 0x100)) {
354
355 u32 newtmp = tmp & ~(0x03 | 0x100);
356 pci_write_config_dword(devno, PCIPM, newtmp);
357 }
358
359 printf("natsemi: EEPROM contents:\n");
360 for (i = 0; i <= EEPROM_SIZE; i++) {
361 short eedata = read_eeprom(dev, EECtrl, i);
362 printf(" %04hx", eedata);
363 }
364 printf("\n");
365
366
367 prev_eedata = read_eeprom(dev, EECtrl, 6);
368 for (i = 0; i < 3; i++) {
369 int eedata = read_eeprom(dev, EECtrl, i + 7);
370 dev->enetaddr[i*2] = (eedata << 1) + (prev_eedata >> 15);
371 dev->enetaddr[i*2+1] = eedata >> 7;
372 prev_eedata = eedata;
373 }
374
375
376 OUTL(dev, ChipReset, ChipCmd);
377
378 advertising = mdio_read(dev, 1, 4);
379 chip_config = INL(dev, ChipConfig);
380#ifdef NATSEMI_DEBUG
381 printf("%s: Transceiver status %#08X advertising %#08X\n",
382 dev->name, (int) INL(dev, BasicStatus), advertising);
383 printf("%s: Transceiver default autoneg. %s 10%s %s duplex.\n",
384 dev->name, chip_config & AnegMask ? "enabled, advertise" :
385 "disabled, force", chip_config & SpeedMask ? "0" : "",
386 chip_config & DuplexMask ? "full" : "half");
387#endif
388 chip_config |= AnegEnBothBoth;
389#ifdef NATSEMI_DEBUG
390 printf("%s: changed to autoneg. %s 10%s %s duplex.\n",
391 dev->name, chip_config & AnegMask ? "enabled, advertise" :
392 "disabled, force", chip_config & SpeedMask ? "0" : "",
393 chip_config & DuplexMask ? "full" : "half");
394#endif
395
396 OUTL(dev, (chip_config | PhyRst), ChipConfig);
397
398 OUTL(dev, chip_config, ChipConfig);
399
400
401
402
403
404
405
406 SavedClkRun = INL(dev, ClkRun);
407 OUTL(dev, SavedClkRun & ~0x100, ClkRun);
408 }
409 return card_number;
410}
411
412
413
414
415
416
417
418#define eeprom_delay(ee_addr) INL(dev, ee_addr)
419
420enum EEPROM_Ctrl_Bits {
421 EE_ShiftClk = 0x04,
422 EE_DataIn = 0x01,
423 EE_ChipSelect = 0x08,
424 EE_DataOut = 0x02
425};
426
427#define EE_Write0 (EE_ChipSelect)
428#define EE_Write1 (EE_ChipSelect | EE_DataIn)
429
430enum EEPROM_Cmds {
431 EE_WrEnCmd = (4 << 6), EE_WriteCmd = (5 << 6),
432 EE_ReadCmd = (6 << 6), EE_EraseCmd = (7 << 6),
433};
434
435#if 0
436static void
437write_eeprom(struct eth_device *dev, long addr, int location, short value)
438{
439 int i;
440 int ee_addr = (typeof(ee_addr))addr;
441 short wren_cmd = EE_WrEnCmd | 0x30;
442 short write_cmd = location | EE_WriteCmd;
443
444#ifdef NATSEMI_DEBUG
445 printf("write_eeprom: %08x, %04hx, %04hx\n",
446 dev->iobase + ee_addr, write_cmd, value);
447#endif
448
449 for (i = 9; i >= 0; i--) {
450 short cmdval = (wren_cmd & (1 << i)) ? EE_Write1 : EE_Write0;
451 OUTL(dev, cmdval, ee_addr);
452 eeprom_delay(ee_addr);
453 OUTL(dev, cmdval | EE_ShiftClk, ee_addr);
454 eeprom_delay(ee_addr);
455 }
456
457 OUTL(dev, 0, ee_addr);
458 OUTL(dev, EE_ShiftClk, ee_addr);
459 eeprom_delay(ee_addr);
460
461
462 for (i = 9; i >= 0; i--) {
463 short cmdval = (write_cmd & (1 << i)) ? EE_Write1 : EE_Write0;
464 OUTL(dev, cmdval, ee_addr);
465 eeprom_delay(ee_addr);
466 OUTL(dev, cmdval | EE_ShiftClk, ee_addr);
467 eeprom_delay(ee_addr);
468 }
469
470 for (i = 0; i < 16; i++) {
471 short cmdval = (value & (1 << i)) ? EE_Write1 : EE_Write0;
472 OUTL(dev, cmdval, ee_addr);
473 eeprom_delay(ee_addr);
474 OUTL(dev, cmdval | EE_ShiftClk, ee_addr);
475 eeprom_delay(ee_addr);
476 }
477
478 OUTL(dev, 0, ee_addr);
479 OUTL(dev, EE_ShiftClk, ee_addr);
480 for (i = 0; i < 200000; i++) {
481 OUTL(dev, EE_Write0, ee_addr);
482 if (INL(dev, ee_addr) & EE_DataOut) {
483 break;
484 }
485 }
486 eeprom_delay(ee_addr);
487
488
489 OUTL(dev, EE_Write0, ee_addr);
490 OUTL(dev, 0, ee_addr);
491 return;
492}
493#endif
494
495static int
496read_eeprom(struct eth_device *dev, long addr, int location)
497{
498 int i;
499 int retval = 0;
500 int ee_addr = (typeof(ee_addr))addr;
501 int read_cmd = location | EE_ReadCmd;
502
503 OUTL(dev, EE_Write0, ee_addr);
504
505
506 for (i = 10; i >= 0; i--) {
507 short dataval = (read_cmd & (1 << i)) ? EE_Write1 : EE_Write0;
508 OUTL(dev, dataval, ee_addr);
509 eeprom_delay(ee_addr);
510 OUTL(dev, dataval | EE_ShiftClk, ee_addr);
511 eeprom_delay(ee_addr);
512 }
513 OUTL(dev, EE_ChipSelect, ee_addr);
514 eeprom_delay(ee_addr);
515
516 for (i = 0; i < 16; i++) {
517 OUTL(dev, EE_ChipSelect | EE_ShiftClk, ee_addr);
518 eeprom_delay(ee_addr);
519 retval |= (INL(dev, ee_addr) & EE_DataOut) ? 1 << i : 0;
520 OUTL(dev, EE_ChipSelect, ee_addr);
521 eeprom_delay(ee_addr);
522 }
523
524
525 OUTL(dev, EE_Write0, ee_addr);
526 OUTL(dev, 0, ee_addr);
527#ifdef NATSEMI_DEBUG
528 if (natsemi_debug)
529 printf("read_eeprom: %08x, %08x, retval %08x\n",
530 dev->iobase + ee_addr, read_cmd, retval);
531#endif
532 return retval;
533}
534
535
536
537
538
539static int
540mdio_read(struct eth_device *dev, int phy_id, int location)
541{
542 if (phy_id == 1 && location < 32)
543 return INL(dev, BasicControl+(location<<2))&0xffff;
544 else
545 return 0xffff;
546}
547
548
549
550
551
552
553
554
555
556
557
558static int
559natsemi_init(struct eth_device *dev, struct bd_info * bis)
560{
561
562 natsemi_reset(dev);
563
564
565
566
567
568
569
570 OUTL(dev, SavedClkRun & ~0x100, ClkRun);
571
572 natsemi_init_rxfilter(dev);
573 natsemi_init_txd(dev);
574 natsemi_init_rxd(dev);
575
576
577 tx_config = TxAutoPad | TxCollRetry | TxMxdma_256 | (0x1002);
578 rx_config = RxMxdma_256 | 0x20;
579
580#ifdef NATSEMI_DEBUG
581 printf("%s: Setting TxConfig Register %#08X\n", dev->name, tx_config);
582 printf("%s: Setting RxConfig Register %#08X\n", dev->name, rx_config);
583#endif
584 OUTL(dev, tx_config, TxConfig);
585 OUTL(dev, rx_config, RxConfig);
586
587 natsemi_check_duplex(dev);
588 natsemi_set_rx_mode(dev);
589
590 OUTL(dev, (RxOn | TxOn), ChipCmd);
591 return 1;
592}
593
594
595
596
597
598
599
600
601
602
603static void
604natsemi_reset(struct eth_device *dev)
605{
606 OUTL(dev, ChipReset, ChipCmd);
607
608
609
610
611
612 if (INL(dev, SiliconRev) == 0x302) {
613 OUTW(dev, 0x0001, PGSEL);
614 OUTW(dev, 0x189C, PMDCSR);
615 OUTW(dev, 0x0000, TSTDAT);
616 OUTW(dev, 0x5040, DSPCFG);
617 OUTW(dev, 0x008C, SDCFG);
618 }
619
620 OUTL(dev, 0, IntrMask);
621 OUTL(dev, 0, IntrEnable);
622}
623
624
625
626
627
628
629
630
631
632
633static void
634natsemi_init_rxfilter(struct eth_device *dev)
635{
636 int i;
637
638 for (i = 0; i < ETH_ALEN; i += 2) {
639 OUTL(dev, i, RxFilterAddr);
640 OUTW(dev, dev->enetaddr[i] + (dev->enetaddr[i + 1] << 8),
641 RxFilterData);
642 }
643}
644
645
646
647
648
649
650
651
652
653
654
655static void
656natsemi_init_txd(struct eth_device *dev)
657{
658 txd.link = (u32) 0;
659 txd.cmdsts = (u32) 0;
660 txd.bufptr = (u32) & txb[0];
661
662
663 OUTL(dev, (u32) & txd, TxRingPtr);
664#ifdef NATSEMI_DEBUG
665 printf("natsemi_init_txd: TX descriptor reg loaded with: %#08X\n",
666 INL(dev, TxRingPtr));
667#endif
668}
669
670
671
672
673
674
675
676
677
678
679static void
680natsemi_init_rxd(struct eth_device *dev)
681{
682 int i;
683
684 cur_rx = 0;
685
686
687 for (i = 0; i < NUM_RX_DESC; i++) {
688 rxd[i].link =
689 cpu_to_le32((i + 1 <
690 NUM_RX_DESC) ? (u32) & rxd[i +
691 1] : (u32) &
692 rxd[0]);
693 rxd[i].cmdsts = cpu_to_le32((u32) RX_BUF_SIZE);
694 rxd[i].bufptr = cpu_to_le32((u32) & rxb[i * RX_BUF_SIZE]);
695#ifdef NATSEMI_DEBUG
696 printf
697 ("natsemi_init_rxd: rxd[%d]=%p link=%X cmdsts=%lX bufptr=%X\n",
698 i, &rxd[i], le32_to_cpu(rxd[i].link),
699 rxd[i].cmdsts, rxd[i].bufptr);
700#endif
701 }
702
703
704 OUTL(dev, (u32) & rxd[0], RxRingPtr);
705
706#ifdef NATSEMI_DEBUG
707 printf("natsemi_init_rxd: RX descriptor register loaded with: %X\n",
708 INL(dev, RxRingPtr));
709#endif
710}
711
712
713
714
715
716
717
718
719
720
721
722
723static void
724natsemi_set_rx_mode(struct eth_device *dev)
725{
726 u32 rx_mode = AcceptBroadcast | AcceptMyPhys;
727
728 OUTL(dev, rx_mode, RxFilterAddr);
729}
730
731static void
732natsemi_check_duplex(struct eth_device *dev)
733{
734 int duplex = INL(dev, ChipConfig) & FullDuplex ? 1 : 0;
735
736#ifdef NATSEMI_DEBUG
737 printf("%s: Setting %s-duplex based on negotiated link"
738 " capability.\n", dev->name, duplex ? "full" : "half");
739#endif
740 if (duplex) {
741 rx_config |= RxAcceptTx;
742 tx_config |= (TxCarrierIgn | TxHeartIgn);
743 } else {
744 rx_config &= ~RxAcceptTx;
745 tx_config &= ~(TxCarrierIgn | TxHeartIgn);
746 }
747 OUTL(dev, tx_config, TxConfig);
748 OUTL(dev, rx_config, RxConfig);
749}
750
751
752
753
754
755
756static int natsemi_send(struct eth_device *dev, void *packet, int length)
757{
758 u32 i, status = 0;
759 u32 tx_status = 0;
760 u32 *tx_ptr = &tx_status;
761 vu_long *res = (vu_long *)tx_ptr;
762
763
764 OUTL(dev, TxOff, ChipCmd);
765
766#ifdef NATSEMI_DEBUG
767 if (natsemi_debug)
768 printf("natsemi_send: sending %d bytes\n", (int) length);
769#endif
770
771
772 txd.link = cpu_to_le32(0);
773 txd.bufptr = cpu_to_le32(phys_to_bus((u32) packet));
774 txd.cmdsts = cpu_to_le32(DescOwn | length);
775
776
777 OUTL(dev, phys_to_bus((u32) & txd), TxRingPtr);
778#ifdef NATSEMI_DEBUG
779 if (natsemi_debug)
780 printf("natsemi_send: TX descriptor register loaded with: %#08X\n",
781 INL(dev, TxRingPtr));
782#endif
783
784 OUTL(dev, TxOn, ChipCmd);
785
786 for (i = 0;
787 (*res = le32_to_cpu(txd.cmdsts)) & DescOwn;
788 i++) {
789 if (i >= TOUT_LOOP) {
790 printf
791 ("%s: tx error buffer not ready: txd.cmdsts == %#X\n",
792 dev->name, tx_status);
793 goto Done;
794 }
795 }
796
797 if (!(tx_status & DescPktOK)) {
798 printf("natsemi_send: Transmit error, Tx status %X.\n",
799 tx_status);
800 goto Done;
801 }
802
803 status = 1;
804 Done:
805 return status;
806}
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822static int
823natsemi_poll(struct eth_device *dev)
824{
825 int retstat = 0;
826 int length = 0;
827 u32 rx_status = le32_to_cpu(rxd[cur_rx].cmdsts);
828
829 if (!(rx_status & (u32) DescOwn))
830 return retstat;
831#ifdef NATSEMI_DEBUG
832 if (natsemi_debug)
833 printf("natsemi_poll: got a packet: cur_rx:%d, status:%X\n",
834 cur_rx, rx_status);
835#endif
836 length = (rx_status & DSIZE) - CRC_SIZE;
837
838 if ((rx_status & (DescMore | DescPktOK | DescRxLong)) != DescPktOK) {
839 printf
840 ("natsemi_poll: Corrupted packet received, buffer status = %X\n",
841 rx_status);
842 retstat = 0;
843 } else {
844 net_process_received_packet((rxb + cur_rx * RX_BUF_SIZE),
845 length);
846 retstat = 1;
847 }
848
849
850 rxd[cur_rx].cmdsts = cpu_to_le32(RX_BUF_SIZE);
851 rxd[cur_rx].bufptr = cpu_to_le32((u32) & rxb[cur_rx * RX_BUF_SIZE]);
852
853 if (++cur_rx == NUM_RX_DESC)
854 cur_rx = 0;
855
856
857 OUTL(dev, RxOn, ChipCmd);
858
859 return retstat;
860}
861
862
863
864
865
866
867
868
869
870
871static void
872natsemi_disable(struct eth_device *dev)
873{
874
875 OUTL(dev, 0, IntrMask);
876 OUTL(dev, 0, IntrEnable);
877
878
879 OUTL(dev, RxOff | TxOff, ChipCmd);
880
881
882 OUTL(dev, SavedClkRun, ClkRun);
883}
884