uboot/drivers/net/sh_eth.c
<<
>>
Prefs
   1/*
   2 * sh_eth.c - Driver for Renesas SH7763's ethernet controler.
   3 *
   4 * Copyright (C) 2008, 2011 Renesas Solutions Corp.
   5 * Copyright (c) 2008, 2011 Nobuhiro Iwamatsu
   6 * Copyright (c) 2007 Carlos Munoz <carlos@kenati.com>
   7 *
   8 * This program is free software; you can redistribute it and/or modify
   9 * it under the terms of the GNU General Public License as published by
  10 * the Free Software Foundation; either version 2 of the License, or
  11 * (at your option) any later version.
  12 *
  13 * This program is distributed in the hope that it will be useful,
  14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  16 * GNU General Public License for more details.
  17 *
  18 * You should have received a copy of the GNU General Public License
  19 * along with this program; if not, write to the Free Software
  20 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  21 */
  22
  23#include <config.h>
  24#include <common.h>
  25#include <malloc.h>
  26#include <net.h>
  27#include <netdev.h>
  28#include <miiphy.h>
  29#include <asm/errno.h>
  30#include <asm/io.h>
  31
  32#include "sh_eth.h"
  33
  34#ifndef CONFIG_SH_ETHER_USE_PORT
  35# error "Please define CONFIG_SH_ETHER_USE_PORT"
  36#endif
  37#ifndef CONFIG_SH_ETHER_PHY_ADDR
  38# error "Please define CONFIG_SH_ETHER_PHY_ADDR"
  39#endif
  40#ifdef CONFIG_SH_ETHER_CACHE_WRITEBACK
  41#define flush_cache_wback(addr, len)    \
  42                        dcache_wback_range((u32)addr, (u32)(addr + len - 1))
  43#else
  44#define flush_cache_wback(...)
  45#endif
  46
  47#define TIMEOUT_CNT 1000
  48
  49int sh_eth_send(struct eth_device *dev, volatile void *packet, int len)
  50{
  51        struct sh_eth_dev *eth = dev->priv;
  52        int port = eth->port, ret = 0, timeout;
  53        struct sh_eth_info *port_info = &eth->port_info[port];
  54
  55        if (!packet || len > 0xffff) {
  56                printf(SHETHER_NAME ": %s: Invalid argument\n", __func__);
  57                ret = -EINVAL;
  58                goto err;
  59        }
  60
  61        /* packet must be a 4 byte boundary */
  62        if ((int)packet & (4 - 1)) {
  63                printf(SHETHER_NAME ": %s: packet not 4 byte alligned\n", __func__);
  64                ret = -EFAULT;
  65                goto err;
  66        }
  67
  68        /* Update tx descriptor */
  69        flush_cache_wback(packet, len);
  70        port_info->tx_desc_cur->td2 = ADDR_TO_PHY(packet);
  71        port_info->tx_desc_cur->td1 = len << 16;
  72        /* Must preserve the end of descriptor list indication */
  73        if (port_info->tx_desc_cur->td0 & TD_TDLE)
  74                port_info->tx_desc_cur->td0 = TD_TACT | TD_TFP | TD_TDLE;
  75        else
  76                port_info->tx_desc_cur->td0 = TD_TACT | TD_TFP;
  77
  78        /* Restart the transmitter if disabled */
  79        if (!(inl(EDTRR(port)) & EDTRR_TRNS))
  80                outl(EDTRR_TRNS, EDTRR(port));
  81
  82        /* Wait until packet is transmitted */
  83        timeout = TIMEOUT_CNT;
  84        while (port_info->tx_desc_cur->td0 & TD_TACT && timeout--)
  85                udelay(100);
  86
  87        if (timeout < 0) {
  88                printf(SHETHER_NAME ": transmit timeout\n");
  89                ret = -ETIMEDOUT;
  90                goto err;
  91        }
  92
  93        port_info->tx_desc_cur++;
  94        if (port_info->tx_desc_cur >= port_info->tx_desc_base + NUM_TX_DESC)
  95                port_info->tx_desc_cur = port_info->tx_desc_base;
  96
  97err:
  98        return ret;
  99}
 100
 101int sh_eth_recv(struct eth_device *dev)
 102{
 103        struct sh_eth_dev *eth = dev->priv;
 104        int port = eth->port, len = 0;
 105        struct sh_eth_info *port_info = &eth->port_info[port];
 106        volatile u8 *packet;
 107
 108        /* Check if the rx descriptor is ready */
 109        if (!(port_info->rx_desc_cur->rd0 & RD_RACT)) {
 110                /* Check for errors */
 111                if (!(port_info->rx_desc_cur->rd0 & RD_RFE)) {
 112                        len = port_info->rx_desc_cur->rd1 & 0xffff;
 113                        packet = (volatile u8 *)
 114                            ADDR_TO_P2(port_info->rx_desc_cur->rd2);
 115                        NetReceive(packet, len);
 116                }
 117
 118                /* Make current descriptor available again */
 119                if (port_info->rx_desc_cur->rd0 & RD_RDLE)
 120                        port_info->rx_desc_cur->rd0 = RD_RACT | RD_RDLE;
 121                else
 122                        port_info->rx_desc_cur->rd0 = RD_RACT;
 123
 124                /* Point to the next descriptor */
 125                port_info->rx_desc_cur++;
 126                if (port_info->rx_desc_cur >=
 127                    port_info->rx_desc_base + NUM_RX_DESC)
 128                        port_info->rx_desc_cur = port_info->rx_desc_base;
 129        }
 130
 131        /* Restart the receiver if disabled */
 132        if (!(inl(EDRRR(port)) & EDRRR_R))
 133                outl(EDRRR_R, EDRRR(port));
 134
 135        return len;
 136}
 137
 138static int sh_eth_reset(struct sh_eth_dev *eth)
 139{
 140        int port = eth->port;
 141#if defined(CONFIG_CPU_SH7763)
 142        int ret = 0, i;
 143
 144        /* Start e-dmac transmitter and receiver */
 145        outl(EDSR_ENALL, EDSR(port));
 146
 147        /* Perform a software reset and wait for it to complete */
 148        outl(EDMR_SRST, EDMR(port));
 149        for (i = 0; i < TIMEOUT_CNT ; i++) {
 150                if (!(inl(EDMR(port)) & EDMR_SRST))
 151                        break;
 152                udelay(1000);
 153        }
 154
 155        if (i == TIMEOUT_CNT) {
 156                printf(SHETHER_NAME  ": Software reset timeout\n");
 157                ret = -EIO;
 158        }
 159
 160        return ret;
 161#else
 162        outl(inl(EDMR(port)) | EDMR_SRST, EDMR(port));
 163        udelay(3000);
 164        outl(inl(EDMR(port)) & ~EDMR_SRST, EDMR(port));
 165
 166        return 0;
 167#endif
 168}
 169
 170static int sh_eth_tx_desc_init(struct sh_eth_dev *eth)
 171{
 172        int port = eth->port, i, ret = 0;
 173        u32 tmp_addr;
 174        struct sh_eth_info *port_info = &eth->port_info[port];
 175        struct tx_desc_s *cur_tx_desc;
 176
 177        /*
 178         * Allocate tx descriptors. They must be TX_DESC_SIZE bytes aligned
 179         */
 180        port_info->tx_desc_malloc = malloc(NUM_TX_DESC *
 181                                                 sizeof(struct tx_desc_s) +
 182                                                 TX_DESC_SIZE - 1);
 183        if (!port_info->tx_desc_malloc) {
 184                printf(SHETHER_NAME ": malloc failed\n");
 185                ret = -ENOMEM;
 186                goto err;
 187        }
 188
 189        tmp_addr = (u32) (((int)port_info->tx_desc_malloc + TX_DESC_SIZE - 1) &
 190                          ~(TX_DESC_SIZE - 1));
 191        flush_cache_wback(tmp_addr, NUM_TX_DESC * sizeof(struct tx_desc_s));
 192        /* Make sure we use a P2 address (non-cacheable) */
 193        port_info->tx_desc_base = (struct tx_desc_s *)ADDR_TO_P2(tmp_addr);
 194        port_info->tx_desc_cur = port_info->tx_desc_base;
 195
 196        /* Initialize all descriptors */
 197        for (cur_tx_desc = port_info->tx_desc_base, i = 0; i < NUM_TX_DESC;
 198             cur_tx_desc++, i++) {
 199                cur_tx_desc->td0 = 0x00;
 200                cur_tx_desc->td1 = 0x00;
 201                cur_tx_desc->td2 = 0x00;
 202        }
 203
 204        /* Mark the end of the descriptors */
 205        cur_tx_desc--;
 206        cur_tx_desc->td0 |= TD_TDLE;
 207
 208        /* Point the controller to the tx descriptor list. Must use physical
 209           addresses */
 210        outl(ADDR_TO_PHY(port_info->tx_desc_base), TDLAR(port));
 211#if defined(CONFIG_CPU_SH7763)
 212        outl(ADDR_TO_PHY(port_info->tx_desc_base), TDFAR(port));
 213        outl(ADDR_TO_PHY(cur_tx_desc), TDFXR(port));
 214        outl(0x01, TDFFR(port));/* Last discriptor bit */
 215#endif
 216
 217err:
 218        return ret;
 219}
 220
 221static int sh_eth_rx_desc_init(struct sh_eth_dev *eth)
 222{
 223        int port = eth->port, i , ret = 0;
 224        struct sh_eth_info *port_info = &eth->port_info[port];
 225        struct rx_desc_s *cur_rx_desc;
 226        u32 tmp_addr;
 227        u8 *rx_buf;
 228
 229        /*
 230         * Allocate rx descriptors. They must be RX_DESC_SIZE bytes aligned
 231         */
 232        port_info->rx_desc_malloc = malloc(NUM_RX_DESC *
 233                                                 sizeof(struct rx_desc_s) +
 234                                                 RX_DESC_SIZE - 1);
 235        if (!port_info->rx_desc_malloc) {
 236                printf(SHETHER_NAME ": malloc failed\n");
 237                ret = -ENOMEM;
 238                goto err;
 239        }
 240
 241        tmp_addr = (u32) (((int)port_info->rx_desc_malloc + RX_DESC_SIZE - 1) &
 242                          ~(RX_DESC_SIZE - 1));
 243        flush_cache_wback(tmp_addr, NUM_RX_DESC * sizeof(struct rx_desc_s));
 244        /* Make sure we use a P2 address (non-cacheable) */
 245        port_info->rx_desc_base = (struct rx_desc_s *)ADDR_TO_P2(tmp_addr);
 246
 247        port_info->rx_desc_cur = port_info->rx_desc_base;
 248
 249        /*
 250         * Allocate rx data buffers. They must be 32 bytes aligned  and in
 251         * P2 area
 252         */
 253        port_info->rx_buf_malloc = malloc(NUM_RX_DESC * MAX_BUF_SIZE + 31);
 254        if (!port_info->rx_buf_malloc) {
 255                printf(SHETHER_NAME ": malloc failed\n");
 256                ret = -ENOMEM;
 257                goto err_buf_malloc;
 258        }
 259
 260        tmp_addr = (u32)(((int)port_info->rx_buf_malloc + (32 - 1)) &
 261                          ~(32 - 1));
 262        port_info->rx_buf_base = (u8 *)ADDR_TO_P2(tmp_addr);
 263
 264        /* Initialize all descriptors */
 265        for (cur_rx_desc = port_info->rx_desc_base,
 266             rx_buf = port_info->rx_buf_base, i = 0;
 267             i < NUM_RX_DESC; cur_rx_desc++, rx_buf += MAX_BUF_SIZE, i++) {
 268                cur_rx_desc->rd0 = RD_RACT;
 269                cur_rx_desc->rd1 = MAX_BUF_SIZE << 16;
 270                cur_rx_desc->rd2 = (u32) ADDR_TO_PHY(rx_buf);
 271        }
 272
 273        /* Mark the end of the descriptors */
 274        cur_rx_desc--;
 275        cur_rx_desc->rd0 |= RD_RDLE;
 276
 277        /* Point the controller to the rx descriptor list */
 278        outl(ADDR_TO_PHY(port_info->rx_desc_base), RDLAR(port));
 279#if defined(CONFIG_CPU_SH7763)
 280        outl(ADDR_TO_PHY(port_info->rx_desc_base), RDFAR(port));
 281        outl(ADDR_TO_PHY(cur_rx_desc), RDFXR(port));
 282        outl(RDFFR_RDLF, RDFFR(port));
 283#endif
 284
 285        return ret;
 286
 287err_buf_malloc:
 288        free(port_info->rx_desc_malloc);
 289        port_info->rx_desc_malloc = NULL;
 290
 291err:
 292        return ret;
 293}
 294
 295static void sh_eth_tx_desc_free(struct sh_eth_dev *eth)
 296{
 297        int port = eth->port;
 298        struct sh_eth_info *port_info = &eth->port_info[port];
 299
 300        if (port_info->tx_desc_malloc) {
 301                free(port_info->tx_desc_malloc);
 302                port_info->tx_desc_malloc = NULL;
 303        }
 304}
 305
 306static void sh_eth_rx_desc_free(struct sh_eth_dev *eth)
 307{
 308        int port = eth->port;
 309        struct sh_eth_info *port_info = &eth->port_info[port];
 310
 311        if (port_info->rx_desc_malloc) {
 312                free(port_info->rx_desc_malloc);
 313                port_info->rx_desc_malloc = NULL;
 314        }
 315
 316        if (port_info->rx_buf_malloc) {
 317                free(port_info->rx_buf_malloc);
 318                port_info->rx_buf_malloc = NULL;
 319        }
 320}
 321
 322static int sh_eth_desc_init(struct sh_eth_dev *eth)
 323{
 324        int ret = 0;
 325
 326        ret = sh_eth_tx_desc_init(eth);
 327        if (ret)
 328                goto err_tx_init;
 329
 330        ret = sh_eth_rx_desc_init(eth);
 331        if (ret)
 332                goto err_rx_init;
 333
 334        return ret;
 335err_rx_init:
 336        sh_eth_tx_desc_free(eth);
 337
 338err_tx_init:
 339        return ret;
 340}
 341
 342static int sh_eth_phy_config(struct sh_eth_dev *eth)
 343{
 344        int port = eth->port, ret = 0;
 345        struct sh_eth_info *port_info = &eth->port_info[port];
 346        struct eth_device *dev = port_info->dev;
 347        struct phy_device *phydev;
 348
 349        phydev = phy_connect(miiphy_get_dev_by_name(dev->name),
 350                        port_info->phy_addr, dev, PHY_INTERFACE_MODE_MII);
 351        port_info->phydev = phydev;
 352        phy_config(phydev);
 353
 354        return ret;
 355}
 356
 357static int sh_eth_config(struct sh_eth_dev *eth, bd_t *bd)
 358{
 359        int port = eth->port, ret = 0;
 360        u32 val;
 361        struct sh_eth_info *port_info = &eth->port_info[port];
 362        struct eth_device *dev = port_info->dev;
 363        struct phy_device *phy;
 364
 365        /* Configure e-dmac registers */
 366        outl((inl(EDMR(port)) & ~EMDR_DESC_R) | EDMR_EL, EDMR(port));
 367        outl(0, EESIPR(port));
 368        outl(0, TRSCER(port));
 369        outl(0, TFTR(port));
 370        outl((FIFO_SIZE_T | FIFO_SIZE_R), FDR(port));
 371        outl(RMCR_RST, RMCR(port));
 372#if !defined(CONFIG_CPU_SH7757) && !defined(CONFIG_CPU_SH7724)
 373        outl(0, RPADIR(port));
 374#endif
 375        outl((FIFO_F_D_RFF | FIFO_F_D_RFD), FCFTR(port));
 376
 377        /* Configure e-mac registers */
 378#if defined(CONFIG_CPU_SH7757)
 379        outl(ECSIPR_BRCRXIP | ECSIPR_PSRTOIP | ECSIPR_LCHNGIP |
 380                ECSIPR_MPDIP | ECSIPR_ICDIP, ECSIPR(port));
 381#else
 382        outl(0, ECSIPR(port));
 383#endif
 384
 385        /* Set Mac address */
 386        val = dev->enetaddr[0] << 24 | dev->enetaddr[1] << 16 |
 387            dev->enetaddr[2] << 8 | dev->enetaddr[3];
 388        outl(val, MAHR(port));
 389
 390        val = dev->enetaddr[4] << 8 | dev->enetaddr[5];
 391        outl(val, MALR(port));
 392
 393        outl(RFLR_RFL_MIN, RFLR(port));
 394#if !defined(CONFIG_CPU_SH7757) && !defined(CONFIG_CPU_SH7724)
 395        outl(0, PIPR(port));
 396#endif
 397#if !defined(CONFIG_CPU_SH7724)
 398        outl(APR_AP, APR(port));
 399        outl(MPR_MP, MPR(port));
 400#endif
 401#if defined(CONFIG_CPU_SH7763)
 402        outl(TPAUSER_TPAUSE, TPAUSER(port));
 403#elif defined(CONFIG_CPU_SH7757)
 404        outl(TPAUSER_UNLIMITED, TPAUSER(port));
 405#endif
 406
 407        /* Configure phy */
 408        ret = sh_eth_phy_config(eth);
 409        if (ret) {
 410                printf(SHETHER_NAME ": phy config timeout\n");
 411                goto err_phy_cfg;
 412        }
 413        phy = port_info->phydev;
 414        phy_startup(phy);
 415
 416        val = 0;
 417
 418        /* Set the transfer speed */
 419        if (phy->speed == 100) {
 420                printf(SHETHER_NAME ": 100Base/");
 421#ifdef CONFIG_CPU_SH7763
 422                outl(GECMR_100B, GECMR(port));
 423#elif defined(CONFIG_CPU_SH7757)
 424                outl(1, RTRATE(port));
 425#elif defined(CONFIG_CPU_SH7724)
 426                val = ECMR_RTM;
 427#endif
 428        } else if (phy->speed == 10) {
 429                printf(SHETHER_NAME ": 10Base/");
 430#ifdef CONFIG_CPU_SH7763
 431                outl(GECMR_10B, GECMR(port));
 432#elif defined(CONFIG_CPU_SH7757)
 433                outl(0, RTRATE(port));
 434#endif
 435        }
 436
 437        /* Check if full duplex mode is supported by the phy */
 438        if (phy->duplex) {
 439                printf("Full\n");
 440                outl(val | (ECMR_CHG_DM|ECMR_RE|ECMR_TE|ECMR_DM), ECMR(port));
 441        } else {
 442                printf("Half\n");
 443                outl(val | (ECMR_CHG_DM|ECMR_RE|ECMR_TE),  ECMR(port));
 444        }
 445
 446        return ret;
 447
 448err_phy_cfg:
 449        return ret;
 450}
 451
 452static void sh_eth_start(struct sh_eth_dev *eth)
 453{
 454        /*
 455         * Enable the e-dmac receiver only. The transmitter will be enabled when
 456         * we have something to transmit
 457         */
 458        outl(EDRRR_R, EDRRR(eth->port));
 459}
 460
 461static void sh_eth_stop(struct sh_eth_dev *eth)
 462{
 463        outl(~EDRRR_R, EDRRR(eth->port));
 464}
 465
 466int sh_eth_init(struct eth_device *dev, bd_t *bd)
 467{
 468        int ret = 0;
 469        struct sh_eth_dev *eth = dev->priv;
 470
 471        ret = sh_eth_reset(eth);
 472        if (ret)
 473                goto err;
 474
 475        ret = sh_eth_desc_init(eth);
 476        if (ret)
 477                goto err;
 478
 479        ret = sh_eth_config(eth, bd);
 480        if (ret)
 481                goto err_config;
 482
 483        sh_eth_start(eth);
 484
 485        return ret;
 486
 487err_config:
 488        sh_eth_tx_desc_free(eth);
 489        sh_eth_rx_desc_free(eth);
 490
 491err:
 492        return ret;
 493}
 494
 495void sh_eth_halt(struct eth_device *dev)
 496{
 497        struct sh_eth_dev *eth = dev->priv;
 498        sh_eth_stop(eth);
 499}
 500
 501int sh_eth_initialize(bd_t *bd)
 502{
 503    int ret = 0;
 504        struct sh_eth_dev *eth = NULL;
 505    struct eth_device *dev = NULL;
 506
 507    eth = (struct sh_eth_dev *)malloc(sizeof(struct sh_eth_dev));
 508        if (!eth) {
 509                printf(SHETHER_NAME ": %s: malloc failed\n", __func__);
 510                ret = -ENOMEM;
 511                goto err;
 512        }
 513
 514    dev = (struct eth_device *)malloc(sizeof(struct eth_device));
 515        if (!dev) {
 516                printf(SHETHER_NAME ": %s: malloc failed\n", __func__);
 517                ret = -ENOMEM;
 518                goto err;
 519        }
 520    memset(dev, 0, sizeof(struct eth_device));
 521    memset(eth, 0, sizeof(struct sh_eth_dev));
 522
 523        eth->port = CONFIG_SH_ETHER_USE_PORT;
 524        eth->port_info[eth->port].phy_addr = CONFIG_SH_ETHER_PHY_ADDR;
 525
 526    dev->priv = (void *)eth;
 527    dev->iobase = 0;
 528    dev->init = sh_eth_init;
 529    dev->halt = sh_eth_halt;
 530    dev->send = sh_eth_send;
 531    dev->recv = sh_eth_recv;
 532    eth->port_info[eth->port].dev = dev;
 533
 534        sprintf(dev->name, SHETHER_NAME);
 535
 536    /* Register Device to EtherNet subsystem  */
 537    eth_register(dev);
 538
 539        bb_miiphy_buses[0].priv = eth;
 540        miiphy_register(dev->name, bb_miiphy_read, bb_miiphy_write);
 541
 542        if (!eth_getenv_enetaddr("ethaddr", dev->enetaddr))
 543                puts("Please set MAC address\n");
 544
 545        return ret;
 546
 547err:
 548        if (dev)
 549                free(dev);
 550
 551        if (eth)
 552                free(eth);
 553
 554        printf(SHETHER_NAME ": Failed\n");
 555        return ret;
 556}
 557
 558/******* for bb_miiphy *******/
 559static int sh_eth_bb_init(struct bb_miiphy_bus *bus)
 560{
 561        return 0;
 562}
 563
 564static int sh_eth_bb_mdio_active(struct bb_miiphy_bus *bus)
 565{
 566        struct sh_eth_dev *eth = bus->priv;
 567        int port = eth->port;
 568
 569        outl(inl(PIR(port)) | PIR_MMD, PIR(port));
 570
 571        return 0;
 572}
 573
 574static int sh_eth_bb_mdio_tristate(struct bb_miiphy_bus *bus)
 575{
 576        struct sh_eth_dev *eth = bus->priv;
 577        int port = eth->port;
 578
 579        outl(inl(PIR(port)) & ~PIR_MMD, PIR(port));
 580
 581        return 0;
 582}
 583
 584static int sh_eth_bb_set_mdio(struct bb_miiphy_bus *bus, int v)
 585{
 586        struct sh_eth_dev *eth = bus->priv;
 587        int port = eth->port;
 588
 589        if (v)
 590                outl(inl(PIR(port)) | PIR_MDO, PIR(port));
 591        else
 592                outl(inl(PIR(port)) & ~PIR_MDO, PIR(port));
 593
 594        return 0;
 595}
 596
 597static int sh_eth_bb_get_mdio(struct bb_miiphy_bus *bus, int *v)
 598{
 599        struct sh_eth_dev *eth = bus->priv;
 600        int port = eth->port;
 601
 602        *v = (inl(PIR(port)) & PIR_MDI) >> 3;
 603
 604        return 0;
 605}
 606
 607static int sh_eth_bb_set_mdc(struct bb_miiphy_bus *bus, int v)
 608{
 609        struct sh_eth_dev *eth = bus->priv;
 610        int port = eth->port;
 611
 612        if (v)
 613                outl(inl(PIR(port)) | PIR_MDC, PIR(port));
 614        else
 615                outl(inl(PIR(port)) & ~PIR_MDC, PIR(port));
 616
 617        return 0;
 618}
 619
 620static int sh_eth_bb_delay(struct bb_miiphy_bus *bus)
 621{
 622        udelay(10);
 623
 624        return 0;
 625}
 626
 627struct bb_miiphy_bus bb_miiphy_buses[] = {
 628        {
 629                .name           = "sh_eth",
 630                .init           = sh_eth_bb_init,
 631                .mdio_active    = sh_eth_bb_mdio_active,
 632                .mdio_tristate  = sh_eth_bb_mdio_tristate,
 633                .set_mdio       = sh_eth_bb_set_mdio,
 634                .get_mdio       = sh_eth_bb_get_mdio,
 635                .set_mdc        = sh_eth_bb_set_mdc,
 636                .delay          = sh_eth_bb_delay,
 637        }
 638};
 639int bb_miiphy_buses_num = ARRAY_SIZE(bb_miiphy_buses);
 640