uboot/drivers/net/dc2114x.c
<<
>>
Prefs
   1/*
   2 * See file CREDITS for list of people who contributed to this
   3 * project.
   4 *
   5 * This program is free software; you can redistribute it and/or
   6 * modify it under the terms of the GNU General Public License as
   7 * published by the Free Software Foundation; either version 2 of
   8 * the License, or (at your option) any later version.
   9 *
  10 * This program is distributed in the hope that it will be useful,
  11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  13 * GNU General Public License for more details.
  14 *
  15 * You should have received a copy of the GNU General Public License
  16 * along with this program; if not, write to the Free Software
  17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
  18 * MA 02111-1307 USA
  19 */
  20
  21#include <common.h>
  22#include <malloc.h>
  23#include <net.h>
  24#include <netdev.h>
  25#include <pci.h>
  26
  27#undef DEBUG_SROM
  28#undef DEBUG_SROM2
  29
  30#undef UPDATE_SROM
  31
  32/* PCI Registers.
  33 */
  34#define PCI_CFDA_PSM            0x43
  35
  36#define CFRV_RN         0x000000f0      /* Revision Number */
  37
  38#define WAKEUP          0x00            /* Power Saving Wakeup */
  39#define SLEEP           0x80            /* Power Saving Sleep Mode */
  40
  41#define DC2114x_BRK     0x0020          /* CFRV break between DC21142 & DC21143 */
  42
  43/* Ethernet chip registers.
  44 */
  45#define DE4X5_BMR       0x000           /* Bus Mode Register */
  46#define DE4X5_TPD       0x008           /* Transmit Poll Demand Reg */
  47#define DE4X5_RRBA      0x018           /* RX Ring Base Address Reg */
  48#define DE4X5_TRBA      0x020           /* TX Ring Base Address Reg */
  49#define DE4X5_STS       0x028           /* Status Register */
  50#define DE4X5_OMR       0x030           /* Operation Mode Register */
  51#define DE4X5_SICR      0x068           /* SIA Connectivity Register */
  52#define DE4X5_APROM     0x048           /* Ethernet Address PROM */
  53
  54/* Register bits.
  55 */
  56#define BMR_SWR         0x00000001      /* Software Reset */
  57#define STS_TS          0x00700000      /* Transmit Process State */
  58#define STS_RS          0x000e0000      /* Receive Process State */
  59#define OMR_ST          0x00002000      /* Start/Stop Transmission Command */
  60#define OMR_SR          0x00000002      /* Start/Stop Receive */
  61#define OMR_PS          0x00040000      /* Port Select */
  62#define OMR_SDP         0x02000000      /* SD Polarity - MUST BE ASSERTED */
  63#define OMR_PM          0x00000080      /* Pass All Multicast */
  64
  65/* Descriptor bits.
  66 */
  67#define R_OWN           0x80000000      /* Own Bit */
  68#define RD_RER          0x02000000      /* Receive End Of Ring */
  69#define RD_LS           0x00000100      /* Last Descriptor */
  70#define RD_ES           0x00008000      /* Error Summary */
  71#define TD_TER          0x02000000      /* Transmit End Of Ring */
  72#define T_OWN           0x80000000      /* Own Bit */
  73#define TD_LS           0x40000000      /* Last Segment */
  74#define TD_FS           0x20000000      /* First Segment */
  75#define TD_ES           0x00008000      /* Error Summary */
  76#define TD_SET          0x08000000      /* Setup Packet */
  77
  78/* The EEPROM commands include the alway-set leading bit. */
  79#define SROM_WRITE_CMD  5
  80#define SROM_READ_CMD   6
  81#define SROM_ERASE_CMD  7
  82
  83#define SROM_HWADD          0x0014      /* Hardware Address offset in SROM */
  84#define SROM_RD         0x00004000      /* Read from Boot ROM */
  85#define EE_DATA_WRITE         0x04      /* EEPROM chip data in. */
  86#define EE_WRITE_0          0x4801
  87#define EE_WRITE_1          0x4805
  88#define EE_DATA_READ          0x08      /* EEPROM chip data out. */
  89#define SROM_SR         0x00000800      /* Select Serial ROM when set */
  90
  91#define DT_IN           0x00000004      /* Serial Data In */
  92#define DT_CLK          0x00000002      /* Serial ROM Clock */
  93#define DT_CS           0x00000001      /* Serial ROM Chip Select */
  94
  95#define POLL_DEMAND     1
  96
  97#ifdef CONFIG_TULIP_FIX_DAVICOM
  98#define RESET_DM9102(dev) {\
  99    unsigned long i;\
 100    i=INL(dev, 0x0);\
 101    udelay(1000);\
 102    OUTL(dev, i | BMR_SWR, DE4X5_BMR);\
 103    udelay(1000);\
 104}
 105#else
 106#define RESET_DE4X5(dev) {\
 107    int i;\
 108    i=INL(dev, DE4X5_BMR);\
 109    udelay(1000);\
 110    OUTL(dev, i | BMR_SWR, DE4X5_BMR);\
 111    udelay(1000);\
 112    OUTL(dev, i, DE4X5_BMR);\
 113    udelay(1000);\
 114    for (i=0;i<5;i++) {INL(dev, DE4X5_BMR); udelay(10000);}\
 115    udelay(1000);\
 116}
 117#endif
 118
 119#define START_DE4X5(dev) {\
 120    s32 omr; \
 121    omr = INL(dev, DE4X5_OMR);\
 122    omr |= OMR_ST | OMR_SR;\
 123    OUTL(dev, omr, DE4X5_OMR);          /* Enable the TX and/or RX */\
 124}
 125
 126#define STOP_DE4X5(dev) {\
 127    s32 omr; \
 128    omr = INL(dev, DE4X5_OMR);\
 129    omr &= ~(OMR_ST|OMR_SR);\
 130    OUTL(dev, omr, DE4X5_OMR);          /* Disable the TX and/or RX */ \
 131}
 132
 133#define NUM_RX_DESC PKTBUFSRX
 134#ifndef CONFIG_TULIP_FIX_DAVICOM
 135        #define NUM_TX_DESC 1                   /* Number of TX descriptors   */
 136#else
 137        #define NUM_TX_DESC 4
 138#endif
 139#define RX_BUFF_SZ  PKTSIZE_ALIGN
 140
 141#define TOUT_LOOP   1000000
 142
 143#define SETUP_FRAME_LEN 192
 144#define ETH_ALEN        6
 145
 146struct de4x5_desc {
 147        volatile s32 status;
 148        u32 des1;
 149        u32 buf;
 150        u32 next;
 151};
 152
 153static struct de4x5_desc rx_ring[NUM_RX_DESC] __attribute__ ((aligned(32))); /* RX descriptor ring         */
 154static struct de4x5_desc tx_ring[NUM_TX_DESC] __attribute__ ((aligned(32))); /* TX descriptor ring         */
 155static int rx_new;                             /* RX descriptor ring pointer */
 156static int tx_new;                             /* TX descriptor ring pointer */
 157
 158static char rxRingSize;
 159static char txRingSize;
 160
 161#if defined(UPDATE_SROM) || !defined(CONFIG_TULIP_FIX_DAVICOM)
 162static void  sendto_srom(struct eth_device* dev, u_int command, u_long addr);
 163static int   getfrom_srom(struct eth_device* dev, u_long addr);
 164static int   do_eeprom_cmd(struct eth_device *dev, u_long ioaddr,int cmd,int cmd_len);
 165static int   do_read_eeprom(struct eth_device *dev,u_long ioaddr,int location,int addr_len);
 166#endif  /* UPDATE_SROM || !CONFIG_TULIP_FIX_DAVICOM */
 167#ifdef UPDATE_SROM
 168static int   write_srom(struct eth_device *dev, u_long ioaddr, int index, int new_value);
 169static void  update_srom(struct eth_device *dev, bd_t *bis);
 170#endif
 171#ifndef CONFIG_TULIP_FIX_DAVICOM
 172static int   read_srom(struct eth_device *dev, u_long ioaddr, int index);
 173static void  read_hw_addr(struct eth_device* dev, bd_t * bis);
 174#endif  /* CONFIG_TULIP_FIX_DAVICOM */
 175static void  send_setup_frame(struct eth_device* dev, bd_t * bis);
 176
 177static int   dc21x4x_init(struct eth_device* dev, bd_t* bis);
 178static int   dc21x4x_send(struct eth_device* dev, volatile void *packet, int length);
 179static int   dc21x4x_recv(struct eth_device* dev);
 180static void  dc21x4x_halt(struct eth_device* dev);
 181#ifdef CONFIG_TULIP_SELECT_MEDIA
 182extern void  dc21x4x_select_media(struct eth_device* dev);
 183#endif
 184
 185#if defined(CONFIG_E500)
 186#define phys_to_bus(a) (a)
 187#else
 188#define phys_to_bus(a)  pci_phys_to_mem((pci_dev_t)dev->priv, a)
 189#endif
 190
 191static int INL(struct eth_device* dev, u_long addr)
 192{
 193        return le32_to_cpu(*(volatile u_long *)(addr + dev->iobase));
 194}
 195
 196static void OUTL(struct eth_device* dev, int command, u_long addr)
 197{
 198        *(volatile u_long *)(addr + dev->iobase) = cpu_to_le32(command);
 199}
 200
 201static struct pci_device_id supported[] = {
 202        { PCI_VENDOR_ID_DEC, PCI_DEVICE_ID_DEC_TULIP_FAST },
 203        { PCI_VENDOR_ID_DEC, PCI_DEVICE_ID_DEC_21142 },
 204#ifdef CONFIG_TULIP_FIX_DAVICOM
 205        { PCI_VENDOR_ID_DAVICOM, PCI_DEVICE_ID_DAVICOM_DM9102A },
 206#endif
 207        { }
 208};
 209
 210int dc21x4x_initialize(bd_t *bis)
 211{
 212        int                     idx=0;
 213        int                     card_number = 0;
 214        unsigned int            cfrv;
 215        unsigned char           timer;
 216        pci_dev_t               devbusfn;
 217        unsigned int            iobase;
 218        unsigned short          status;
 219        struct eth_device*      dev;
 220
 221        while(1) {
 222                devbusfn =  pci_find_devices(supported, idx++);
 223                if (devbusfn == -1) {
 224                        break;
 225                }
 226
 227                /* Get the chip configuration revision register. */
 228                pci_read_config_dword(devbusfn, PCI_REVISION_ID, &cfrv);
 229
 230#ifndef CONFIG_TULIP_FIX_DAVICOM
 231                if ((cfrv & CFRV_RN) < DC2114x_BRK ) {
 232                        printf("Error: The chip is not DC21143.\n");
 233                        continue;
 234                }
 235#endif
 236
 237                pci_read_config_word(devbusfn, PCI_COMMAND, &status);
 238                status |=
 239#ifdef CONFIG_TULIP_USE_IO
 240                  PCI_COMMAND_IO |
 241#else
 242                  PCI_COMMAND_MEMORY |
 243#endif
 244                  PCI_COMMAND_MASTER;
 245                pci_write_config_word(devbusfn, PCI_COMMAND, status);
 246
 247                pci_read_config_word(devbusfn, PCI_COMMAND, &status);
 248#ifdef CONFIG_TULIP_USE_IO
 249                if (!(status & PCI_COMMAND_IO)) {
 250                        printf("Error: Can not enable I/O access.\n");
 251                        continue;
 252                }
 253#else
 254                if (!(status & PCI_COMMAND_MEMORY)) {
 255                        printf("Error: Can not enable MEMORY access.\n");
 256                        continue;
 257                }
 258#endif
 259
 260                if (!(status & PCI_COMMAND_MASTER)) {
 261                        printf("Error: Can not enable Bus Mastering.\n");
 262                        continue;
 263                }
 264
 265                /* Check the latency timer for values >= 0x60. */
 266                pci_read_config_byte(devbusfn, PCI_LATENCY_TIMER, &timer);
 267
 268                if (timer < 0x60) {
 269                        pci_write_config_byte(devbusfn, PCI_LATENCY_TIMER, 0x60);
 270                }
 271
 272#ifdef CONFIG_TULIP_USE_IO
 273                /* read BAR for memory space access */
 274                pci_read_config_dword(devbusfn, PCI_BASE_ADDRESS_0, &iobase);
 275                iobase &= PCI_BASE_ADDRESS_IO_MASK;
 276#else
 277                /* read BAR for memory space access */
 278                pci_read_config_dword(devbusfn, PCI_BASE_ADDRESS_1, &iobase);
 279                iobase &= PCI_BASE_ADDRESS_MEM_MASK;
 280#endif
 281                debug ("dc21x4x: DEC 21142 PCI Device @0x%x\n", iobase);
 282
 283                dev = (struct eth_device*) malloc(sizeof *dev);
 284
 285                if (!dev) {
 286                        printf("Can not allocalte memory of dc21x4x\n");
 287                        break;
 288                }
 289                memset(dev, 0, sizeof(*dev));
 290
 291#ifdef CONFIG_TULIP_FIX_DAVICOM
 292                sprintf(dev->name, "Davicom#%d", card_number);
 293#else
 294                sprintf(dev->name, "dc21x4x#%d", card_number);
 295#endif
 296
 297#ifdef CONFIG_TULIP_USE_IO
 298                dev->iobase = pci_io_to_phys(devbusfn, iobase);
 299#else
 300                dev->iobase = pci_mem_to_phys(devbusfn, iobase);
 301#endif
 302                dev->priv   = (void*) devbusfn;
 303                dev->init   = dc21x4x_init;
 304                dev->halt   = dc21x4x_halt;
 305                dev->send   = dc21x4x_send;
 306                dev->recv   = dc21x4x_recv;
 307
 308                /* Ensure we're not sleeping. */
 309                pci_write_config_byte(devbusfn, PCI_CFDA_PSM, WAKEUP);
 310
 311                udelay(10 * 1000);
 312
 313#ifndef CONFIG_TULIP_FIX_DAVICOM
 314                read_hw_addr(dev, bis);
 315#endif
 316                eth_register(dev);
 317
 318                card_number++;
 319        }
 320
 321        return card_number;
 322}
 323
 324static int dc21x4x_init(struct eth_device* dev, bd_t* bis)
 325{
 326        int             i;
 327        int             devbusfn = (int) dev->priv;
 328
 329        /* Ensure we're not sleeping. */
 330        pci_write_config_byte(devbusfn, PCI_CFDA_PSM, WAKEUP);
 331
 332#ifdef CONFIG_TULIP_FIX_DAVICOM
 333        RESET_DM9102(dev);
 334#else
 335        RESET_DE4X5(dev);
 336#endif
 337
 338        if ((INL(dev, DE4X5_STS) & (STS_TS | STS_RS)) != 0) {
 339                printf("Error: Cannot reset ethernet controller.\n");
 340                return -1;
 341        }
 342
 343#ifdef CONFIG_TULIP_SELECT_MEDIA
 344        dc21x4x_select_media(dev);
 345#else
 346        OUTL(dev, OMR_SDP | OMR_PS | OMR_PM, DE4X5_OMR);
 347#endif
 348
 349        for (i = 0; i < NUM_RX_DESC; i++) {
 350                rx_ring[i].status = cpu_to_le32(R_OWN);
 351                rx_ring[i].des1 = cpu_to_le32(RX_BUFF_SZ);
 352                rx_ring[i].buf = cpu_to_le32(phys_to_bus((u32) NetRxPackets[i]));
 353#ifdef CONFIG_TULIP_FIX_DAVICOM
 354                rx_ring[i].next = cpu_to_le32(phys_to_bus((u32) &rx_ring[(i+1) % NUM_RX_DESC]));
 355#else
 356                rx_ring[i].next = 0;
 357#endif
 358        }
 359
 360        for (i=0; i < NUM_TX_DESC; i++) {
 361                tx_ring[i].status = 0;
 362                tx_ring[i].des1 = 0;
 363                tx_ring[i].buf = 0;
 364
 365#ifdef CONFIG_TULIP_FIX_DAVICOM
 366        tx_ring[i].next = cpu_to_le32(phys_to_bus((u32) &tx_ring[(i+1) % NUM_TX_DESC]));
 367#else
 368                tx_ring[i].next = 0;
 369#endif
 370        }
 371
 372        rxRingSize = NUM_RX_DESC;
 373        txRingSize = NUM_TX_DESC;
 374
 375        /* Write the end of list marker to the descriptor lists. */
 376        rx_ring[rxRingSize - 1].des1 |= cpu_to_le32(RD_RER);
 377        tx_ring[txRingSize - 1].des1 |= cpu_to_le32(TD_TER);
 378
 379        /* Tell the adapter where the TX/RX rings are located. */
 380        OUTL(dev, phys_to_bus((u32) &rx_ring), DE4X5_RRBA);
 381        OUTL(dev, phys_to_bus((u32) &tx_ring), DE4X5_TRBA);
 382
 383        START_DE4X5(dev);
 384
 385        tx_new = 0;
 386        rx_new = 0;
 387
 388        send_setup_frame(dev, bis);
 389
 390        return 0;
 391}
 392
 393static int dc21x4x_send(struct eth_device* dev, volatile void *packet, int length)
 394{
 395        int             status = -1;
 396        int             i;
 397
 398        if (length <= 0) {
 399                printf("%s: bad packet size: %d\n", dev->name, length);
 400                goto Done;
 401        }
 402
 403        for(i = 0; tx_ring[tx_new].status & cpu_to_le32(T_OWN); i++) {
 404                if (i >= TOUT_LOOP) {
 405                        printf("%s: tx error buffer not ready\n", dev->name);
 406                        goto Done;
 407                }
 408        }
 409
 410        tx_ring[tx_new].buf    = cpu_to_le32(phys_to_bus((u32) packet));
 411        tx_ring[tx_new].des1   = cpu_to_le32(TD_TER | TD_LS | TD_FS | length);
 412        tx_ring[tx_new].status = cpu_to_le32(T_OWN);
 413
 414        OUTL(dev, POLL_DEMAND, DE4X5_TPD);
 415
 416        for(i = 0; tx_ring[tx_new].status & cpu_to_le32(T_OWN); i++) {
 417                if (i >= TOUT_LOOP) {
 418                        printf(".%s: tx buffer not ready\n", dev->name);
 419                        goto Done;
 420                }
 421        }
 422
 423        if (le32_to_cpu(tx_ring[tx_new].status) & TD_ES) {
 424#if 0 /* test-only */
 425                printf("TX error status = 0x%08X\n",
 426                        le32_to_cpu(tx_ring[tx_new].status));
 427#endif
 428                tx_ring[tx_new].status = 0x0;
 429                goto Done;
 430        }
 431
 432        status = length;
 433
 434 Done:
 435    tx_new = (tx_new+1) % NUM_TX_DESC;
 436        return status;
 437}
 438
 439static int dc21x4x_recv(struct eth_device* dev)
 440{
 441        s32             status;
 442        int             length    = 0;
 443
 444        for ( ; ; ) {
 445                status = (s32)le32_to_cpu(rx_ring[rx_new].status);
 446
 447                if (status & R_OWN) {
 448                        break;
 449                }
 450
 451                if (status & RD_LS) {
 452                        /* Valid frame status.
 453                         */
 454                        if (status & RD_ES) {
 455
 456                                /* There was an error.
 457                                 */
 458                                printf("RX error status = 0x%08X\n", status);
 459                        } else {
 460                                /* A valid frame received.
 461                                 */
 462                                length = (le32_to_cpu(rx_ring[rx_new].status) >> 16);
 463
 464                                /* Pass the packet up to the protocol
 465                                 * layers.
 466                                 */
 467                                NetReceive(NetRxPackets[rx_new], length - 4);
 468                        }
 469
 470                        /* Change buffer ownership for this frame, back
 471                         * to the adapter.
 472                         */
 473                        rx_ring[rx_new].status = cpu_to_le32(R_OWN);
 474                }
 475
 476                /* Update entry information.
 477                 */
 478                rx_new = (rx_new + 1) % rxRingSize;
 479        }
 480
 481        return length;
 482}
 483
 484static void dc21x4x_halt(struct eth_device* dev)
 485{
 486        int             devbusfn = (int) dev->priv;
 487
 488        STOP_DE4X5(dev);
 489        OUTL(dev, 0, DE4X5_SICR);
 490
 491        pci_write_config_byte(devbusfn, PCI_CFDA_PSM, SLEEP);
 492}
 493
 494static void send_setup_frame(struct eth_device* dev, bd_t *bis)
 495{
 496        int             i;
 497        char    setup_frame[SETUP_FRAME_LEN];
 498        char    *pa = &setup_frame[0];
 499
 500        memset(pa, 0xff, SETUP_FRAME_LEN);
 501
 502        for (i = 0; i < ETH_ALEN; i++) {
 503                *(pa + (i & 1)) = dev->enetaddr[i];
 504                if (i & 0x01) {
 505                        pa += 4;
 506                }
 507        }
 508
 509        for(i = 0; tx_ring[tx_new].status & cpu_to_le32(T_OWN); i++) {
 510                if (i >= TOUT_LOOP) {
 511                        printf("%s: tx error buffer not ready\n", dev->name);
 512                        goto Done;
 513                }
 514        }
 515
 516        tx_ring[tx_new].buf = cpu_to_le32(phys_to_bus((u32) &setup_frame[0]));
 517        tx_ring[tx_new].des1 = cpu_to_le32(TD_TER | TD_SET| SETUP_FRAME_LEN);
 518        tx_ring[tx_new].status = cpu_to_le32(T_OWN);
 519
 520        OUTL(dev, POLL_DEMAND, DE4X5_TPD);
 521
 522        for(i = 0; tx_ring[tx_new].status & cpu_to_le32(T_OWN); i++) {
 523                if (i >= TOUT_LOOP) {
 524                        printf("%s: tx buffer not ready\n", dev->name);
 525                        goto Done;
 526                }
 527        }
 528
 529        if (le32_to_cpu(tx_ring[tx_new].status) != 0x7FFFFFFF) {
 530                printf("TX error status2 = 0x%08X\n", le32_to_cpu(tx_ring[tx_new].status));
 531        }
 532        tx_new = (tx_new+1) % NUM_TX_DESC;
 533
 534Done:
 535        return;
 536}
 537
 538#if defined(UPDATE_SROM) || !defined(CONFIG_TULIP_FIX_DAVICOM)
 539/* SROM Read and write routines.
 540 */
 541static void
 542sendto_srom(struct eth_device* dev, u_int command, u_long addr)
 543{
 544        OUTL(dev, command, addr);
 545        udelay(1);
 546}
 547
 548static int
 549getfrom_srom(struct eth_device* dev, u_long addr)
 550{
 551        s32 tmp;
 552
 553        tmp = INL(dev, addr);
 554        udelay(1);
 555
 556        return tmp;
 557}
 558
 559/* Note: this routine returns extra data bits for size detection. */
 560static int do_read_eeprom(struct eth_device *dev, u_long ioaddr, int location, int addr_len)
 561{
 562        int i;
 563        unsigned retval = 0;
 564        int read_cmd = location | (SROM_READ_CMD << addr_len);
 565
 566        sendto_srom(dev, SROM_RD | SROM_SR, ioaddr);
 567        sendto_srom(dev, SROM_RD | SROM_SR | DT_CS, ioaddr);
 568
 569#ifdef DEBUG_SROM
 570        printf(" EEPROM read at %d ", location);
 571#endif
 572
 573        /* Shift the read command bits out. */
 574        for (i = 4 + addr_len; i >= 0; i--) {
 575                short dataval = (read_cmd & (1 << i)) ? EE_DATA_WRITE : 0;
 576                sendto_srom(dev, SROM_RD | SROM_SR | DT_CS | dataval, ioaddr);
 577                udelay(10);
 578                sendto_srom(dev, SROM_RD | SROM_SR | DT_CS | dataval | DT_CLK, ioaddr);
 579                udelay(10);
 580#ifdef DEBUG_SROM2
 581                printf("%X", getfrom_srom(dev, ioaddr) & 15);
 582#endif
 583                retval = (retval << 1) | ((getfrom_srom(dev, ioaddr) & EE_DATA_READ) ? 1 : 0);
 584        }
 585
 586        sendto_srom(dev, SROM_RD | SROM_SR | DT_CS, ioaddr);
 587
 588#ifdef DEBUG_SROM2
 589        printf(" :%X:", getfrom_srom(dev, ioaddr) & 15);
 590#endif
 591
 592        for (i = 16; i > 0; i--) {
 593                sendto_srom(dev, SROM_RD | SROM_SR | DT_CS | DT_CLK, ioaddr);
 594                udelay(10);
 595#ifdef DEBUG_SROM2
 596                printf("%X", getfrom_srom(dev, ioaddr) & 15);
 597#endif
 598                retval = (retval << 1) | ((getfrom_srom(dev, ioaddr) & EE_DATA_READ) ? 1 : 0);
 599                sendto_srom(dev, SROM_RD | SROM_SR | DT_CS, ioaddr);
 600                udelay(10);
 601        }
 602
 603        /* Terminate the EEPROM access. */
 604        sendto_srom(dev, SROM_RD | SROM_SR, ioaddr);
 605
 606#ifdef DEBUG_SROM2
 607        printf(" EEPROM value at %d is %5.5x.\n", location, retval);
 608#endif
 609
 610        return retval;
 611}
 612#endif  /* UPDATE_SROM || !CONFIG_TULIP_FIX_DAVICOM */
 613
 614/* This executes a generic EEPROM command, typically a write or write
 615 * enable. It returns the data output from the EEPROM, and thus may
 616 * also be used for reads.
 617 */
 618#if defined(UPDATE_SROM) || !defined(CONFIG_TULIP_FIX_DAVICOM)
 619static int do_eeprom_cmd(struct eth_device *dev, u_long ioaddr, int cmd, int cmd_len)
 620{
 621        unsigned retval = 0;
 622
 623#ifdef DEBUG_SROM
 624        printf(" EEPROM op 0x%x: ", cmd);
 625#endif
 626
 627        sendto_srom(dev,SROM_RD | SROM_SR | DT_CS | DT_CLK, ioaddr);
 628
 629        /* Shift the command bits out. */
 630        do {
 631                short dataval = (cmd & (1 << cmd_len)) ? EE_WRITE_1 : EE_WRITE_0;
 632                sendto_srom(dev,dataval, ioaddr);
 633                udelay(10);
 634
 635#ifdef DEBUG_SROM2
 636                printf("%X", getfrom_srom(dev,ioaddr) & 15);
 637#endif
 638
 639                sendto_srom(dev,dataval | DT_CLK, ioaddr);
 640                udelay(10);
 641                retval = (retval << 1) | ((getfrom_srom(dev,ioaddr) & EE_DATA_READ) ? 1 : 0);
 642        } while (--cmd_len >= 0);
 643        sendto_srom(dev,SROM_RD | SROM_SR | DT_CS, ioaddr);
 644
 645        /* Terminate the EEPROM access. */
 646        sendto_srom(dev,SROM_RD | SROM_SR, ioaddr);
 647
 648#ifdef DEBUG_SROM
 649        printf(" EEPROM result is 0x%5.5x.\n", retval);
 650#endif
 651
 652        return retval;
 653}
 654#endif  /* UPDATE_SROM || !CONFIG_TULIP_FIX_DAVICOM */
 655
 656#ifndef CONFIG_TULIP_FIX_DAVICOM
 657static int read_srom(struct eth_device *dev, u_long ioaddr, int index)
 658{
 659        int ee_addr_size = do_read_eeprom(dev, ioaddr, 0xff, 8) & 0x40000 ? 8 : 6;
 660
 661        return do_eeprom_cmd(dev, ioaddr,
 662                             (((SROM_READ_CMD << ee_addr_size) | index) << 16)
 663                             | 0xffff, 3 + ee_addr_size + 16);
 664}
 665#endif  /* CONFIG_TULIP_FIX_DAVICOM */
 666
 667#ifdef UPDATE_SROM
 668static int write_srom(struct eth_device *dev, u_long ioaddr, int index, int new_value)
 669{
 670        int ee_addr_size = do_read_eeprom(dev, ioaddr, 0xff, 8) & 0x40000 ? 8 : 6;
 671        int i;
 672        unsigned short newval;
 673
 674        udelay(10*1000); /* test-only */
 675
 676#ifdef DEBUG_SROM
 677        printf("ee_addr_size=%d.\n", ee_addr_size);
 678        printf("Writing new entry 0x%4.4x to offset %d.\n", new_value, index);
 679#endif
 680
 681        /* Enable programming modes. */
 682        do_eeprom_cmd(dev, ioaddr, (0x4f << (ee_addr_size-4)), 3+ee_addr_size);
 683
 684        /* Do the actual write. */
 685        do_eeprom_cmd(dev, ioaddr,
 686                      (((SROM_WRITE_CMD<<ee_addr_size)|index) << 16) | new_value,
 687                      3 + ee_addr_size + 16);
 688
 689        /* Poll for write finished. */
 690        sendto_srom(dev, SROM_RD | SROM_SR | DT_CS, ioaddr);
 691        for (i = 0; i < 10000; i++)                     /* Typical 2000 ticks */
 692                if (getfrom_srom(dev, ioaddr) & EE_DATA_READ)
 693                        break;
 694
 695#ifdef DEBUG_SROM
 696        printf(" Write finished after %d ticks.\n", i);
 697#endif
 698
 699        /* Disable programming. */
 700        do_eeprom_cmd(dev, ioaddr, (0x40 << (ee_addr_size-4)), 3 + ee_addr_size);
 701
 702        /* And read the result. */
 703        newval = do_eeprom_cmd(dev, ioaddr,
 704                               (((SROM_READ_CMD<<ee_addr_size)|index) << 16)
 705                               | 0xffff, 3 + ee_addr_size + 16);
 706#ifdef DEBUG_SROM
 707        printf("  New value at offset %d is %4.4x.\n", index, newval);
 708#endif
 709        return 1;
 710}
 711#endif
 712
 713#ifndef CONFIG_TULIP_FIX_DAVICOM
 714static void read_hw_addr(struct eth_device *dev, bd_t *bis)
 715{
 716        u_short tmp, *p = (u_short *)(&dev->enetaddr[0]);
 717        int i, j = 0;
 718
 719        for (i = 0; i < (ETH_ALEN >> 1); i++) {
 720                tmp = read_srom(dev, DE4X5_APROM, ((SROM_HWADD >> 1) + i));
 721                *p = le16_to_cpu(tmp);
 722                j += *p++;
 723        }
 724
 725        if ((j == 0) || (j == 0x2fffd)) {
 726                memset (dev->enetaddr, 0, ETH_ALEN);
 727                debug ("Warning: can't read HW address from SROM.\n");
 728                goto Done;
 729        }
 730
 731        return;
 732
 733Done:
 734#ifdef UPDATE_SROM
 735        update_srom(dev, bis);
 736#endif
 737        return;
 738}
 739#endif  /* CONFIG_TULIP_FIX_DAVICOM */
 740
 741#ifdef UPDATE_SROM
 742static void update_srom(struct eth_device *dev, bd_t *bis)
 743{
 744        int i;
 745        static unsigned short eeprom[0x40] = {
 746                0x140b, 0x6610, 0x0000, 0x0000, /* 00 */
 747                0x0000, 0x0000, 0x0000, 0x0000, /* 04 */
 748                0x00a3, 0x0103, 0x0000, 0x0000, /* 08 */
 749                0x0000, 0x1f00, 0x0000, 0x0000, /* 0c */
 750                0x0108, 0x038d, 0x0000, 0x0000, /* 10 */
 751                0xe078, 0x0001, 0x0040, 0x0018, /* 14 */
 752                0x0000, 0x0000, 0x0000, 0x0000, /* 18 */
 753                0x0000, 0x0000, 0x0000, 0x0000, /* 1c */
 754                0x0000, 0x0000, 0x0000, 0x0000, /* 20 */
 755                0x0000, 0x0000, 0x0000, 0x0000, /* 24 */
 756                0x0000, 0x0000, 0x0000, 0x0000, /* 28 */
 757                0x0000, 0x0000, 0x0000, 0x0000, /* 2c */
 758                0x0000, 0x0000, 0x0000, 0x0000, /* 30 */
 759                0x0000, 0x0000, 0x0000, 0x0000, /* 34 */
 760                0x0000, 0x0000, 0x0000, 0x0000, /* 38 */
 761                0x0000, 0x0000, 0x0000, 0x4e07, /* 3c */
 762        };
 763        uchar enetaddr[6];
 764
 765        /* Ethernet Addr... */
 766        if (!eth_getenv_enetaddr("ethaddr", enetaddr))
 767                return;
 768        eeprom[0x0a] = (enetaddr[1] << 8) | enetaddr[0];
 769        eeprom[0x0b] = (enetaddr[3] << 8) | enetaddr[2];
 770        eeprom[0x0c] = (enetaddr[5] << 8) | enetaddr[4];
 771
 772        for (i=0; i<0x40; i++) {
 773                write_srom(dev, DE4X5_APROM, i, eeprom[i]);
 774        }
 775}
 776#endif  /* UPDATE_SROM */
 777