uboot/board/freescale/ls1088a/eth_ls1088aqds.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0+
   2/*
   3 * Copyright 2017 NXP
   4 */
   5
   6#include <common.h>
   7#include <command.h>
   8#include <env.h>
   9#include <log.h>
  10#include <net.h>
  11#include <netdev.h>
  12#include <asm/io.h>
  13#include <asm/arch/fsl_serdes.h>
  14#include <hwconfig.h>
  15#include <fsl_mdio.h>
  16#include <malloc.h>
  17#include <phy.h>
  18#include <fm_eth.h>
  19#include <i2c.h>
  20#include <miiphy.h>
  21#include <fsl-mc/fsl_mc.h>
  22#include <fsl-mc/ldpaa_wriop.h>
  23#include <linux/delay.h>
  24
  25#include "../common/qixis.h"
  26
  27#include "ls1088a_qixis.h"
  28
  29#ifndef CONFIG_DM_ETH
  30#ifdef CONFIG_FSL_MC_ENET
  31
  32#define SFP_TX          0
  33
  34 /* - In LS1088A A there are only 16 SERDES lanes, spread across 2 SERDES banks.
  35 *   Bank 1 -> Lanes A, B, C, D,
  36 *   Bank 2 -> Lanes A,B, C, D,
  37 */
  38
  39 /* Mapping of 8 SERDES lanes to LS1088A QDS board slots. A value of '0' here
  40  * means that the mapping must be determined dynamically, or that the lane
  41  * maps to something other than a board slot.
  42  */
  43
  44static u8 lane_to_slot_fsm1[] = {
  45        0, 0, 0, 0, 0, 0, 0, 0
  46};
  47
  48/* On the Vitesse VSC8234XHG SGMII riser card there are 4 SGMII PHYs
  49 * housed.
  50 */
  51
  52static int xqsgii_riser_phy_addr[] = {
  53        XQSGMII_CARD_PHY1_PORT0_ADDR,
  54        XQSGMII_CARD_PHY2_PORT0_ADDR,
  55        XQSGMII_CARD_PHY3_PORT0_ADDR,
  56        XQSGMII_CARD_PHY4_PORT0_ADDR,
  57        XQSGMII_CARD_PHY3_PORT2_ADDR,
  58        XQSGMII_CARD_PHY1_PORT2_ADDR,
  59        XQSGMII_CARD_PHY4_PORT2_ADDR,
  60        XQSGMII_CARD_PHY2_PORT2_ADDR,
  61};
  62
  63static int sgmii_riser_phy_addr[] = {
  64        SGMII_CARD_PORT1_PHY_ADDR,
  65        SGMII_CARD_PORT2_PHY_ADDR,
  66        SGMII_CARD_PORT3_PHY_ADDR,
  67        SGMII_CARD_PORT4_PHY_ADDR,
  68};
  69
  70/* Slot2 does not have EMI connections */
  71#define EMI_NONE        0xFF
  72#define EMI1_RGMII1     0
  73#define EMI1_RGMII2     1
  74#define EMI1_SLOT1      2
  75
  76static const char * const mdio_names[] = {
  77        "LS1088A_QDS_MDIO0",
  78        "LS1088A_QDS_MDIO1",
  79        "LS1088A_QDS_MDIO2",
  80        DEFAULT_WRIOP_MDIO2_NAME,
  81};
  82
  83struct ls1088a_qds_mdio {
  84        u8 muxval;
  85        struct mii_dev *realbus;
  86};
  87
  88struct reg_pair {
  89        uint addr;
  90        u8 *val;
  91};
  92
  93static void sgmii_configure_repeater(int dpmac)
  94{
  95        struct mii_dev *bus;
  96        uint8_t a = 0xf;
  97        int i, j, k, ret;
  98        unsigned short value;
  99        const char *dev = "LS1088A_QDS_MDIO2";
 100        int i2c_addr[] = {0x58, 0x59, 0x5a, 0x5b};
 101        int i2c_phy_addr = 0;
 102        int phy_addr = 0;
 103
 104        uint8_t ch_a_eq[] = {0x1, 0x2, 0x3, 0x7};
 105        uint8_t ch_a_ctl2[] = {0x81, 0x82, 0x83, 0x84};
 106        uint8_t ch_b_eq[] = {0x1, 0x2, 0x3, 0x7};
 107        uint8_t ch_b_ctl2[] = {0x81, 0x82, 0x83, 0x84};
 108
 109        u8 reg_val[6] = {0x18, 0x38, 0x4, 0x14, 0xb5, 0x20};
 110        struct reg_pair reg_pair[10] = {
 111                {6, &reg_val[0]}, {4, &reg_val[1]},
 112                {8, &reg_val[2]}, {0xf, NULL},
 113                {0x11, NULL}, {0x16, NULL},
 114                {0x18, NULL}, {0x23, &reg_val[3]},
 115                {0x2d, &reg_val[4]}, {4, &reg_val[5]},
 116        };
 117#if CONFIG_IS_ENABLED(DM_I2C)
 118        struct udevice *udev;
 119#endif
 120
 121        /* Set I2c to Slot 1 */
 122#if !CONFIG_IS_ENABLED(DM_I2C)
 123        ret = i2c_write(0x77, 0, 0, &a, 1);
 124#else
 125        ret = i2c_get_chip_for_busnum(0, 0x77, 1, &udev);
 126        if (!ret)
 127                ret = dm_i2c_write(udev, 0, &a, 1);
 128#endif
 129        if (ret)
 130                goto error;
 131
 132        switch (dpmac) {
 133        case 1:
 134                i2c_phy_addr = i2c_addr[1];
 135                phy_addr = 4;
 136                break;
 137        case 2:
 138                i2c_phy_addr = i2c_addr[0];
 139                phy_addr = 0;
 140                break;
 141        case 3:
 142                i2c_phy_addr = i2c_addr[3];
 143                phy_addr = 0xc;
 144                break;
 145        case 7:
 146                i2c_phy_addr = i2c_addr[2];
 147                phy_addr = 8;
 148                break;
 149        }
 150
 151        /* Check the PHY status */
 152        ret = miiphy_set_current_dev(dev);
 153        if (ret > 0)
 154                goto error;
 155
 156        bus = mdio_get_current_dev();
 157        debug("Reading from bus %s\n", bus->name);
 158
 159        ret = miiphy_write(dev, phy_addr, 0x1f, 3);
 160        if (ret > 0)
 161                goto error;
 162
 163        mdelay(10);
 164        ret = miiphy_read(dev, phy_addr, 0x11, &value);
 165        if (ret > 0)
 166                        goto error;
 167
 168        mdelay(10);
 169
 170        if ((value & 0xfff) == 0x401) {
 171                miiphy_write(dev, phy_addr, 0x1f, 0);
 172                printf("DPMAC %d:PHY is ..... Configured\n", dpmac);
 173                return;
 174        }
 175
 176#if CONFIG_IS_ENABLED(DM_I2C)
 177        i2c_get_chip_for_busnum(0, i2c_phy_addr, 1, &udev);
 178#endif
 179
 180        for (i = 0; i < 4; i++) {
 181                for (j = 0; j < 4; j++) {
 182                        reg_pair[3].val = &ch_a_eq[i];
 183                        reg_pair[4].val = &ch_a_ctl2[j];
 184                        reg_pair[5].val = &ch_b_eq[i];
 185                        reg_pair[6].val = &ch_b_ctl2[j];
 186                        for (k = 0; k < 10; k++) {
 187#if !CONFIG_IS_ENABLED(DM_I2C)
 188                                ret = i2c_write(i2c_phy_addr,
 189                                                reg_pair[k].addr,
 190                                                1, reg_pair[k].val, 1);
 191#else
 192                                ret = i2c_get_chip_for_busnum(0,
 193                                                              i2c_phy_addr,
 194                                                              1, &udev);
 195                                if (!ret)
 196                                        ret = dm_i2c_write(udev,
 197                                                           reg_pair[k].addr,
 198                                                           reg_pair[k].val, 1);
 199#endif
 200                                if (ret)
 201                                        goto error;
 202                        }
 203
 204                        mdelay(100);
 205                        ret = miiphy_read(dev, phy_addr, 0x11, &value);
 206                        if (ret > 0)
 207                                goto error;
 208
 209                        mdelay(100);
 210                        ret = miiphy_read(dev, phy_addr, 0x11, &value);
 211                        if (ret > 0)
 212                                goto error;
 213
 214                        if ((value & 0xfff) == 0x401) {
 215                                printf("DPMAC %d :PHY is configured ",
 216                                       dpmac);
 217                                printf("after setting repeater 0x%x\n",
 218                                       value);
 219                                i = 5;
 220                                j = 5;
 221                        } else {
 222                                printf("DPMAC %d :PHY is failed to ",
 223                                       dpmac);
 224                                printf("configure the repeater 0x%x\n", value);
 225                        }
 226                }
 227        }
 228        miiphy_write(dev, phy_addr, 0x1f, 0);
 229error:
 230        if (ret)
 231                printf("DPMAC %d ..... FAILED to configure PHY\n", dpmac);
 232        return;
 233}
 234
 235static void qsgmii_configure_repeater(int dpmac)
 236{
 237        uint8_t a = 0xf;
 238        int i, j, k;
 239        int i2c_phy_addr = 0;
 240        int phy_addr = 0;
 241        int i2c_addr[] = {0x58, 0x59, 0x5a, 0x5b};
 242
 243        uint8_t ch_a_eq[] = {0x1, 0x2, 0x3, 0x7};
 244        uint8_t ch_a_ctl2[] = {0x81, 0x82, 0x83, 0x84};
 245        uint8_t ch_b_eq[] = {0x1, 0x2, 0x3, 0x7};
 246        uint8_t ch_b_ctl2[] = {0x81, 0x82, 0x83, 0x84};
 247
 248        u8 reg_val[6] = {0x18, 0x38, 0x4, 0x14, 0xb5, 0x20};
 249        struct reg_pair reg_pair[10] = {
 250                {6, &reg_val[0]}, {4, &reg_val[1]},
 251                {8, &reg_val[2]}, {0xf, NULL},
 252                {0x11, NULL}, {0x16, NULL},
 253                {0x18, NULL}, {0x23, &reg_val[3]},
 254                {0x2d, &reg_val[4]}, {4, &reg_val[5]},
 255        };
 256
 257        const char *dev = mdio_names[EMI1_SLOT1];
 258        int ret = 0;
 259        unsigned short value;
 260#if CONFIG_IS_ENABLED(DM_I2C)
 261        struct udevice *udev;
 262#endif
 263
 264        /* Set I2c to Slot 1 */
 265#if !CONFIG_IS_ENABLED(DM_I2C)
 266        ret = i2c_write(0x77, 0, 0, &a, 1);
 267#else
 268        ret = i2c_get_chip_for_busnum(0, 0x77, 1, &udev);
 269        if (!ret)
 270                ret = dm_i2c_write(udev, 0, &a, 1);
 271#endif
 272        if (ret)
 273                goto error;
 274
 275        switch (dpmac) {
 276        case 7:
 277        case 8:
 278        case 9:
 279        case 10:
 280                i2c_phy_addr = i2c_addr[2];
 281                phy_addr = 8;
 282                break;
 283
 284        case 3:
 285        case 4:
 286        case 5:
 287        case 6:
 288                i2c_phy_addr = i2c_addr[3];
 289                phy_addr = 0xc;
 290                break;
 291        }
 292
 293        /* Check the PHY status */
 294        ret = miiphy_set_current_dev(dev);
 295        ret = miiphy_write(dev, phy_addr, 0x1f, 3);
 296        mdelay(10);
 297        ret = miiphy_read(dev, phy_addr, 0x11, &value);
 298        mdelay(10);
 299        ret = miiphy_read(dev, phy_addr, 0x11, &value);
 300        mdelay(10);
 301        if ((value & 0xf) == 0xf) {
 302                miiphy_write(dev, phy_addr, 0x1f, 0);
 303                printf("DPMAC %d :PHY is ..... Configured\n", dpmac);
 304                return;
 305        }
 306
 307#if CONFIG_IS_ENABLED(DM_I2C)
 308        i2c_get_chip_for_busnum(0, i2c_phy_addr, 1, &udev);
 309#endif
 310
 311        for (i = 0; i < 4; i++) {
 312                for (j = 0; j < 4; j++) {
 313                        reg_pair[3].val = &ch_a_eq[i];
 314                        reg_pair[4].val = &ch_a_ctl2[j];
 315                        reg_pair[5].val = &ch_b_eq[i];
 316                        reg_pair[6].val = &ch_b_ctl2[j];
 317
 318                        for (k = 0; k < 10; k++) {
 319#if !CONFIG_IS_ENABLED(DM_I2C)
 320                                ret = i2c_write(i2c_phy_addr,
 321                                                reg_pair[k].addr,
 322                                                1, reg_pair[k].val, 1);
 323#else
 324                                ret = i2c_get_chip_for_busnum(0,
 325                                                              i2c_addr[dpmac],
 326                                                              1, &udev);
 327                                if (!ret)
 328                                        ret = dm_i2c_write(udev,
 329                                                           reg_pair[k].addr,
 330                                                           reg_pair[k].val, 1);
 331#endif
 332                                if (ret)
 333                                        goto error;
 334                        }
 335
 336                        ret = miiphy_read(dev, phy_addr, 0x11, &value);
 337                        if (ret > 0)
 338                                goto error;
 339                        mdelay(1);
 340                        ret = miiphy_read(dev, phy_addr, 0x11, &value);
 341                        if (ret > 0)
 342                                goto error;
 343                        mdelay(10);
 344                        if ((value & 0xf) == 0xf) {
 345                                miiphy_write(dev, phy_addr, 0x1f, 0);
 346                                printf("DPMAC %d :PHY is ..... Configured\n",
 347                                       dpmac);
 348                                return;
 349                        }
 350                }
 351        }
 352error:
 353        printf("DPMAC %d :PHY ..... FAILED to configure PHY\n", dpmac);
 354        return;
 355}
 356
 357static const char *ls1088a_qds_mdio_name_for_muxval(u8 muxval)
 358{
 359        return mdio_names[muxval];
 360}
 361
 362struct mii_dev *mii_dev_for_muxval(u8 muxval)
 363{
 364        struct mii_dev *bus;
 365        const char *name = ls1088a_qds_mdio_name_for_muxval(muxval);
 366
 367        if (!name) {
 368                printf("No bus for muxval %x\n", muxval);
 369                return NULL;
 370        }
 371
 372        bus = miiphy_get_dev_by_name(name);
 373
 374        if (!bus) {
 375                printf("No bus by name %s\n", name);
 376                return NULL;
 377        }
 378
 379        return bus;
 380}
 381
 382static void ls1088a_qds_enable_SFP_TX(u8 muxval)
 383{
 384        u8 brdcfg9;
 385
 386        brdcfg9 = QIXIS_READ(brdcfg[9]);
 387        brdcfg9 &= ~BRDCFG9_SFPTX_MASK;
 388        brdcfg9 |= (muxval << BRDCFG9_SFPTX_SHIFT);
 389        QIXIS_WRITE(brdcfg[9], brdcfg9);
 390}
 391
 392static void ls1088a_qds_mux_mdio(u8 muxval)
 393{
 394        u8 brdcfg4;
 395
 396        if (muxval <= 5) {
 397                brdcfg4 = QIXIS_READ(brdcfg[4]);
 398                brdcfg4 &= ~BRDCFG4_EMISEL_MASK;
 399                brdcfg4 |= (muxval << BRDCFG4_EMISEL_SHIFT);
 400                QIXIS_WRITE(brdcfg[4], brdcfg4);
 401        }
 402}
 403
 404static int ls1088a_qds_mdio_read(struct mii_dev *bus, int addr,
 405                                 int devad, int regnum)
 406{
 407        struct ls1088a_qds_mdio *priv = bus->priv;
 408
 409        ls1088a_qds_mux_mdio(priv->muxval);
 410
 411        return priv->realbus->read(priv->realbus, addr, devad, regnum);
 412}
 413
 414static int ls1088a_qds_mdio_write(struct mii_dev *bus, int addr, int devad,
 415                                  int regnum, u16 value)
 416{
 417        struct ls1088a_qds_mdio *priv = bus->priv;
 418
 419        ls1088a_qds_mux_mdio(priv->muxval);
 420
 421        return priv->realbus->write(priv->realbus, addr, devad, regnum, value);
 422}
 423
 424static int ls1088a_qds_mdio_reset(struct mii_dev *bus)
 425{
 426        struct ls1088a_qds_mdio *priv = bus->priv;
 427
 428        return priv->realbus->reset(priv->realbus);
 429}
 430
 431static int ls1088a_qds_mdio_init(char *realbusname, u8 muxval)
 432{
 433        struct ls1088a_qds_mdio *pmdio;
 434        struct mii_dev *bus = mdio_alloc();
 435
 436        if (!bus) {
 437                printf("Failed to allocate ls1088a_qds MDIO bus\n");
 438                return -1;
 439        }
 440
 441        pmdio = malloc(sizeof(*pmdio));
 442        if (!pmdio) {
 443                printf("Failed to allocate ls1088a_qds private data\n");
 444                free(bus);
 445                return -1;
 446        }
 447
 448        bus->read = ls1088a_qds_mdio_read;
 449        bus->write = ls1088a_qds_mdio_write;
 450        bus->reset = ls1088a_qds_mdio_reset;
 451        sprintf(bus->name, ls1088a_qds_mdio_name_for_muxval(muxval));
 452
 453        pmdio->realbus = miiphy_get_dev_by_name(realbusname);
 454
 455        if (!pmdio->realbus) {
 456                printf("No bus with name %s\n", realbusname);
 457                free(bus);
 458                free(pmdio);
 459                return -1;
 460        }
 461
 462        pmdio->muxval = muxval;
 463        bus->priv = pmdio;
 464
 465        return mdio_register(bus);
 466}
 467
 468/*
 469 * Initialize the dpmac_info array.
 470 *
 471 */
 472static void initialize_dpmac_to_slot(void)
 473{
 474        struct ccsr_gur __iomem *gur = (void *)CONFIG_SYS_FSL_GUTS_ADDR;
 475        u32 serdes1_prtcl, cfg;
 476
 477        cfg = in_le32(&gur->rcwsr[FSL_CHASSIS3_SRDS1_REGSR - 1]) &
 478                                FSL_CHASSIS3_SRDS1_PRTCL_MASK;
 479        cfg >>= FSL_CHASSIS3_SRDS1_PRTCL_SHIFT;
 480        serdes1_prtcl = serdes_get_number(FSL_SRDS_1, cfg);
 481
 482        switch (serdes1_prtcl) {
 483        case 0x12:
 484                printf("qds: WRIOP: Supported SerDes1 Protocol 0x%02x\n",
 485                       serdes1_prtcl);
 486                lane_to_slot_fsm1[0] = EMI1_SLOT1 - 1;
 487                lane_to_slot_fsm1[1] = EMI1_SLOT1 - 1;
 488                lane_to_slot_fsm1[2] = EMI1_SLOT1 - 1;
 489                lane_to_slot_fsm1[3] = EMI1_SLOT1 - 1;
 490                break;
 491        case 0x15:
 492        case 0x1D:
 493                printf("qds: WRIOP: Supported SerDes1 Protocol 0x%02x\n",
 494                       serdes1_prtcl);
 495                lane_to_slot_fsm1[0] = EMI1_SLOT1 - 1;
 496                lane_to_slot_fsm1[1] = EMI1_SLOT1 - 1;
 497                lane_to_slot_fsm1[2] = EMI_NONE;
 498                lane_to_slot_fsm1[3] = EMI_NONE;
 499                break;
 500        case 0x1E:
 501                printf("qds: WRIOP: Supported SerDes1 Protocol 0x%02x\n",
 502                       serdes1_prtcl);
 503                lane_to_slot_fsm1[0] = EMI1_SLOT1 - 1;
 504                lane_to_slot_fsm1[1] = EMI1_SLOT1 - 1;
 505                lane_to_slot_fsm1[2] = EMI1_SLOT1 - 1;
 506                lane_to_slot_fsm1[3] = EMI_NONE;
 507                break;
 508        case 0x3A:
 509                printf("qds: WRIOP: Supported SerDes1 Protocol 0x%02x\n",
 510                       serdes1_prtcl);
 511                lane_to_slot_fsm1[0] = EMI1_SLOT1 - 1;
 512                lane_to_slot_fsm1[1] = EMI_NONE;
 513                lane_to_slot_fsm1[2] = EMI1_SLOT1 - 1;
 514                lane_to_slot_fsm1[3] = EMI1_SLOT1 - 1;
 515                break;
 516
 517        default:
 518                printf("%s qds: WRIOP: Unsupported SerDes1 Protocol 0x%02x\n",
 519                       __func__, serdes1_prtcl);
 520                break;
 521        }
 522}
 523
 524void ls1088a_handle_phy_interface_sgmii(int dpmac_id)
 525{
 526        struct mii_dev *bus;
 527        struct ccsr_gur __iomem *gur = (void *)CONFIG_SYS_FSL_GUTS_ADDR;
 528        u32 serdes1_prtcl, cfg;
 529
 530        cfg = in_le32(&gur->rcwsr[FSL_CHASSIS3_SRDS1_REGSR - 1]) &
 531                                FSL_CHASSIS3_SRDS1_PRTCL_MASK;
 532        cfg >>= FSL_CHASSIS3_SRDS1_PRTCL_SHIFT;
 533        serdes1_prtcl = serdes_get_number(FSL_SRDS_1, cfg);
 534
 535        int *riser_phy_addr;
 536        char *env_hwconfig = env_get("hwconfig");
 537
 538        if (hwconfig_f("xqsgmii", env_hwconfig))
 539                riser_phy_addr = &xqsgii_riser_phy_addr[0];
 540        else
 541                riser_phy_addr = &sgmii_riser_phy_addr[0];
 542
 543        switch (serdes1_prtcl) {
 544        case 0x12:
 545        case 0x15:
 546        case 0x1E:
 547        case 0x3A:
 548                switch (dpmac_id) {
 549                case 1:
 550                        wriop_set_phy_address(dpmac_id, 0, riser_phy_addr[1]);
 551                        break;
 552                case 2:
 553                        wriop_set_phy_address(dpmac_id, 0, riser_phy_addr[0]);
 554                        break;
 555                case 3:
 556                        wriop_set_phy_address(dpmac_id, 0, riser_phy_addr[3]);
 557                        break;
 558                case 7:
 559                        wriop_set_phy_address(dpmac_id, 0, riser_phy_addr[2]);
 560                        break;
 561                default:
 562                        printf("WRIOP: Wrong DPMAC%d set to SGMII", dpmac_id);
 563                        break;
 564                }
 565                break;
 566        default:
 567                printf("%s qds: WRIOP: Unsupported SerDes1 Protocol 0x%02x\n",
 568                       __func__, serdes1_prtcl);
 569                return;
 570        }
 571        dpmac_info[dpmac_id].board_mux = EMI1_SLOT1;
 572        bus = mii_dev_for_muxval(EMI1_SLOT1);
 573        wriop_set_mdio(dpmac_id, bus);
 574}
 575
 576void ls1088a_handle_phy_interface_qsgmii(int dpmac_id)
 577{
 578        struct mii_dev *bus;
 579        struct ccsr_gur __iomem *gur = (void *)CONFIG_SYS_FSL_GUTS_ADDR;
 580        u32 serdes1_prtcl, cfg;
 581
 582        cfg = in_le32(&gur->rcwsr[FSL_CHASSIS3_SRDS1_REGSR - 1]) &
 583                                FSL_CHASSIS3_SRDS1_PRTCL_MASK;
 584        cfg >>= FSL_CHASSIS3_SRDS1_PRTCL_SHIFT;
 585        serdes1_prtcl = serdes_get_number(FSL_SRDS_1, cfg);
 586
 587        switch (serdes1_prtcl) {
 588        case 0x1D:
 589        case 0x1E:
 590                switch (dpmac_id) {
 591                case 3:
 592                case 4:
 593                case 5:
 594                case 6:
 595                        wriop_set_phy_address(dpmac_id, 0, dpmac_id + 9);
 596                        break;
 597                case 7:
 598                case 8:
 599                case 9:
 600                case 10:
 601                        wriop_set_phy_address(dpmac_id, 0, dpmac_id + 1);
 602                        break;
 603                }
 604
 605                dpmac_info[dpmac_id].board_mux = EMI1_SLOT1;
 606                bus = mii_dev_for_muxval(EMI1_SLOT1);
 607                wriop_set_mdio(dpmac_id, bus);
 608                break;
 609        default:
 610                printf("qds: WRIOP: Unsupported SerDes Protocol 0x%02x\n",
 611                       serdes1_prtcl);
 612                break;
 613        }
 614}
 615
 616void ls1088a_handle_phy_interface_xsgmii(int i)
 617{
 618        struct ccsr_gur __iomem *gur = (void *)CONFIG_SYS_FSL_GUTS_ADDR;
 619        u32 serdes1_prtcl, cfg;
 620
 621        cfg = in_le32(&gur->rcwsr[FSL_CHASSIS3_SRDS1_REGSR - 1]) &
 622                                FSL_CHASSIS3_SRDS1_PRTCL_MASK;
 623        cfg >>= FSL_CHASSIS3_SRDS1_PRTCL_SHIFT;
 624        serdes1_prtcl = serdes_get_number(FSL_SRDS_1, cfg);
 625
 626        switch (serdes1_prtcl) {
 627        case 0x15:
 628        case 0x1D:
 629        case 0x1E:
 630                wriop_set_phy_address(i, 0, i + 26);
 631                ls1088a_qds_enable_SFP_TX(SFP_TX);
 632                break;
 633        default:
 634                printf("qds: WRIOP: Unsupported SerDes Protocol 0x%02x\n",
 635                       serdes1_prtcl);
 636                break;
 637        }
 638}
 639
 640static void ls1088a_handle_phy_interface_rgmii(int dpmac_id)
 641{
 642        struct ccsr_gur __iomem *gur = (void *)CONFIG_SYS_FSL_GUTS_ADDR;
 643        u32 serdes1_prtcl, cfg;
 644        struct mii_dev *bus;
 645
 646        cfg = in_le32(&gur->rcwsr[FSL_CHASSIS3_SRDS1_REGSR - 1]) &
 647                                FSL_CHASSIS3_SRDS1_PRTCL_MASK;
 648        cfg >>= FSL_CHASSIS3_SRDS1_PRTCL_SHIFT;
 649        serdes1_prtcl = serdes_get_number(FSL_SRDS_1, cfg);
 650
 651        switch (dpmac_id) {
 652        case 4:
 653                wriop_set_phy_address(dpmac_id, 0, RGMII_PHY1_ADDR);
 654                dpmac_info[dpmac_id].board_mux = EMI1_RGMII1;
 655                bus = mii_dev_for_muxval(EMI1_RGMII1);
 656                wriop_set_mdio(dpmac_id, bus);
 657                break;
 658        case 5:
 659                wriop_set_phy_address(dpmac_id, 0, RGMII_PHY2_ADDR);
 660                dpmac_info[dpmac_id].board_mux = EMI1_RGMII2;
 661                bus = mii_dev_for_muxval(EMI1_RGMII2);
 662                wriop_set_mdio(dpmac_id, bus);
 663                break;
 664        default:
 665                printf("qds: WRIOP: Unsupported RGMII SerDes Protocol 0x%02x\n",
 666                       serdes1_prtcl);
 667                break;
 668        }
 669}
 670#endif
 671
 672int board_eth_init(struct bd_info *bis)
 673{
 674        int error = 0, i;
 675#ifdef CONFIG_FSL_MC_ENET
 676        struct memac_mdio_info *memac_mdio0_info;
 677        char *env_hwconfig = env_get("hwconfig");
 678
 679        initialize_dpmac_to_slot();
 680
 681        memac_mdio0_info = (struct memac_mdio_info *)malloc(
 682                                        sizeof(struct memac_mdio_info));
 683        memac_mdio0_info->regs =
 684                (struct memac_mdio_controller *)
 685                                        CONFIG_SYS_FSL_WRIOP1_MDIO1;
 686        memac_mdio0_info->name = DEFAULT_WRIOP_MDIO1_NAME;
 687
 688        /* Register the real MDIO1 bus */
 689        fm_memac_mdio_init(bis, memac_mdio0_info);
 690        /* Register the muxing front-ends to the MDIO buses */
 691        ls1088a_qds_mdio_init(DEFAULT_WRIOP_MDIO1_NAME, EMI1_RGMII1);
 692        ls1088a_qds_mdio_init(DEFAULT_WRIOP_MDIO1_NAME, EMI1_RGMII2);
 693        ls1088a_qds_mdio_init(DEFAULT_WRIOP_MDIO1_NAME, EMI1_SLOT1);
 694
 695        for (i = WRIOP1_DPMAC1; i < NUM_WRIOP_PORTS; i++) {
 696                switch (wriop_get_enet_if(i)) {
 697                case PHY_INTERFACE_MODE_RGMII:
 698                case PHY_INTERFACE_MODE_RGMII_ID:
 699                        ls1088a_handle_phy_interface_rgmii(i);
 700                        break;
 701                case PHY_INTERFACE_MODE_QSGMII:
 702                        ls1088a_handle_phy_interface_qsgmii(i);
 703                        break;
 704                case PHY_INTERFACE_MODE_SGMII:
 705                        ls1088a_handle_phy_interface_sgmii(i);
 706                        break;
 707                case PHY_INTERFACE_MODE_XGMII:
 708                        ls1088a_handle_phy_interface_xsgmii(i);
 709                        break;
 710                default:
 711                        break;
 712
 713                if (i == 16)
 714                        i = NUM_WRIOP_PORTS;
 715                }
 716        }
 717
 718        error = cpu_eth_init(bis);
 719
 720        if (hwconfig_f("xqsgmii", env_hwconfig)) {
 721                for (i = WRIOP1_DPMAC1; i < NUM_WRIOP_PORTS; i++) {
 722                        switch (wriop_get_enet_if(i)) {
 723                        case PHY_INTERFACE_MODE_QSGMII:
 724                                qsgmii_configure_repeater(i);
 725                                break;
 726                        case PHY_INTERFACE_MODE_SGMII:
 727                                sgmii_configure_repeater(i);
 728                                break;
 729                        default:
 730                                break;
 731                        }
 732
 733                        if (i == 16)
 734                                i = NUM_WRIOP_PORTS;
 735                }
 736        }
 737#endif
 738        error = pci_eth_init(bis);
 739        return error;
 740}
 741#endif // !CONFIG_DM_ETH
 742
 743#if defined(CONFIG_RESET_PHY_R)
 744void reset_phy(void)
 745{
 746        mc_env_boot();
 747}
 748#endif /* CONFIG_RESET_PHY_R */
 749
 750#if defined(CONFIG_DM_ETH) && defined(CONFIG_MULTI_DTB_FIT)
 751
 752/* Structure to hold SERDES protocols supported in case of
 753 * CONFIG_DM_ETH enabled (network interfaces are described in the DTS).
 754 *
 755 * @serdes_block: the index of the SERDES block
 756 * @serdes_protocol: the decimal value of the protocol supported
 757 * @dts_needed: DTS notes describing the current configuration are needed
 758 *
 759 * When dts_needed is true, the board_fit_config_name_match() function
 760 * will try to exactly match the current configuration of the block with a DTS
 761 * name provided.
 762 */
 763static struct serdes_configuration {
 764        u8 serdes_block;
 765        u32 serdes_protocol;
 766        bool dts_needed;
 767} supported_protocols[] = {
 768        /* Serdes block #1 */
 769        {1, 21, true},
 770        {1, 29, true},
 771};
 772
 773#define SUPPORTED_SERDES_PROTOCOLS ARRAY_SIZE(supported_protocols)
 774
 775static bool protocol_supported(u8 serdes_block, u32 protocol)
 776{
 777        struct serdes_configuration serdes_conf;
 778        int i;
 779
 780        for (i = 0; i < SUPPORTED_SERDES_PROTOCOLS; i++) {
 781                serdes_conf = supported_protocols[i];
 782                if (serdes_conf.serdes_block == serdes_block &&
 783                    serdes_conf.serdes_protocol == protocol)
 784                        return true;
 785        }
 786
 787        return false;
 788}
 789
 790static void get_str_protocol(u8 serdes_block, u32 protocol, char *str)
 791{
 792        struct serdes_configuration serdes_conf;
 793        int i;
 794
 795        for (i = 0; i < SUPPORTED_SERDES_PROTOCOLS; i++) {
 796                serdes_conf = supported_protocols[i];
 797                if (serdes_conf.serdes_block == serdes_block &&
 798                    serdes_conf.serdes_protocol == protocol) {
 799                        if (serdes_conf.dts_needed == true)
 800                                sprintf(str, "%u", protocol);
 801                        else
 802                                sprintf(str, "x");
 803                        return;
 804                }
 805        }
 806}
 807
 808int board_fit_config_name_match(const char *name)
 809{
 810        struct ccsr_gur *gur = (void *)(CONFIG_SYS_FSL_GUTS_ADDR);
 811        char expected_dts[100];
 812        char srds_s1_str[2];
 813        u32 srds_s1, cfg;
 814
 815        cfg = in_le32(&gur->rcwsr[FSL_CHASSIS3_SRDS1_REGSR - 1]) &
 816                      FSL_CHASSIS3_SRDS1_PRTCL_MASK;
 817        cfg >>= FSL_CHASSIS3_SRDS1_PRTCL_SHIFT;
 818        srds_s1 = serdes_get_number(FSL_SRDS_1, cfg);
 819
 820        /* Check for supported protocols. The default DTS will be used
 821         * in this case
 822         */
 823        if (!protocol_supported(1, srds_s1))
 824                return -1;
 825
 826        get_str_protocol(1, srds_s1, srds_s1_str);
 827
 828        sprintf(expected_dts, "fsl-ls1088a-qds-%s-x", srds_s1_str);
 829
 830        if (!strcmp(name, expected_dts))
 831                return 0;
 832
 833        return -1;
 834}
 835#endif
 836