00001 #define INLINE
00002 #define CONST const
00003 #define NETBUF char
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093 #include "contiki.h"
00094
00095 #include <string.h>
00096
00097 #include <avr/io.h>
00098
00099
00100
00101
00102 #ifndef LANC111_BASE_ADDR
00103 #define LANC111_BASE_ADDR 0xC000
00104 #endif
00105
00106 #ifndef LANC111_SIGNAL_IRQ
00107 #define LANC111_SIGNAL_IRQ INT5
00108 #endif
00109
00110 #ifdef LANC111_RESET_BIT
00111
00112 #if (LANC111_RESET_AVRPORT == AVRPORTB)
00113 #define LANC111_RESET_PORT PORTB
00114 #define LANC111_RESET_DDR DDRB
00115
00116 #elif (LANC111_RESET_AVRPORT == AVRPORTD)
00117 #define LANC111_RESET_PORT PORTD
00118 #define LANC111_RESET_DDR DDRD
00119
00120 #elif (LANC111_RESET_AVRPORT == AVRPORTE)
00121 #define LANC111_RESET_PORT PORTE
00122 #define LANC111_RESET_DDR DDRE
00123
00124 #elif (LANC111_RESET_AVRPORT == AVRPORTF)
00125 #define LANC111_RESET_PORT PORTF
00126 #define LANC111_RESET_DDR DDRF
00127
00128 #endif
00129
00130 #endif
00131
00132
00133
00134
00135 #if (LANC111_SIGNAL_IRQ == INT0)
00136 #define LANC111_SIGNAL sig_INTERRUPT0
00137 #define LANC111_SIGNAL_MODE() sbi(EICRA, ISC00); sbi(EICRA, ISC01)
00138
00139 #elif (LANC111_SIGNAL_IRQ == INT1)
00140 #define LANC111_SIGNAL sig_INTERRUPT1
00141 #define LANC111_SIGNAL_MODE() sbi(EICRA, ISC10); sbi(EICRA, ISC11)
00142
00143 #elif (LANC111_SIGNAL_IRQ == INT2)
00144 #define LANC111_SIGNAL sig_INTERRUPT2
00145 #define LANC111_SIGNAL_MODE() sbi(EICRA, ISC20); sbi(EICRA, ISC21)
00146
00147 #elif (LANC111_SIGNAL_IRQ == INT3)
00148 #define LANC111_SIGNAL sig_INTERRUPT3
00149 #define LANC111_SIGNAL_MODE() sbi(EICRA, ISC30); sbi(EICRA, ISC31)
00150
00151 #elif (LANC111_SIGNAL_IRQ == INT4)
00152 #define LANC111_SIGNAL sig_INTERRUPT4
00153 #define LANC111_SIGNAL_MODE() sbi(EICRB, ISC40); sbi(EICRB, ISC41)
00154
00155 #elif (LANC111_SIGNAL_IRQ == INT6)
00156 #define LANC111_SIGNAL sig_INTERRUPT6
00157 #define LANC111_SIGNAL_MODE() sbi(EICRB, ISC60); sbi(EICRB, ISC61)
00158
00159 #elif (LANC111_SIGNAL_IRQ == INT7)
00160 #define LANC111_SIGNAL sig_INTERRUPT7
00161 #define LANC111_SIGNAL_MODE() sbi(EICRB, ISC70); sbi(EICRB, ISC71)
00162
00163 #else
00164 #define LANC111_SIGNAL sig_INTERRUPT5
00165 #define LANC111_SIGNAL_MODE() sbi(EICRB, ISC50); sbi(EICRB, ISC51)
00166
00167 #endif
00168
00169
00170
00171
00172
00173
00174
00175
00176
00177 #define NIC_BSR (LANC111_BASE_ADDR + 0x0E)
00178
00179
00180
00181
00182 #define NIC_TCR (LANC111_BASE_ADDR + 0x00)
00183
00184 #define TCR_SWFDUP 0x8000
00185 #define TCR_EPH_LOOP 0x2000
00186 #define TCR_STP_SQET 0x1000
00187 #define TCR_FDUPLX 0x0800
00188 #define TCR_MON_CSN 0x0400
00189 #define TCR_NOCRC 0x0100
00190 #define TCR_PAD_EN 0x0080
00191 #define TCR_FORCOL 0x0004
00192 #define TCR_LOOP 0x0002
00193 #define TCR_TXENA 0x0001
00194
00195
00196
00197
00198
00199 #define NIC_EPHSR (LANC111_BASE_ADDR + 0x02)
00200
00201
00202
00203
00204 #define NIC_RCR (LANC111_BASE_ADDR + 0x04)
00205
00206 #define RCR_SOFT_RST 0x8000
00207 #define RCR_FILT_CAR 0x4000
00208 #define RCR_ABORT_ENB 0x2000
00209 #define RCR_STRIP_CRC 0x0200
00210 #define RCR_RXEN 0x0100
00211 #define RCR_ALMUL 0x0004
00212 #define RCR_PRMS 0x0002
00213 #define RCR_RX_ABORT 0x0001
00214
00215
00216
00217
00218 #define NIC_ECR (LANC111_BASE_ADDR + 0x06)
00219
00220
00221
00222
00223 #define NIC_MIR (LANC111_BASE_ADDR + 0x08)
00224
00225
00226
00227
00228 #define NIC_RPCR (LANC111_BASE_ADDR + 0x0A)
00229
00230 #define RPCR_SPEED 0x2000
00231 #define RPCR_DPLX 0x1000
00232 #define RPCR_ANEG 0x0800
00233 #define RPCR_LEDA_PAT 0x0000
00234 #define RPCR_LEDB_PAT 0x0010
00235
00236
00237
00238
00239 #define NIC_CR (LANC111_BASE_ADDR + 0x00)
00240
00241 #define CR_EPH_EN 0x8000
00242
00243
00244
00245
00246 #define NIC_BAR (LANC111_BASE_ADDR + 0x02)
00247
00248
00249
00250
00251 #define NIC_IAR (LANC111_BASE_ADDR + 0x04)
00252
00253
00254
00255
00256 #define NIC_GPR (LANC111_BASE_ADDR + 0x0A)
00257
00258
00259
00260
00261 #define NIC_CTR (LANC111_BASE_ADDR + 0x0C)
00262
00263 #define CTR_RCV_BAD 0x4000
00264 #define CTR_AUTO_RELEASE 0x0800
00265
00266
00267
00268
00269 #define NIC_MMUCR (LANC111_BASE_ADDR + 0x00)
00270
00271 #define MMUCR_BUSY 0x0001
00272
00273 #define MMU_NOP 0
00274 #define MMU_ALO (1<<5)
00275 #define MMU_RST (2<<5)
00276 #define MMU_REM (3<<5)
00277 #define MMU_TOP (4<<5)
00278 #define MMU_PKT (5<<5)
00279 #define MMU_ENQ (6<<5)
00280 #define MMU_RTX (7<<5)
00281
00282
00283
00284
00285
00286
00287 #define NIC_PNR (LANC111_BASE_ADDR + 0x02)
00288
00289
00290
00291
00292
00293
00294 #define NIC_ARR (LANC111_BASE_ADDR + 0x03)
00295
00296 #define ARR_FAILED 0x80
00297
00298
00299
00300
00301 #define NIC_FIFO (LANC111_BASE_ADDR + 0x04)
00302
00303
00304
00305
00306 #define NIC_PTR (LANC111_BASE_ADDR + 0x06)
00307
00308 #define PTR_RCV 0x8000
00309 #define PTR_AUTO_INCR 0x4000
00310 #define PTR_READ 0x2000
00311 #define PTR_ETEN 0x1000
00312 #define PTR_NOT_EMPTY 0x0800
00313
00314
00315
00316
00317 #define NIC_DATA (LANC111_BASE_ADDR + 0x08)
00318
00319
00320
00321
00322 #define NIC_IST (LANC111_BASE_ADDR + 0x0C)
00323
00324
00325
00326
00327 #define NIC_ACK (LANC111_BASE_ADDR + 0x0C)
00328
00329
00330
00331
00332 #define NIC_MSK (LANC111_BASE_ADDR + 0x0D)
00333
00334 #define INT_MD 0x80
00335 #define INT_ERCV 0x40
00336 #define INT_EPH 0x20
00337 #define INT_RX_OVRN 0x10
00338 #define INT_ALLOC 0x08
00339 #define INT_TX_EMPTY 0x04
00340 #define INT_TX 0x02
00341 #define INT_RCV 0x01
00342
00343
00344
00345
00346 #define NIC_MT (LANC111_BASE_ADDR + 0x00)
00347
00348
00349
00350
00351 #define NIC_MGMT (LANC111_BASE_ADDR + 0x08)
00352
00353 #define MGMT_MDOE 0x08
00354 #define MGMT_MCLK 0x04
00355 #define MGMT_MDI 0x02
00356 #define MGMT_MDO 0x01
00357
00358
00359
00360
00361 #define NIC_REV (LANC111_BASE_ADDR + 0x0A)
00362
00363
00364
00365
00366 #define NIC_ERCV (LANC111_BASE_ADDR + 0x0C)
00367
00368
00369
00370
00371 #define NIC_PHYCR 0
00372
00373 #define PHYCR_RST 0x8000
00374 #define PHYCR_LPBK 0x4000
00375 #define PHYCR_SPEED 0x2000
00376 #define PHYCR_ANEG_EN 0x1000
00377 #define PHYCR_PDN 0x0800
00378 #define PHYCR_MII_DIS 0x0400
00379 #define PHYCR_ANEG_RST 0x0200
00380 #define PHYCR_DPLX 0x0100
00381 #define PHYCR_COLST 0x0080
00382
00383
00384
00385
00386
00387 #define NIC_PHYSR 1
00388
00389 #define PHYSR_CAP_T4 0x8000
00390 #define PHYSR_CAP_TXF 0x4000
00391 #define PHYSR_CAP_TXH 0x2000
00392 #define PHYSR_CAP_TF 0x1000
00393 #define PHYSR_CAP_TH 0x0800
00394 #define PHYSR_CAP_SUPR 0x0040
00395 #define PHYSR_ANEG_ACK 0x0020
00396 #define PHYSR_REM_FLT 0x0010
00397 #define PHYSR_CAP_ANEG 0x0008
00398 #define PHYSR_LINK 0x0004
00399 #define PHYSR_JAB 0x0002
00400 #define PHYSR_EXREG 0x0001
00401
00402
00403
00404
00405
00406 #define NIC_PHYID1 2
00407
00408
00409
00410
00411 #define NIC_PHYID2 3
00412
00413
00414
00415
00416 #define NIC_PHYANAD 4
00417
00418 #define PHYANAD_NP 0x8000
00419 #define PHYANAD_ACK 0x4000
00420 #define PHYANAD_RF 0x2000
00421 #define PHYANAD_T4 0x0200
00422 #define PHYANAD_TX_FDX 0x0100
00423 #define PHYANAD_TX_HDX 0x0080
00424 #define PHYANAD_10FDX 0x0040
00425 #define PHYANAD_10_HDX 0x0020
00426 #define PHYANAD_CSMA 0x0001
00427
00428
00429
00430
00431 #define NIC_PHYANRC 5
00432
00433
00434
00435
00436 #define NIC_PHYCFR1 16
00437
00438
00439
00440
00441 #define NIC_PHYCFR2 17
00442
00443
00444
00445
00446 #define NIC_PHYSOR 18
00447
00448 #define PHYSOR_INT 0x8000
00449 #define PHYSOR_LNKFAIL 0x4000
00450 #define PHYSOR_LOSSSYNC 0x2000
00451 #define PHYSOR_CWRD 0x1000
00452 #define PHYSOR_SSD 0x0800
00453 #define PHYSOR_ESD 0x0400
00454 #define PHYSOR_RPOL 0x0200
00455 #define PHYSOR_JAB 0x0100
00456 #define PHYSOR_SPDDET 0x0080
00457 #define PHYSOR_DPLXDET 0x0040
00458
00459
00460
00461
00462 #define NIC_PHYMSK 19
00463
00464 #define PHYMSK_MINT 0x8000
00465 #define PHYMSK_MLNKFAIL 0x4000
00466 #define PHYMSK_MLOSSSYN 0x2000
00467 #define PHYMSK_MCWRD 0x1000
00468 #define PHYMSK_MSSD 0x0800
00469 #define PHYMSK_MESD 0x0400
00470 #define PHYMSK_MRPOL 0x0200
00471 #define PHYMSK_MJAB 0x0100
00472 #define PHYMSK_MSPDDT 0x0080
00473 #define PHYMSK_MDPLDT 0x0040
00474
00475
00476
00477 #define MSBV(bit) (1 << ((bit) - 8))
00478
00479 #define nic_outlb(addr, val) (*(volatile u8_t *)(addr) = (val))
00480 #define nic_outhb(addr, val) (*(volatile u8_t *)((addr) + 1) = (val))
00481 #define nic_outwx(addr, val) (*(volatile u16_t *)(addr) = (val))
00482 #define nic_outw(addr, val) { \
00483 *(volatile u8_t *)(addr) = (u8_t)(val); \
00484 *((volatile u8_t *)(addr) + 1) = (u8_t)((val) >> 8); \
00485 }
00486
00487 #define nic_inlb(addr) (*(volatile u8_t *)(addr))
00488 #define nic_inhb(addr) (*(volatile u8_t *)((addr) + 1))
00489 #define nic_inw(addr) (*(volatile u16_t *)(addr))
00490
00491 #define nic_bs(bank) nic_outlb(NIC_BSR, bank)
00492
00493
00494
00495
00496
00497
00498
00499
00500
00501
00502
00503
00504
00505
00506
00507
00508
00509
00510
00511
00512
00513
00514
00515
00516 static u8_t NicPhyRegSelect(u8_t reg, u8_t we)
00517 {
00518 u8_t rs;
00519 u8_t msk;
00520 u8_t i;
00521
00522 nic_bs(3);
00523 rs = (nic_inlb(NIC_MGMT) & ~(MGMT_MCLK | MGMT_MDO)) | MGMT_MDOE;
00524
00525
00526 for (i = 0; i < 33; i++) {
00527 nic_outlb(NIC_MGMT, rs | MGMT_MDO);
00528 nic_outlb(NIC_MGMT, rs | MGMT_MDO | MGMT_MCLK);
00529 }
00530
00531
00532 nic_outlb(NIC_MGMT, rs);
00533 nic_outlb(NIC_MGMT, rs | MGMT_MCLK);
00534 nic_outlb(NIC_MGMT, rs | MGMT_MDO);
00535 nic_outlb(NIC_MGMT, rs | MGMT_MDO | MGMT_MCLK);
00536
00537
00538 if (we) {
00539 nic_outlb(NIC_MGMT, rs);
00540 nic_outlb(NIC_MGMT, rs | MGMT_MCLK);
00541 nic_outlb(NIC_MGMT, rs | MGMT_MDO);
00542 nic_outlb(NIC_MGMT, rs | MGMT_MDO | MGMT_MCLK);
00543 } else {
00544 nic_outlb(NIC_MGMT, rs | MGMT_MDO);
00545 nic_outlb(NIC_MGMT, rs | MGMT_MDO | MGMT_MCLK);
00546 nic_outlb(NIC_MGMT, rs);
00547 nic_outlb(NIC_MGMT, rs | MGMT_MCLK);
00548 }
00549
00550
00551 for (i = 0; i < 5; i++) {
00552 nic_outlb(NIC_MGMT, rs);
00553 nic_outlb(NIC_MGMT, rs | MGMT_MCLK);
00554 }
00555
00556
00557 for (msk = 0x10; msk; msk >>= 1) {
00558 if (reg & msk) {
00559 nic_outlb(NIC_MGMT, rs | MGMT_MDO);
00560 nic_outlb(NIC_MGMT, rs | MGMT_MDO | MGMT_MCLK);
00561 } else {
00562 nic_outlb(NIC_MGMT, rs);
00563 nic_outlb(NIC_MGMT, rs | MGMT_MCLK);
00564 }
00565 }
00566 nic_outlb(NIC_MGMT, rs);
00567
00568 return rs;
00569 }
00570
00571
00572
00573
00574
00575
00576
00577
00578
00579
00580 static u16_t NicPhyRead(u8_t reg)
00581 {
00582 u16_t rc = 0;
00583 u8_t rs;
00584 u8_t i;
00585
00586
00587 rs = NicPhyRegSelect(reg, 0);
00588
00589
00590 rs &= ~MGMT_MDOE;
00591 nic_outlb(NIC_MGMT, rs);
00592 nic_outlb(NIC_MGMT, rs | MGMT_MCLK);
00593
00594
00595 for (i = 0; i < 16; i++) {
00596 nic_outlb(NIC_MGMT, rs);
00597 nic_outlb(NIC_MGMT, rs | MGMT_MCLK);
00598 rc <<= 1;
00599 rc |= (nic_inlb(NIC_MGMT) & MGMT_MDI) != 0;
00600 }
00601
00602
00603 nic_outlb(NIC_MGMT, rs);
00604
00605 return rc;
00606 }
00607
00608
00609
00610
00611
00612
00613
00614
00615
00616 static void NicPhyWrite(u8_t reg, u16_t val)
00617 {
00618 u16_t msk;
00619 u8_t rs;
00620
00621
00622 rs = NicPhyRegSelect(reg, 1);
00623
00624
00625 nic_outlb(NIC_MGMT, rs | MGMT_MDO);
00626 nic_outlb(NIC_MGMT, rs | MGMT_MDO | MGMT_MCLK);
00627 nic_outlb(NIC_MGMT, rs);
00628 nic_outlb(NIC_MGMT, rs | MGMT_MCLK);
00629
00630
00631 for (msk = 0x8000; msk; msk >>= 1) {
00632 if (val & msk) {
00633 nic_outlb(NIC_MGMT, rs | MGMT_MDO);
00634 nic_outlb(NIC_MGMT, rs | MGMT_MDO | MGMT_MCLK);
00635 } else {
00636 nic_outlb(NIC_MGMT, rs);
00637 nic_outlb(NIC_MGMT, rs | MGMT_MCLK);
00638 }
00639 }
00640
00641
00642 nic_outlb(NIC_MGMT, rs & ~MGMT_MDOE);
00643 }
00644
00645
00646
00647
00648
00649
00650 static int NicPhyConfig(void)
00651 {
00652 u16_t phy_sor;
00653 u16_t phy_sr;
00654 u16_t phy_to;
00655 u16_t mode;
00656
00657
00658
00659
00660
00661
00662
00663 NicPhyWrite(NIC_PHYCR, PHYCR_RST);
00664 for (phy_to = 0;; phy_to++) {
00665 NutSleep(63);
00666 if ((NicPhyRead(NIC_PHYCR) & PHYCR_RST) == 0)
00667 break;
00668 if (phy_to > 3)
00669 return -1;
00670 }
00671
00672
00673
00674 phy_sor = NicPhyRead(NIC_PHYSOR);
00675
00676
00677 NicPhyWrite(NIC_PHYMSK, PHYMSK_MLOSSSYN | PHYMSK_MCWRD | PHYMSK_MSSD |
00678 PHYMSK_MESD | PHYMSK_MRPOL | PHYMSK_MJAB | PHYMSK_MSPDDT | PHYMSK_MDPLDT);
00679
00680
00681 mode = RPCR_ANEG | RPCR_LEDA_PAT | RPCR_LEDB_PAT;
00682 nic_bs(0);
00683 nic_outw(NIC_RPCR, mode);
00684
00685 #ifdef NIC_FIXED
00686
00687 phy_sr = NicPhyRead(NIC_PHYCFR1);
00688 NicPhyWrite(NIC_PHYCFR1, phy_sr | 0x8000);
00689 NutSleep(63);
00690
00691
00692 NicPhyWrite(NIC_PHYCR, NIC_FIXED);
00693 nic_bs(0);
00694 nic_outw(NIC_RPCR, mode);
00695
00696
00697 phy_sr = NicPhyRead(NIC_PHYCFR1);
00698 NicPhyWrite(NIC_PHYCFR1, phy_sr & ~0x8000);
00699 phy_sr = NicPhyRead(NIC_PHYCFR1);
00700
00701 #else
00702
00703
00704
00705
00706
00707 NicPhyWrite(NIC_PHYANAD, PHYANAD_TX_FDX | PHYANAD_TX_HDX | PHYANAD_10FDX | PHYANAD_10_HDX | PHYANAD_CSMA);
00708 NutSleep(63);
00709 for (phy_to = 0, phy_sr = 0;; phy_to++) {
00710
00711 if (phy_to >= 1024)
00712 return -1;
00713
00714 if ((phy_to & 127) == 0 ) {
00715 NicPhyWrite(NIC_PHYCR, PHYCR_ANEG_EN | PHYCR_ANEG_RST);
00716
00717 NutSleep(63);
00718 }
00719
00720 phy_sr = NicPhyRead(NIC_PHYSR);
00721
00722 if (phy_sr & PHYSR_ANEG_ACK)
00723 break;
00724 NutSleep(63);
00725 }
00726
00727 #endif
00728
00729 return 0;
00730 }
00731
00732
00733
00734
00735
00736
00737
00738
00739
00740
00741
00742 static INLINE int NicMmuWait(u16_t tmo)
00743 {
00744 while (tmo--) {
00745 if ((nic_inlb(NIC_MMUCR) & MMUCR_BUSY) == 0)
00746 break;
00747 NutDelay(1);
00748 }
00749 return tmo ? 0 : -1;
00750 }
00751
00752
00753
00754
00755
00756
00757 static int NicReset(void)
00758 {
00759 #ifdef LANC111_RESET_BIT
00760 sbi(LANC111_RESET_DDR, LANC111_RESET_BIT);
00761 sbi(LANC111_RESET_PORT, LANC111_RESET_BIT);
00762 NutDelay(WAIT100);
00763 cbi(LANC111_RESET_PORT, LANC111_RESET_BIT);
00764 NutDelay(WAIT250);
00765 NutDelay(WAIT250);
00766 #endif
00767
00768
00769 nic_outlb(NIC_MSK, 0);
00770
00771
00772 nic_bs(0);
00773 nic_outw(NIC_RCR, RCR_SOFT_RST);
00774
00775
00776 nic_bs(1);
00777 nic_outw(NIC_CR, CR_EPH_EN);
00778
00779 NutDelay(10);
00780
00781
00782 nic_bs(0);
00783 nic_outw(NIC_RCR, 0);
00784 nic_outw(NIC_TCR, 0);
00785
00786
00787 nic_bs(1);
00788 nic_outw(NIC_CTR, CTR_AUTO_RELEASE);
00789
00790
00791 nic_bs(2);
00792 nic_outlb(NIC_MMUCR, MMU_RST);
00793 if (NicMmuWait(1000))
00794 return -1;
00795
00796 return 0;
00797 }
00798
00799
00800
00801
00802
00803
00804
00805
00806 static int NicStart(CONST u8_t * mac)
00807 {
00808 u8_t i;
00809
00810 if (NicReset())
00811 return -1;
00812
00813
00814 nic_bs(3);
00815 nic_outlb(NIC_ERCV, 7);
00816 nic_bs(0);
00817 nic_outw(NIC_RCR, RCR_RXEN);
00818
00819
00820 nic_outw(NIC_TCR, TCR_PAD_EN | TCR_TXENA);
00821
00822
00823 if (NicPhyConfig())
00824 return -1;
00825
00826
00827
00828 nic_bs(1);
00829 for (i = 0; i < 6; i++)
00830 nic_outlb(NIC_IAR + i, mac[i]);
00831
00832
00833
00834 nic_bs(2);
00835 nic_outlb(NIC_MSK, INT_ERCV | INT_RCV | INT_RX_OVRN);
00836
00837 return 0;
00838 }
00839
00840
00841
00842
00843 #if 0
00844 static void NicInterrupt(void *arg)
00845 {
00846 u8_t isr;
00847 u8_t imr;
00848 NICINFO *ni = (NICINFO *) ((NUTDEVICE *) arg)->dev_dcb;
00849
00850 ni->ni_interrupts++;
00851
00852
00853 nic_bs(2);
00854 imr = nic_inlb(NIC_MSK);
00855 nic_outlb(NIC_MSK, 0);
00856
00857
00858 isr = nic_inlb(NIC_IST);
00859
00860 isr &= imr;
00861
00862
00863
00864
00865
00866
00867 if (isr & INT_TX_EMPTY) {
00868 nic_outlb(NIC_ACK, INT_TX_EMPTY);
00869 imr &= ~INT_TX_EMPTY;
00870 NutEventPostFromIrq(&ni->ni_tx_rdy);
00871 }
00872
00873 else if (isr & INT_TX) {
00874
00875 nic_bs(0);
00876 nic_outw(NIC_TCR, nic_inlb(NIC_TCR) | TCR_TXENA);
00877 nic_bs(2);
00878 nic_outlb(NIC_ACK, INT_TX);
00879
00880 nic_outlb(NIC_MMUCR, MMU_PKT);
00881
00882 NutEventPostFromIrq(&ni->ni_tx_rdy);
00883 }
00884
00885
00886
00887
00888
00889
00890 if (isr & INT_RX_OVRN) {
00891 nic_outlb(NIC_ACK, INT_RX_OVRN);
00892
00893 }
00894 if (isr & INT_ERCV) {
00895 nic_outlb(NIC_ACK, INT_ERCV);
00896 NutEventPostFromIrq(&ni->ni_rx_rdy);
00897 }
00898 if (isr & INT_RCV) {
00899 nic_outlb(NIC_ACK, INT_RCV);
00900 imr &= ~INT_RCV;
00901 NutEventPostFromIrq(&ni->ni_rx_rdy);
00902 }
00903
00904 if (isr & INT_ALLOC) {
00905 imr &= ~INT_ALLOC;
00906 NutEventPostFromIrq(&maq);
00907 }
00908
00909 nic_outlb(NIC_MSK, imr);
00910 }
00911 #endif
00912
00913
00914
00915 static void NicWrite(u8_t * buf, u16_t len)
00916 {
00917 register u16_t l = len - 1;
00918 register u8_t ih = (u16_t) l >> 8;
00919 register u8_t il = (u8_t) l;
00920
00921 if (!len)
00922 return;
00923
00924 do {
00925 do {
00926 nic_outlb(NIC_DATA, *buf++);
00927 } while (il-- != 0);
00928 } while (ih-- != 0);
00929 }
00930
00931
00932
00933
00934 static void NicRead(u8_t * buf, u16_t len)
00935 {
00936 register u16_t l = len - 1;
00937 register u8_t ih = (u16_t) l >> 8;
00938 register u8_t il = (u8_t) l;
00939
00940 if (!len)
00941 return;
00942
00943 do {
00944 do {
00945 *buf++ = nic_inlb(NIC_DATA);
00946 } while (il-- != 0);
00947 } while (ih-- != 0);
00948 }
00949
00950
00951
00952
00953
00954
00955
00956
00957
00958
00959
00960 static NETBUF *NicGetPacket(void)
00961 {
00962 NETBUF *nb = 0;
00963
00964 u16_t fsw;
00965 u16_t fbc;
00966
00967
00968
00969 nic_bs(2);
00970 if (nic_inw(NIC_FIFO) & 0x8000) {
00971 return 0;
00972 }
00973
00974
00975 nic_outw(NIC_PTR, PTR_READ | PTR_RCV | PTR_AUTO_INCR);
00976 _NOP();
00977 _NOP();
00978 _NOP();
00979 _NOP();
00980
00981
00982 fsw = nic_inw(NIC_DATA);
00983 fbc = nic_inw(NIC_DATA);
00984
00985
00986
00987 if (fsw & 0xAC00) {
00988 nb = (NETBUF *) 0xFFFF;
00989 }
00990
00991 else if (fbc < 66 || fbc > 1524) {
00992 nb = (NETBUF *) 0xFFFF;
00993 }
00994
00995 else {
00996
00997
00998
00999
01000 fbc -= 3;
01001
01002
01003
01004
01005
01006 }
01007
01008
01009 nic_outlb(NIC_MMUCR, MMU_TOP);
01010
01011 return nb;
01012 }
01013
01014
01015
01016
01017
01018
01019
01020
01021
01022
01023
01024
01025
01026
01027
01028 #if 0
01029 static int NicPutPacket(NETBUF * nb)
01030 {
01031 u16_t sz;
01032 u8_t odd = 0;
01033 u8_t imsk;
01034
01035
01036
01037
01038
01039
01040
01041
01042 if ((sz = nb->nb_nw.sz + nb->nb_tp.sz + nb->nb_ap.sz) > ETHERMTU)
01043 return -1;
01044
01045
01046 imsk = nic_inlb(NIC_MSK);
01047 nic_outlb(NIC_MSK, 0);
01048
01049
01050 nic_bs(2);
01051 nic_outlb(NIC_MMUCR, MMU_ALO);
01052 if (NicMmuWait(100))
01053 return -1;
01054
01055
01056 nic_outlb(NIC_MSK, imsk | INT_ALLOC);
01057
01058
01059 sz += nb->nb_dl.sz;
01060 sz += 6;
01061 if (sz & 1) {
01062 sz++;
01063 odd++;
01064 }
01065
01066
01067 while ((nic_inlb(NIC_IST) & INT_ALLOC) == 0) {
01068 if (NutEventWait(&maq, 125)) {
01069 nic_outlb(NIC_MMUCR, MMU_RST);
01070 NicMmuWait(1000);
01071 nic_outlb(NIC_MMUCR, MMU_ALO);
01072 if (NicMmuWait(100) || (nic_inlb(NIC_IST) & INT_ALLOC) == 0) {
01073 if (NutEventWait(&maq, 125)) {
01074 return -1;
01075 }
01076 }
01077 }
01078 }
01079
01080
01081 imsk = nic_inlb(NIC_MSK);
01082 nic_outlb(NIC_MSK, 0);
01083
01084
01085 nic_outlb(NIC_PNR, nic_inhb(NIC_PNR));
01086
01087 nic_outw(NIC_PTR, 0x4000);
01088
01089
01090 nic_outlb(NIC_DATA, 0);
01091 nic_outlb(NIC_DATA, 0);
01092
01093
01094 nic_outw(NIC_DATA, sz);
01095
01096
01097 NicWrite(nb->nb_dl.vp, nb->nb_dl.sz);
01098 NicWrite(nb->nb_nw.vp, nb->nb_nw.sz);
01099 NicWrite(nb->nb_tp.vp, nb->nb_tp.sz);
01100 NicWrite(nb->nb_ap.vp, nb->nb_ap.sz);
01101
01102 if (odd)
01103 nic_outlb(NIC_DATA, 0);
01104
01105
01106 nic_outw(NIC_DATA, 0);
01107
01108
01109 if (NicMmuWait(100))
01110 return -1;
01111 nic_outlb(NIC_MMUCR, MMU_ENQ);
01112
01113
01114 imsk |= INT_TX | INT_TX_EMPTY;
01115 nic_outlb(NIC_MSK, imsk);
01116
01117 return 0;
01118 }
01119 #endif
01120
01121
01122
01123
01124
01125 #if 1
01126 PROCESS_THREAD(lanc111_process, ev, data)
01127
01128 {
01129
01130
01131
01132
01133 u8_t imsk;
01134 static struct etimer et;
01135
01136
01137
01138
01139
01140
01141
01142
01143
01144
01145
01146 PROCESS_BEGIN();
01147
01148
01149
01150 while(0) {
01151 etimer_set(&et, CLOCK_SECOND / 8);
01152 PROCESS_WAIT_UNTIL(etimer_expired(&et));
01153 }
01154
01155
01156
01157
01158
01159
01160
01161
01162 while(0) {
01163
01164 etimer_set(&et, CLOCK_SECOND);
01165 PROCESS_WAIT_UNTIL(etimer_expired(&et));
01166 }
01167
01168 LANC111_SIGNAL_MODE();
01169 sbi(EIMSK, LANC111_SIGNAL_IRQ);
01170
01171
01172
01173
01174
01175
01176 for (;;) {
01177
01178
01179
01180
01181
01182
01183 PROCESS_WAIT_EVENT();
01184
01185
01186
01187
01188
01189 imsk = nic_inlb(NIC_MSK);
01190 nic_outlb(NIC_MSK, 0);
01191
01192
01193
01194
01195
01196
01197 nic_outlb(NIC_MSK, imsk | INT_RCV | INT_ERCV);
01198 }
01199
01200 PROCESS_END();
01201 }
01202 #endif
01203
01204
01205
01206
01207
01208
01209
01210
01211
01212
01213 #if 0
01214 int LancOutput(NUTDEVICE * dev, NETBUF * nb)
01215 {
01216 static u_long mx_wait = 5000;
01217 int rc = -1;
01218 NICINFO *ni;
01219
01220
01221
01222
01223
01224 if (NutEventWait(&mutex, mx_wait) == 0) {
01225 ni = (NICINFO *) dev->dev_dcb;
01226
01227 if (NicPutPacket(nb) == 0) {
01228 ni->ni_tx_packets++;
01229 rc = 0;
01230
01231
01232 mx_wait = 5000;
01233 }
01234 NutEventPost(&mutex);
01235 }
01236
01237
01238
01239
01240 else {
01241 mx_wait = 500;
01242 }
01243 return rc;
01244 }
01245 #endif
01246 #if 0
01247
01248
01249
01250
01251
01252
01253
01254
01255
01256
01257
01258
01259
01260
01261
01262
01263
01264 int LancInit(NUTDEVICE * dev)
01265 {
01266
01267 cbi(EIMSK, LANC111_SIGNAL_IRQ);
01268 memset(dev->dev_dcb, 0, sizeof(NICINFO));
01269
01270
01271 if (NutRegisterIrqHandler(&LANC111_SIGNAL, NicInterrupt, dev))
01272 return -1;
01273
01274
01275
01276
01277 NutThreadCreate("rxi5", NicRxLanc, dev, 640);
01278
01279
01280
01281 return 0;
01282 }
01283
01284
01285
01286
01287
01288
01289
01290
01291 static NICINFO dcb_eth0;
01292
01293
01294
01295
01296
01297
01298 static IFNET ifn_eth0 = {
01299 IFT_ETHER,
01300 {0, 0, 0, 0, 0, 0},
01301 0,
01302 0,
01303 0,
01304 ETHERMTU,
01305 0,
01306 0,
01307 NutEtherInput,
01308 LancOutput,
01309 NutEtherOutput
01310 };
01311
01312
01313
01314
01315
01316
01317
01318
01319
01320
01321 NUTDEVICE devSmsc111 = {
01322 0,
01323 {'e', 't', 'h', '0', 0, 0, 0, 0, 0},
01324 IFTYP_NET,
01325 0,
01326 0,
01327 &ifn_eth0,
01328 &dcb_eth0,
01329 LancInit,
01330 0,
01331 0,
01332 0,
01333 0,
01334 0,
01335 0,
01336 0
01337 };
01338
01339
01340 #endif
01341
01342
01343 int
01344 lanc111_init(void)
01345 {
01346
01347 cbi(EIMSK, LANC111_SIGNAL_IRQ);
01348
01349
01350
01351
01352
01353
01354
01355
01356
01357
01358
01359
01360 return 0;
01361 }
01362