openbcm

Git mirror of https://github.com/Broadcom-Network-Switching-Software/OpenBCM
git clone git://git.finwo.net/mirror/broadcom/openbcm
Log | Files | Refs | README

phy84334.c (88453B)


      1 /* 
      2  * This license is set out in https://raw.githubusercontent.com/Broadcom-Network-Switching-Software/OpenBCM/master/Legal/LICENSE file.
      3  * 
      4  * Copyright 2007-2019 Broadcom Inc. All rights reserved.
      5  */
      6 
      7 /*
      8  * File:        phy84334.c
      9  * Purpose:     PHY driver for BCM84334 (MACSec)
     10  *
     11  * References:
     12  *     
     13  *    +----------+   +---------------------------+
     14  *    |  XAUI /  |   |            +->Copper      |<--> Magnetic
     15  *    |  SGMII   |<->| XAUI/SGMII-+              |
     16  *    | (SerDes) |   |            |              |
     17  *    |          |   |            +->SGMII/      |<--> (PHY)SFP (10/100/1000)
     18  *    +----------+   |               1000BASE-X/ |<--> 1000BASE-X SFP
     19  *        Switch     |               XAUI        |
     20  *                   |                           |
     21  *                   |                           |
     22  *                   +---------------------------+
     23  *                               84334
     24  *
     25  * Notes:
     26  */ 
     27 
     28 
     29 #include <sal/types.h>
     30 #include <sal/core/spl.h>
     31 #include <shared/bsl.h>
     32 #include <soc/drv.h>
     33 #include <soc/debug.h>
     34 #include <soc/error.h>
     35 #include <soc/phyreg.h>
     36 
     37 #include <soc/phy.h>
     38 #include <soc/phy/phyctrl.h>
     39 #include <soc/phy/drv.h>
     40 
     41 #include "phynull.h"
     42 #include "phyxehg.h"
     43 
     44 #include "phydefs.h"      /* Must include before other phy related includes */
     45 
     46 
     47 
     48 #ifdef INCLUDE_MACSEC
     49 #if defined(INCLUDE_PHY_84334)
     50 #include "phyconfig.h"    /* Must be the first phy include after phydefs.h */
     51 #include "phyident.h"
     52 #include "phyreg.h"
     53 #include "phyfege.h"
     54 #include "phy84334.h"
     55 #include <soc/macsecphy.h>
     56 
     57 #define AUTO_MDIX_WHEN_AN_DIS   0       /* Non-standard-compliant option */
     58 #define DISABLE_CLK125          0       /* Disable if unused to reduce */
     59                                         /*  EMI emissions */
     60 
     61 /* Move flag to mac_ctrl.c */
     62 #define MAC_CTRL_FLAG_MACSEC_XMAC_V2  (1<<1)
     63 
     64 /* typedefs */
     65 typedef struct {
     66     int           flags;
     67     soc_timeout_t to;
     68     uint8         *firmware;
     69     int           firmware_len;
     70     unsigned int  iter;
     71     int           phy_ext_boot;
     72     int           fiber_preferred;
     73 } PHY8433_PRIV_t;
     74 
     75 #define FLAGS(_pc) (((PHY8433_PRIV_t *)((_pc) + 1))->flags)
     76 #define ITER(_pc) (((PHY8433_PRIV_t *)((_pc) + 1))->iter)
     77 #define PHY_EXT_BOOT(_pc) (((PHY8433_PRIV_t *)((_pc) + 1))->phy_ext_boot)
     78 #define FIBER_PREF(_pc) (((PHY8433_PRIV_t *)((_pc) + 1))->fiber_preferred)
     79 #define TO(_pc) (((PHY8433_PRIV_t *)((_pc) + 1))->to)
     80 #define FIRMWARE(_pc) (((PHY8433_PRIV_t *)((_pc) + 1))->firmware)
     81 #define FIRMWARE_LEN(_pc) (((PHY8433_PRIV_t *)((_pc) + 1))->firmware_len)
     82 
     83 extern buint8_t bcm84334_firmware[];
     84 extern buint32_t bcm84334_firmware_length;
     85 
     86 #define BMACSEC_PHY84334_MAP_UCODE_OFFSET(x)\
     87 ((x) == PHYCTRL_UCODE_BCST_SETUP     ? BMACSEC_PHY84334_UCODE_BCST_SETUP   :\
     88 ((x) == PHYCTRL_UCODE_BCST_uC_SETUP  ? BMACSEC_PHY84334_UCODE_BCST_uC_SETUP:\
     89 ((x) == PHYCTRL_UCODE_BCST_ENABLE    ? BMACSEC_PHY84334_UCODE_BCST_ENABLE  :\
     90 ((x) == PHYCTRL_UCODE_BCST_LOAD      ? BMACSEC_PHY84334_UCODE_BCST_LOAD   :\
     91                                        BMACSEC_PHY84334_UCODE_BCST_END  ))))
     92 
     93 
     94 
     95 
     96 
     97 static bmacsec_error_t error_tbl[] = {
     98                                 SOC_E_NONE,
     99                                 SOC_E_INTERNAL,
    100                                 SOC_E_MEMORY,
    101                                 SOC_E_PARAM,
    102                                 SOC_E_EMPTY,
    103                                 SOC_E_FULL,
    104                                 SOC_E_NOT_FOUND,
    105                                 SOC_E_EXISTS,
    106                                 SOC_E_TIMEOUT,
    107                                 SOC_E_FAIL,
    108                                 SOC_E_DISABLED,
    109                                 SOC_E_BADID,
    110                                 SOC_E_RESOURCE,
    111                                 SOC_E_CONFIG,
    112                                 SOC_E_UNAVAIL,
    113                                 SOC_E_INIT,
    114                                 SOC_E_PORT,
    115                             };
    116 /*
    117  * Convert BMACSEC return codes to SOC return code.
    118  */
    119 #define SOC_ERROR(e)    error_tbl[(-e)]
    120 
    121 #define PHY84334_REG_READ(_unit, _phy_ctrl, _addr, _val) \
    122             READ_PHY_REG((_unit), (_phy_ctrl), (_addr), (_val))
    123 
    124 #define READ_PHY84334_PMA_PMD_REG(_unit, _phy_ctrl, _reg,_val) \
    125             PHY84334_REG_READ((_unit), (_phy_ctrl), \
    126               SOC_PHY_CLAUSE45_ADDR(1, (_reg)), (_val))
    127 
    128 #define MACSEC_READ_PHY_REG(_unit, _pc, _mdio, _reg, _value)     \
    129             ((_pc->read)((_unit), (_mdio), (_reg), (_value)))
    130 #define MACSEC_WRITE_PHY_REG(_unit, _pc, _mdio, _reg, _value)     \
    131             ((_pc->write)((_unit), (_mdio), (_reg), (_value)))
    132 
    133 
    134 STATIC int _phy_84334_medium_change(int unit, soc_port_t port, 
    135                           int force_update, soc_port_medium_t force_medium);
    136 STATIC int phy_84334_duplex_set(int unit, soc_port_t port, int duplex);
    137 STATIC int phy_84334_speed_set(int unit, soc_port_t port, int speed);
    138 STATIC int phy_84334_master_set(int unit, soc_port_t port, int master);
    139 STATIC int phy_84334_autoneg_set(int unit, soc_port_t port, int autoneg);
    140 STATIC int phy_84334_mdix_set(int unit, soc_port_t port, soc_port_mdix_t mode);
    141 STATIC int phy_84334_speed_get(int unit, soc_port_t port, int *speed);
    142 STATIC int phy_84334_ability_advert_set(int unit, soc_port_t port, soc_port_ability_t *ability);
    143 STATIC int phy_84334_ability_local_get(int unit, soc_port_t port,soc_port_ability_t *ability);
    144 STATIC int phy_84334_linkup(int unit, soc_port_t port);
    145 int phy_84334_reset(int unit, soc_port_t port, void *user_arg);
    146 
    147 
    148 
    149 /***********************************************************************
    150  *
    151  * HELPER FUNCTIONS
    152  */
    153 /*
    154  * Function:
    155  *      _phy_84334_medium_check
    156  * Purpose:
    157  *      Determine if chip should operate in copper or fiber mode.
    158  * Parameters:
    159  *      unit - StrataSwitch unit #.
    160  *      port - StrataSwitch port #.
    161  *      medium - (OUT) SOC_PORT_MEDIUM_XXX
    162  * Returns:
    163  *      SOC_E_XXX
    164  */
    165 STATIC int
    166 _phy_84334_medium_check(int unit, soc_port_t port, int *medium)
    167 {
    168     phy_ctrl_t    *pc = EXT_PHY_SW_STATE(unit, port);
    169     int rv;
    170     bmacsec_dev_addr_t phy_dev_addr;
    171     bmacsec_phy84334_port_medium_t bmacsec_port_medium;
    172 
    173     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
    174 
    175     rv = bmacsec_phy84334_medium_check(phy_dev_addr, &bmacsec_port_medium); 
    176     if(!BMACSEC_E_SUCCESS(rv)) {
    177         return SOC_E_FAIL;
    178     }
    179 
    180     *medium = SOC_PORT_MEDIUM_COPPER;
    181 
    182     if (pc->automedium) {
    183         if (pc->fiber.preferred) {
    184             if (bmacsec_port_medium == BMACSEC_PHY_MEDIUM_COPPER) {
    185                 /* Only Copper is lined up */
    186                 *medium = SOC_PORT_MEDIUM_COPPER;
    187             } else {
    188                 *medium = SOC_PORT_MEDIUM_FIBER;
    189             }
    190         } else {
    191             if (bmacsec_port_medium == BMACSEC_PHY_MEDIUM_FIBER) {
    192                 /* Only Fiber is linked up */
    193                 *medium = SOC_PORT_MEDIUM_FIBER;
    194             } else {
    195                 *medium = SOC_PORT_MEDIUM_COPPER;
    196             }
    197         }
    198     } else {
    199        *medium = pc->fiber.preferred ? SOC_PORT_MEDIUM_FIBER:
    200                   SOC_PORT_MEDIUM_COPPER; 
    201     }
    202 
    203     LOG_VERBOSE(BSL_LS_SOC_PHY,
    204                 (BSL_META_U(unit,
    205                             "_phy_84334_medium_check: "
    206                             "u=%d p=%d fiber_pref=%d fiber=%d\n"),
    207                  unit, port, pc->fiber.preferred,
    208                  (*medium == SOC_PORT_MEDIUM_FIBER) ? 1 : 0));
    209 
    210     return SOC_E_NONE;
    211 }
    212 
    213 /*
    214  * Function:
    215  *      phy_84334_medium_status
    216  * Purpose:
    217  *      Indicate the current active medium
    218  * Parameters:
    219  *      unit - StrataSwitch unit #.
    220  *      port - StrataSwitch port #.
    221  *      medium - (OUT) One of:
    222  *              SOC_PORT_MEDIUM_COPPER
    223  *              SOC_PORT_MEDIUM_FIBER
    224  * Returns:
    225  *      SOC_E_NONE
    226  */
    227 
    228 STATIC int
    229 phy_84334_medium_status(int unit, soc_port_t port, soc_port_medium_t *medium)
    230 {
    231     if (PHY_COPPER_MODE(unit, port)) {
    232         *medium = SOC_PORT_MEDIUM_COPPER;
    233     } else {
    234         *medium = SOC_PORT_MEDIUM_FIBER;
    235     }
    236     return SOC_E_NONE;
    237 }
    238 
    239 /*
    240  * Function:
    241  *      _phy_84334_medium_config_update
    242  * Purpose:
    243  *      Update the PHY with config parameters
    244  * Parameters:
    245  *      unit - StrataSwitch unit #.
    246  *      port - StrataSwitch port #.
    247  *      cfg - Config structure.
    248  * Returns:
    249  *      SOC_E_XXX
    250  */
    251 
    252 STATIC int
    253 _phy_84334_medium_config_update(int unit, soc_port_t port,
    254                                 soc_phy_config_t *cfg)
    255 {
    256     SOC_IF_ERROR_RETURN
    257         (phy_84334_speed_set(unit, port, cfg->force_speed));
    258     SOC_IF_ERROR_RETURN
    259         (phy_84334_duplex_set(unit, port, cfg->force_duplex));
    260     SOC_IF_ERROR_RETURN
    261         (phy_84334_master_set(unit, port, cfg->master));
    262     SOC_IF_ERROR_RETURN
    263         (phy_84334_ability_advert_set(unit, port, &cfg->advert_ability));
    264     SOC_IF_ERROR_RETURN
    265         (phy_84334_autoneg_set(unit, port, cfg->autoneg_enable));
    266     SOC_IF_ERROR_RETURN
    267         (phy_84334_mdix_set(unit, port, cfg->mdix));
    268 
    269     return SOC_E_NONE;
    270 }
    271 
    272 /***********************************************************************
    273  *
    274  * PHY84334 DRIVER ROUTINES
    275  */
    276 
    277 /*
    278  * Function:
    279  *      phy_84334_medium_config_set
    280  * Purpose:
    281  *      Set the operating parameters that are automatically selected
    282  *      when medium switches type.
    283  * Parameters:
    284  *      unit - StrataSwitch unit #
    285  *      port - Port number
    286  *      medium - SOC_PORT_MEDIUM_COPPER/FIBER
    287  *      cfg - Operating parameters
    288  * Returns:
    289  *      SOC_E_XXX
    290  */
    291 
    292 STATIC int
    293 phy_84334_medium_config_set(int unit, soc_port_t port, 
    294                            soc_port_medium_t  medium,
    295                            soc_phy_config_t  *cfg)
    296 {
    297     phy_ctrl_t    *pc;
    298     soc_phy_config_t *active_medium;  /* Currently active medium */
    299     soc_phy_config_t *change_medium;  /* Requested medium */
    300     soc_phy_config_t *other_medium;   /* The other medium */
    301     int               medium_update;
    302     int               rv;
    303     bmacsec_dev_addr_t phy_dev_addr;
    304 
    305     if (NULL == cfg) {
    306         return SOC_E_PARAM;
    307     }
    308 
    309     pc            = EXT_PHY_SW_STATE(unit, port);
    310     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
    311     medium_update = FALSE;
    312 
    313    switch (medium) {
    314     case SOC_PORT_MEDIUM_COPPER:
    315         if (!pc->automedium && !PHY_COPPER_MODE(unit, port)) {
    316             return SOC_E_UNAVAIL;
    317         }
    318         change_medium  = &pc->copper;
    319         other_medium   = &pc->fiber;
    320         break;
    321     case SOC_PORT_MEDIUM_FIBER:
    322         if (!pc->automedium && !PHY_FIBER_MODE(unit, port)) {
    323             return SOC_E_UNAVAIL;
    324         }
    325         change_medium  = &pc->fiber;
    326         other_medium   = &pc->copper;
    327         break;
    328     default:
    329         return SOC_E_PARAM;
    330     }
    331 
    332     /*
    333      * Changes take effect immediately if the target medium is active or
    334      * the preferred medium changes.
    335      */
    336     if (change_medium->enable != cfg->enable) {
    337         medium_update = TRUE;
    338     }
    339     if (change_medium->preferred != cfg->preferred) {
    340         /* Make sure that only one medium is preferred */
    341         other_medium->preferred = !cfg->preferred;
    342         medium_update = TRUE;
    343     }
    344 
    345     sal_memcpy(change_medium, cfg, sizeof(*change_medium));
    346 
    347     rv = bmacsec_phy84334_port_priority_set(phy_dev_addr, pc->fiber.preferred ? BMACSEC_PHY_MEDIUM_FIBER : BMACSEC_PHY_MEDIUM_COPPER);
    348 
    349     if(!BMACSEC_E_SUCCESS(rv)) {
    350         return SOC_E_FAIL;
    351     }
    352 
    353     if (medium_update) {
    354         /* The new configuration may cause medium change. Check
    355          * and update medium.
    356          */
    357         SOC_IF_ERROR_RETURN
    358             (_phy_84334_medium_change(unit, port, TRUE, medium));
    359     } else {
    360         active_medium = (PHY_COPPER_MODE(unit, port)) ?  
    361                             &pc->copper : &pc->fiber;
    362         if (active_medium == change_medium) {
    363             /* If the medium to update is active, update the configuration */
    364             SOC_IF_ERROR_RETURN
    365                 (_phy_84334_medium_config_update(unit, port, change_medium));
    366         }
    367     }
    368     return SOC_E_NONE;
    369 }
    370 
    371 /*
    372  * Function:
    373  *      phy_84334_medium_config_get
    374  * Purpose:
    375  *      Get the operating parameters that are automatically selected
    376  *      when medium switches type.
    377  * Parameters:
    378  *      unit - StrataSwitch unit #
    379  *      port - Port number
    380  *      medium - SOC_PORT_MEDIUM_COPPER/FIBER
    381  *      cfg - (OUT) Operating parameters
    382  * Returns:
    383  *      SOC_E_XXX
    384  */
    385 
    386 STATIC int
    387 phy_84334_medium_config_get(int unit, soc_port_t port, 
    388                            soc_port_medium_t medium,
    389                            soc_phy_config_t *cfg)
    390 {
    391     int            rv;
    392     phy_ctrl_t    *pc;
    393 
    394     pc = EXT_PHY_SW_STATE(unit, port);
    395     rv = SOC_E_NONE;
    396 
    397     switch (medium) {
    398     case SOC_PORT_MEDIUM_COPPER:
    399         if (pc->automedium || PHY_COPPER_MODE(unit, port)) {
    400             sal_memcpy(cfg, &pc->copper, sizeof (*cfg));
    401         } else {
    402             rv = SOC_E_UNAVAIL;
    403         }
    404         break;
    405     case SOC_PORT_MEDIUM_FIBER:
    406         if (pc->automedium || PHY_FIBER_MODE(unit, port)) {
    407             sal_memcpy(cfg, &pc->fiber, sizeof (*cfg));
    408         } else {
    409             rv = SOC_E_UNAVAIL;
    410         }
    411         break;
    412     default:
    413         rv = SOC_E_PARAM;
    414         break;
    415     }
    416 
    417     return rv;
    418 }
    419 
    420 #if 0
    421 /*
    422  * Function:
    423  *      _phy_84334_no_reset_setup
    424  * Purpose:
    425  *      Setup the operating parameters of the PHY without resetting PHY
    426  * Parameters:
    427  *      unit - StrataSwitch unit #
    428  *      port - Port number
    429  * Returns:
    430  *      SOC_E_XXX
    431  */
    432 
    433 STATIC int
    434 _phy_84334_no_reset_setup(int unit, soc_port_t port, int fiber)
    435 {
    436     phy_ctrl_t    *int_pc;
    437     phy_ctrl_t    *pc;
    438     bmacsec_dev_addr_t phy_dev_addr;
    439     int rv = SOC_E_NONE;
    440     int fiber_capable = 0;
    441 
    442     LOG_INFO(BSL_LS_SOC_PHY,
    443              (BSL_META_U(unit,
    444                          "_phy_84334_reset_setup: u=%d p=%d medium=%s\n"),
    445                          unit, port,
    446               PHY_COPPER_MODE(unit, port) ? "COPPER" : "FIBER"));
    447 
    448     pc      = EXT_PHY_SW_STATE(unit, port);
    449     int_pc  = INT_PHY_SW_STATE(unit, port);
    450 
    451     if (NULL != int_pc) {
    452         SOC_IF_ERROR_RETURN
    453             (PHY_INIT(int_pc->pd, unit, port));
    454 
    455         if (PHY_FIBER_MODE(unit, port)) {
    456            /* Interface to MAC or internal SerDes is always SGMII mode.
    457             * Typical internal SerDes driver set the interface to 1000BASE-X,
    458             * if the media is fiber. Therefore, we need to force the interface 
    459             * of internal SerDes Driver to SGMII. */
    460            SOC_IF_ERROR_RETURN
    461                (PHY_NOTIFY(int_pc->pd, unit, port, phyEventInterface,
    462                            SOC_PORT_IF_SGMII));
    463         } 
    464 
    465         if (PHY_COPPER_MODE(unit, port) && 
    466             !PHY_SGMII_AUTONEG_MODE(unit, port)) {
    467             /* Make sure internal SerDes is in power down state 
    468              * until the MAC is ready. */
    469             SOC_IF_ERROR_RETURN
    470                 (PHY_NOTIFY(int_pc->pd, unit, port, 
    471                             phyEventStop, PHY_STOP_COPPER));
    472         }
    473     }
    474  
    475     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
    476     rv = bmacsec_phy84334_init(phy_dev_addr, 0,
    477                                pc->automedium,
    478                                fiber,
    479                                pc->fiber_detect,
    480                                pc->macsec_enable,
    481                                &fiber_capable, 1, NULL);
    482    if (rv != BMACSEC_E_NONE) {
    483        return SOC_E_FAIL;
    484    }
    485    return SOC_E_NONE;
    486 }
    487 #endif
    488 
    489 /*
    490  * Function:
    491  *      phy_84334_init
    492  * Purpose:
    493  *      Init function for 84334 PHY.
    494  * Parameters:
    495  *      unit - StrataSwitch unit #.
    496  *      port - StrataSwitch port #.
    497  * Returns:
    498  *      SOC_E_NONE
    499  */
    500 
    501 STATIC int
    502 phy_84334_init(int unit, soc_port_t port)
    503 {
    504     phy_ctrl_t *pc;
    505     int        fiber_capable, rv;
    506     int        fiber_preferred;
    507     bmacsec_dev_addr_t  phy_dev_addr;
    508     int         mmi_mdio_addr, port_index, macsec_enable, phy_ext_boot;
    509     uint32      phy_mdi_pair_map;
    510     int         status;
    511     uint32      mac_config_flag = 0;
    512     uint16      temp1, temp2, saved_phy_addr;
    513 
    514     LOG_INFO(BSL_LS_SOC_PHY,
    515              (BSL_META_U(unit,
    516                          "phy_84334_init: u=%d p=%d\n"),
    517                          unit, port));
    518 
    519     pc = EXT_PHY_SW_STATE(unit, port);
    520 
    521   if (PHYCTRL_INIT_STATE(pc) == PHYCTRL_INIT_STATE_DEFAULT ||
    522       PHYCTRL_INIT_STATE(pc) == PHYCTRL_INIT_STATE_PASS1   ) {
    523 
    524     PHY_FLAGS_SET(unit, port, PHY_FLAGS_C45);
    525     rv = BMACSEC_E_NONE;
    526 
    527     pc->interface = SOC_PORT_IF_XGMII;
    528 
    529 
    530     mmi_mdio_addr = soc_property_port_get(unit, port, spn_MACSEC_DEV_ADDR, -1);
    531     phy_ext_boot = soc_property_port_get(unit, port,
    532                                             spn_PHY_EXT_ROM_BOOT, 1);
    533     PHY_EXT_BOOT(pc) = phy_ext_boot;
    534 
    535     if (mmi_mdio_addr == -1) {
    536         LOG_WARN(BSL_LS_SOC_PHY,
    537                  (BSL_META_U(unit,
    538                              "phy_84334_init: "
    539                              "MACSEC_DEV_ADDR property "
    540                              "not configured for u=%d p=%d\n"), unit, port));
    541         return SOC_E_CONFIG;
    542     }
    543 
    544     port_index = soc_property_port_get(unit, port, spn_MACSEC_PORT_INDEX, -1);
    545     if (port_index == -1) {
    546         LOG_WARN(BSL_LS_SOC_PHY,
    547                  (BSL_META_U(unit,
    548                              "phy_84334_init: "
    549                              "MACSEC_PORT_INDEX property not configured for "
    550                              "u=%d p=%d\n"), unit, port));
    551         return SOC_E_CONFIG;
    552     }
    553 
    554     pc->macsec_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, mmi_mdio_addr, 1);
    555     pc->macsec_dev_port = port_index;
    556 
    557     phy_dev_addr    = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
    558 
    559     macsec_enable = soc_property_port_get(unit, port, spn_MACSEC_ENABLE, 0);
    560     pc->macsec_enable = macsec_enable;
    561 
    562     switch (PHY_MODEL(pc->phy_id0, pc->phy_id1)) {
    563         case PHY_BCM84844_MODEL:
    564         case PHY_BCM84846_MODEL:
    565         case PHY_BCM84848_MODEL:
    566             mac_config_flag |= MAC_CTRL_FLAG_MACSEC_XMAC_V2;
    567             break;
    568         default:
    569             mac_config_flag = 0;
    570             break;
    571     }
    572 
    573     rv = bmacsec_phy84334_phy_mac_addr_set(phy_dev_addr, pc->macsec_dev_addr, 
    574                                    pc->macsec_dev_port,
    575                                    bmacsec_io_mmi1_cl45_10gbt,
    576                                    mac_config_flag );
    577 
    578     if(rv != BMACSEC_E_NONE) {
    579         LOG_WARN(BSL_LS_SOC_PHY,
    580                  (BSL_META_U(unit,
    581                              "phy_84334_init: bmacsec_phy_mac_addr_set "
    582                              "returned error for u=%d p=%d\n"), unit, port));
    583         return SOC_E_FAIL;
    584     }
    585 
    586     fiber_capable = 1;
    587 
    588     fiber_preferred =
    589         soc_property_port_get(unit, port, spn_PHY_FIBER_PREF, 0);
    590 
    591     FIBER_PREF(pc) = fiber_preferred;
    592 
    593     /*
    594     pc->automedium =
    595         soc_property_port_get(unit, port, spn_PHY_AUTOMEDIUM, 1);
    596      */
    597     pc->automedium = TRUE;
    598 
    599     pc->fiber_detect =
    600         soc_property_port_get(unit, port, spn_PHY_FIBER_DETECT, 0);
    601 
    602     LOG_INFO(BSL_LS_SOC_PHY,
    603              (BSL_META_U(unit,
    604                          "phy_84334_init: "
    605                          "u=%d p=%d type=84334%s automedium=%d fiber_pref=%d detect=%d\n"),
    606               unit, port, fiber_capable ? "S" : "",
    607               pc->automedium, fiber_preferred, pc->fiber_detect));
    608 
    609     ITER(pc) = 0 ;
    610     soc_timeout_init(&TO(pc), 0, 0);
    611     if (PHYCTRL_INIT_STATE(pc) == PHYCTRL_INIT_STATE_PASS1) {
    612         /* indicate second pass of init is needed */
    613         PHYCTRL_INIT_STATE_SET(pc,PHYCTRL_INIT_STATE_PASS2);
    614     }
    615 
    616 #ifdef PHY84334_FIRMWARE_INIT_CHECK
    617     /* prepare for download(init check) */
    618     rv = bmacsec_phy84334_init_check(phy_dev_addr, &status);
    619     if(rv != BMACSEC_E_NONE) {
    620         LOG_WARN(BSL_LS_SOC_PHY,
    621                  (BSL_META_U(unit,
    622                              "phy_84334_init: bmacsec_phy84334_init_check "
    623                              "returned error %d for u=%d p=%d\n"), rv, unit, port));
    624         return SOC_E_FAIL;
    625     }
    626 
    627     if (!phy_ext_boot && status != BMACSEC_PHY84334_INIT_UCODE_ACTIVE) {
    628 #else
    629     if (!phy_ext_boot) {
    630 #endif
    631 
    632         /* read ID registers for address zero of the MDIO bus */
    633         saved_phy_addr = pc->phy_id;
    634         pc->phy_id &= ~0x1f;
    635 
    636         SOC_IF_ERROR_RETURN
    637             (READ_PHY84334_PMA_PMD_REG(unit, pc, 0x2, &temp1));
    638         SOC_IF_ERROR_RETURN
    639             (READ_PHY84334_PMA_PMD_REG(unit, pc, 0x3, &temp2));
    640 
    641         pc->phy_id = saved_phy_addr;
    642 
    643         if(temp1 != 0xffff) {
    644             if((temp1 != pc->phy_id0) || (temp2 != pc->phy_id1)) {
    645                 LOG_WARN(BSL_LS_SOC_PHY,
    646                          (BSL_META_U(unit,
    647                                      "Another PHY already exist on same broadcast MDIO address. Doing unicast\n")));
    648 
    649                 if (PHYCTRL_INIT_STATE(pc) == PHYCTRL_INIT_STATE_DEFAULT) {
    650                     goto  skip_bcst;
    651                 } else {
    652                     return SOC_E_NONE;
    653                 }
    654             }
    655         }
    656 
    657 
    658 
    659         /* do MDIO download steps */
    660         ITER(pc) = 1 ;
    661         FIRMWARE(pc) = bcm84334_firmware ;
    662         FIRMWARE_LEN(pc) = bcm84334_firmware_length ;
    663         pc->flags |= PHYCTRL_MDIO_BCST;
    664         switch (PHY_MODEL(pc->phy_id0, pc->phy_id1)) {
    665             case PHY_BCM84844_MODEL:
    666             case PHY_BCM84846_MODEL:
    667             case PHY_BCM84848_MODEL:
    668                 pc->dev_name = "BCM8484X" ;
    669                 break;
    670             default:
    671                 pc->dev_name = "BCM8433X" ;
    672                 break;
    673         }
    674 
    675         soc_timeout_init(&TO(pc), 60000000, 0);
    676         /* indicate second pass of init is needed */
    677         PHYCTRL_INIT_STATE_SET(pc,PHYCTRL_INIT_STATE_PASS2);
    678 
    679         /* reset port */
    680         rv = bmacsec_phy84334_reset_no_wait(phy_dev_addr);
    681         if(rv != BMACSEC_E_NONE) {
    682             LOG_WARN(BSL_LS_SOC_PHY,
    683                      (BSL_META_U(unit,
    684                                  "phy_84334_init: bmacsec_phy84334_reset_no_wait "
    685                                  "returned error %d for u=%d p=%d\n"), rv, unit, port));
    686             return SOC_E_FAIL;
    687         }
    688 
    689         return SOC_E_NONE;
    690     }
    691   } 
    692 
    693 skip_bcst:
    694 
    695     phy_dev_addr    = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
    696     phy_ext_boot    = PHY_EXT_BOOT(pc);
    697     fiber_preferred = FIBER_PREF(pc);
    698 
    699   if ((PHYCTRL_INIT_STATE(pc) == PHYCTRL_INIT_STATE_PASS2) ||
    700       (PHYCTRL_INIT_STATE(pc) == PHYCTRL_INIT_STATE_DEFAULT)) {
    701 
    702     do {
    703     /* Init PHYS and MACs to defaults */
    704     rv = bmacsec_phy84334_init(phy_dev_addr, 1,
    705                                pc->automedium,
    706                                fiber_preferred,
    707                                pc->fiber_detect,
    708                                pc->macsec_enable,
    709                                &fiber_capable, phy_ext_boot, 
    710                                ITER(pc) == 0 ? NULL : &ITER(pc) );
    711 
    712         if (rv != BMACSEC_E_NONE || ITER(pc) == 0) {
    713             break;
    714         }
    715 
    716     } while (!soc_timeout_check(&TO(pc)));
    717 
    718     if (rv != BMACSEC_E_NONE) {
    719         return SOC_E_FAIL;
    720     }
    721 
    722     if (ITER(pc) != 0) {
    723         return SOC_E_TIMEOUT;
    724     }
    725 
    726     if (PHYCTRL_INIT_STATE(pc) == PHYCTRL_INIT_STATE_PASS2) {
    727         /* indicate second pass of init is needed */
    728         PHYCTRL_INIT_STATE_SET(pc,PHYCTRL_INIT_STATE_PASS3);
    729         soc_timeout_init(&TO(pc), 700000, 0);
    730         return SOC_E_NONE;
    731     }
    732   }
    733 
    734   if ((PHYCTRL_INIT_STATE(pc) == PHYCTRL_INIT_STATE_PASS3) ||
    735       (PHYCTRL_INIT_STATE(pc) == PHYCTRL_INIT_STATE_DEFAULT)) {
    736 
    737 #if 1
    738     while (!soc_timeout_check(&TO(pc))) {
    739         rv = bmacsec_phy84334_handshake_status(phy_dev_addr, &status);
    740         if(rv != BMACSEC_E_NONE) {
    741             return SOC_E_FAIL;
    742         }
    743         if(status == BMACSEC_PHY84334_HS_STATUS_DONE) {
    744             break;
    745         }
    746     }
    747 #endif
    748 
    749     /* software controlled medium selection is not available yet */
    750     pc->copper.enable         = TRUE;
    751     pc->copper.force_duplex    = TRUE;
    752     pc->copper.force_speed    = 10000;
    753     pc->copper.autoneg_enable = TRUE;
    754     pc->copper.master = SOC_PORT_MS_AUTO;
    755     pc->copper.mdix = SOC_PORT_MDIX_AUTO;
    756     pc->copper.preferred = !fiber_preferred;
    757 
    758     pc->fiber.enable          = TRUE;
    759     pc->fiber.force_speed     = 10000;
    760     pc->fiber.force_duplex    = TRUE;
    761     pc->fiber.autoneg_enable = FALSE;
    762     pc->fiber.preferred = fiber_preferred;
    763 
    764 
    765     /* Initially configure for the preferred medium. */
    766     PHY_FLAGS_SET(unit, port, PHY_FLAGS_COPPER);
    767     PHY_FLAGS_CLR(unit, port, PHY_FLAGS_FIBER);
    768     PHY_FLAGS_CLR(unit, port, PHY_FLAGS_PASSTHRU);
    769     PHY_FLAGS_CLR(unit, port, PHY_FLAGS_100FX);
    770 
    771     /*
    772      * Some reasonable defaults
    773      */
    774     pc->macsec_switch_fixed = 0;
    775     pc->macsec_switch_fixed_speed = 10000;
    776     pc->macsec_switch_fixed_duplex = 1;
    777     pc->macsec_switch_fixed_pause = 1;
    778     pc->macsec_pause_rx_fwd = 0;
    779     pc->macsec_pause_tx_fwd = 0;
    780     pc->macsec_line_ipg = 0xc;
    781     pc->macsec_switch_ipg = 0xc;
    782 
    783     /* Check config for MDI PAIR */
    784     phy_mdi_pair_map = soc_property_port_get(unit, port,
    785                                             spn_PHY_MDI_PAIR_MAP, 0);
    786     if (phy_mdi_pair_map) {
    787         rv = bmacsec_phy84334_phy_mdi_pair_set(phy_dev_addr, phy_mdi_pair_map);
    788 
    789         if(rv != BMACSEC_E_NONE) {
    790             LOG_WARN(BSL_LS_SOC_PHY,
    791                      (BSL_META_U(unit,
    792                                  "phy_84334_init: bmacsec_phy84334_phy_mdi_pair_set "
    793                                  "returned error %d for u=%d p=%d\n"), rv, unit, port));
    794             return SOC_E_FAIL;
    795         }
    796     }
    797 
    798     /* Set Local Advertising Configuration */
    799     SOC_IF_ERROR_RETURN
    800         (phy_84334_ability_local_get(unit, port, &pc->copper.advert_ability));
    801 
    802     SOC_IF_ERROR_RETURN
    803         (phy_84334_ability_advert_set(unit, port, &pc->copper.advert_ability));
    804 
    805 
    806 #ifdef PHY84334_FIBER_1G_SUPPORT  /* Need to Revist this */
    807     if (!(PHY_FLAGS_TST(unit, port, PHY_FLAGS_FORCED_COPPER)) &&
    808           pc->fiber.preferred                                 &&
    809           pc->automedium  ){
    810         int            medium;
    811 
    812         /* Try 1G Fiber */
    813         pc->fiber.force_speed     = 1000;
    814         SOC_IF_ERROR_RETURN
    815             (_phy_84334_medium_change(unit, port, TRUE,
    816                                       SOC_PORT_MEDIUM_FIBER ));
    817 
    818         
    819         /* Wait to check if 1G Fiber is up */
    820         sal_usleep(400000);
    821 
    822         SOC_IF_ERROR_RETURN
    823             (_phy_84334_medium_check(unit, port, &medium));
    824 
    825         pc->fiber.force_speed     = 10000;
    826         if (medium != SOC_PORT_MEDIUM_FIBER) {
    827             /* Did not detect 1G Fiber - Try 10G Fiber */
    828             SOC_IF_ERROR_RETURN
    829                 (_phy_84334_medium_change(unit, port, TRUE,
    830                                           SOC_PORT_MEDIUM_FIBER ));
    831             /* Wait to check if 10G Fiber is up */
    832             sal_usleep(400000);
    833         }
    834     }
    835 #endif
    836 
    837     if (pc->macsec_enable) {
    838         switch (PHY_MODEL(pc->phy_id0, pc->phy_id1)) {
    839             case PHY_BCM84844_MODEL:
    840             case PHY_BCM84846_MODEL:
    841             case PHY_BCM84848_MODEL:
    842                 rv = soc_macsecphy_init(unit, port, pc,
    843                     BMACSEC_CORE_BCM8484X, bmacsec_io_mmi1_cl45_10gbt);
    844                 break;
    845             default:
    846                 rv = soc_macsecphy_init(unit, port, pc,
    847                     BMACSEC_CORE_BCM8483X, bmacsec_io_mmi1_cl45_10gbt);
    848                 break;
    849         }
    850         if (!SOC_SUCCESS(rv)) {
    851         LOG_ERROR(BSL_LS_SOC_PHY,
    852                   (BSL_META_U(unit,
    853                               "soc_macsecphy_init: MACSEC init for"
    854                               " u=%d p=%d FAILED "), unit, port));
    855         } else {
    856         LOG_INFO(BSL_LS_SOC_PHY,
    857                  (BSL_META_U(unit,
    858                              "soc_macsecphy_init: MACSEC init for"
    859                              " u=%d p=%d SUCCESS "), unit, port));
    860         }
    861     }
    862   }
    863     return SOC_E_NONE;
    864 }
    865 
    866 
    867 /*
    868  * Function: 	
    869  *	phy_84334_reset
    870  * Purpose:	
    871  *	Reset PHY and wait for it to come out of reset.
    872  * Parameters:
    873  *	unit - StrataSwitch unit #.
    874  *	port - StrataSwitch port #. 
    875  * Returns:	
    876  *	SOC_E_XXX
    877  */
    878 
    879 int
    880 phy_84334_reset(int unit, soc_port_t port, void *user_arg)
    881 {
    882 
    883     int rv;
    884     phy_ctrl_t    *pc;
    885     bmacsec_dev_addr_t phy_dev_addr;
    886 
    887     pc = EXT_PHY_SW_STATE(unit, port);
    888 
    889     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
    890     rv = bmacsec_phy84334_reset(phy_dev_addr);
    891 
    892     return (SOC_ERROR(rv));
    893 }
    894 
    895 /*
    896  * Function:
    897  *      phy_84334_enable_set
    898  * Purpose:
    899  *      Enable or disable the physical interface.
    900  * Parameters:
    901  *      unit - StrataSwitch unit #.
    902  *      port - StrataSwitch port #.
    903  *      enable - Boolean, true = enable PHY, false = disable.
    904  * Returns:
    905  *      SOC_E_XXX
    906  */
    907 
    908 STATIC int
    909 phy_84334_enable_set(int unit, soc_port_t port, int enable)
    910 {
    911     phy_ctrl_t    *pc;
    912     int rv = SOC_E_NONE;
    913     bmacsec_dev_addr_t phy_dev_addr;
    914     bmacsec_phy84334_port_mode_t port_mode = 0;
    915 
    916     pc     = EXT_PHY_SW_STATE(unit, port);
    917 
    918     if(PHY_COPPER_MODE(unit, port)) {
    919         port_mode = BMACSEC_PHY_COPPER;
    920     } else {
    921         port_mode = BMACSEC_PHY_FIBER;
    922     }
    923     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
    924     rv = bmacsec_phy84334_enable_set(phy_dev_addr, pc->automedium,
    925                                      port_mode, enable);
    926     if(rv != BMACSEC_E_NONE) {
    927         return SOC_E_FAIL;
    928     }
    929 
    930     if (pc->automedium || PHY_FIBER_MODE(unit, port)) {
    931         phy_ctrl_t  *int_pc;
    932 
    933         int_pc = INT_PHY_SW_STATE(unit, port);
    934         if (NULL != int_pc) {
    935             SOC_IF_ERROR_RETURN
    936                 (PHY_ENABLE_SET(int_pc->pd, unit, port, enable));
    937         }
    938     
    939         LOG_INFO(BSL_LS_SOC_PHY,
    940                  (BSL_META_U(unit,
    941                              "phy_84334_enable_set: "
    942                              "Power %s fiber medium\n"), (enable) ? "up" : "down"));
    943     }
    944 
    945     /* Update software state */
    946     SOC_IF_ERROR_RETURN(phy_fe_ge_enable_set(unit, port, enable));
    947 
    948     return SOC_E_NONE;
    949 }
    950 
    951 /*
    952  * Function:
    953  *      phy_84334_enable_get
    954  * Purpose:
    955  *      Enable or disable the physical interface for a 84334 device.
    956  * Parameters:
    957  *      unit - StrataSwitch unit #.
    958  *      port - StrataSwitch port #.
    959  *      enable - (OUT) Boolean, true = enable PHY, false = disable.
    960  * Returns:
    961  *      SOC_E_XXX
    962  */
    963 
    964 STATIC int
    965 phy_84334_enable_get(int unit, soc_port_t port, int *enable)
    966 {
    967     return phy_fe_ge_enable_get(unit, port, enable);
    968 }
    969 
    970 /*
    971  * Function:
    972  *      _phy_84334_medium_change
    973  * Purpose:
    974  *      Change medium when media change detected or forced
    975  * Parameters:
    976  *      unit         - StrataSwitch unit #.
    977  *      port         - StrataSwitch port #.
    978  *      force_update - Force update
    979  *      force_medium - Force update medium
    980  * Returns:
    981  *      SOC_E_XXX
    982  */
    983 STATIC int
    984 _phy_84334_medium_change(int unit, soc_port_t port, int force_update,
    985                          soc_port_medium_t force_medium)
    986 {
    987     phy_ctrl_t    *pc;
    988     int            medium = SOC_PORT_MEDIUM_COPPER;
    989     bmacsec_dev_addr_t phy_dev_addr;
    990     int            rv;
    991 
    992     pc    = EXT_PHY_SW_STATE(unit, port);
    993     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
    994 
    995     if (force_update == TRUE) {
    996         medium = force_medium;
    997     } else {
    998         SOC_IF_ERROR_RETURN
    999             (_phy_84334_medium_check(unit, port, &medium));
   1000     }
   1001 
   1002     if (medium == SOC_PORT_MEDIUM_COPPER) {
   1003         if (!PHY_COPPER_MODE(unit, port) || force_update) { /* Was fiber */ 
   1004             PHY_FLAGS_SET(unit, port, PHY_FLAGS_COPPER);
   1005             PHY_FLAGS_CLR(unit, port, PHY_FLAGS_FIBER);
   1006             PHY_FLAGS_CLR(unit, port, PHY_FLAGS_100FX);
   1007             PHY_FLAGS_SET(unit, port, PHY_FLAGS_MEDIUM_CHANGE);
   1008             rv = bmacsec_phy84334_port_mode_set(phy_dev_addr, BMACSEC_PHY_COPPER);
   1009             if (!BMACSEC_E_SUCCESS(rv)) {
   1010                 return SOC_E_FAIL;
   1011             }
   1012 
   1013             /* Do Not power up the interface if medium is disabled */
   1014             if (pc->copper.enable) {
   1015                 SOC_IF_ERROR_RETURN
   1016                     (_phy_84334_medium_config_update(unit, port, &pc->copper));
   1017             }
   1018             LOG_INFO(BSL_LS_SOC_PHY,
   1019                      (BSL_META_U(unit,
   1020                                  "_phy_84334_link_auto_detect: u=%d p=%d [F->C]\n"),
   1021                       unit, port));
   1022         }
   1023     } else {        /* Fiber */
   1024         if (PHY_COPPER_MODE(unit, port) || force_update) { /* Was copper */
   1025             PHY_FLAGS_CLR(unit, port, PHY_FLAGS_COPPER);
   1026             PHY_FLAGS_SET(unit, port, PHY_FLAGS_FIBER);
   1027             PHY_FLAGS_SET(unit, port, PHY_FLAGS_MEDIUM_CHANGE);
   1028             rv = bmacsec_phy84334_port_mode_set(phy_dev_addr, BMACSEC_PHY_FIBER);
   1029             if (!BMACSEC_E_SUCCESS(rv)) {
   1030                 return SOC_E_FAIL;
   1031             }
   1032 
   1033             /* Do Not power up the interface if medium is disabled */
   1034             if (pc->fiber.enable) {
   1035                 SOC_IF_ERROR_RETURN
   1036                     (_phy_84334_medium_config_update(unit, port, &pc->fiber));
   1037             }
   1038             LOG_INFO(BSL_LS_SOC_PHY,
   1039                      (BSL_META_U(unit,
   1040                                  "_phy_84334_link_auto_detect: u=%d p=%d [C->F]\n"),
   1041                       unit, port));
   1042         }
   1043     }
   1044 
   1045     return SOC_E_NONE;
   1046 }
   1047 
   1048 /*
   1049  * Function:
   1050  *      phy_84334_link_get
   1051  * Purpose:
   1052  *      Determine the current link up/down status for a 84334 device.
   1053  * Parameters:
   1054  *      unit - StrataSwitch unit #.
   1055  *      port - StrataSwitch port #.
   1056  *      link - (OUT) Boolean, true indicates link established.
   1057  * Returns:
   1058  *      SOC_E_XXX
   1059  * Notes:
   1060  *      If using automedium, also switches the mode.
   1061  */
   1062 STATIC int
   1063 phy_84334_link_get(int unit, soc_port_t port, int *link)
   1064 {
   1065     phy_ctrl_t    *pc;
   1066     uint16         data; 
   1067     int rv = SOC_E_NONE;
   1068     bmacsec_phy84334_port_mode_t port_mode = 0;
   1069     bmacsec_dev_addr_t phy_dev_addr;
   1070     int bmacsec_link;
   1071 
   1072 
   1073     pc    = EXT_PHY_SW_STATE(unit, port);
   1074     *link = FALSE;      /* Default return */
   1075 
   1076     if (PHY_FLAGS_TST(unit, port, PHY_FLAGS_DISABLE)) {
   1077         return SOC_E_NONE;
   1078     }
   1079 
   1080     if (!pc->fiber.enable && !pc->copper.enable) {
   1081         return SOC_E_NONE;
   1082     }
   1083 
   1084     PHY_FLAGS_CLR(unit, port, PHY_FLAGS_MEDIUM_CHANGE);
   1085     if (pc->automedium) {
   1086         /* Check for medium change and update HW/SW accordingly. */
   1087         SOC_IF_ERROR_RETURN
   1088             (_phy_84334_medium_change(unit, port, FALSE, 0));
   1089     }
   1090 
   1091     if(PHY_COPPER_MODE(unit, port)) {
   1092         port_mode = BMACSEC_PHY_COPPER;
   1093     } else {
   1094         port_mode = BMACSEC_PHY_FIBER;
   1095     }
   1096     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   1097     rv = bmacsec_phy84334_link_get(phy_dev_addr, port_mode, &bmacsec_link);
   1098     if (!BMACSEC_E_SUCCESS(rv)) {
   1099         return SOC_E_FAIL;
   1100     }
   1101     if (bmacsec_link == 1) {
   1102         *link = TRUE;
   1103     } else {
   1104         *link = FALSE;
   1105     }
   1106 
   1107     /* If preferred medium is up, disable the other medium 
   1108      * to prevent false link. */
   1109     if (pc->automedium) {
   1110         if (pc->copper.preferred) {
   1111 #if 0 /* Revisit this after implementing enable set for FIBER/COPPER */
   1112             if (pc->fiber.enable) {
   1113                 /* Power down Serdes if Copper mode is up */
   1114                 data = (*link && PHY_COPPER_MODE(unit, port)) ? 0 : 1;
   1115             } else {
   1116                 data = 0;
   1117 
   1118             }
   1119             port_mode = BMACSEC_PHY_FIBER;
   1120             (void)bmacsec_phy84334_enable_set(phy_dev_addr, pc->automedium,
   1121                                                  port_mode, data);
   1122 #endif
   1123         } else {  /* pc->fiber.preferred */
   1124             if (pc->copper.enable) {
   1125                 data = (*link && PHY_FIBER_MODE(unit, port)) ? 0 : 1;
   1126             } else {
   1127                 data = 0;
   1128             }
   1129             port_mode = BMACSEC_PHY_COPPER;
   1130             (void)bmacsec_phy84334_enable_set(phy_dev_addr, pc->automedium,
   1131                                              port_mode, data);
   1132         }
   1133     }
   1134 
   1135     LOG_VERBOSE(BSL_LS_SOC_PHY,
   1136                 (BSL_META_U(unit,
   1137                             "phy_84334_link_get: u=%d p=%d mode=%s%s link=%d\n"),
   1138                  unit, port,
   1139                  PHY_COPPER_MODE(unit, port) ? "C" : "F",
   1140                  PHY_FIBER_100FX_MODE(unit, port)? "(100FX)" : "",
   1141                  *link));
   1142 
   1143     return SOC_E_NONE;
   1144 }
   1145 
   1146 
   1147 /*
   1148  * Function:
   1149  *      phy_84334_duplex_set
   1150  * Purpose:
   1151  *      Set the current duplex mode (forced).
   1152  * Parameters:
   1153  *      unit - StrataSwitch unit #.
   1154  *      port - StrataSwitch port #.
   1155  *      duplex - Boolean, true indicates full duplex, false indicates half.
   1156  * Returns:
   1157  *      SOC_E_NONE
   1158  *      SOC_E_UNAVAIL - Half duplex requested, and not supported.
   1159  * Notes:
   1160  *      The duplex is set only for the ACTIVE medium.
   1161  *      No synchronization performed at this level.
   1162  *      Autonegotiation is not manipulated.
   1163  */
   1164 
   1165 STATIC int
   1166 phy_84334_duplex_set(int unit, soc_port_t port, int duplex)
   1167 {
   1168     int                          rv;
   1169     phy_ctrl_t                   *pc;
   1170     bmacsec_phy84334_port_mode_t port_mode = 0;
   1171     bmacsec_dev_addr_t phy_dev_addr;
   1172     bmacsec_phy84334_duplex_t bmacsec_duplex;
   1173 
   1174     pc = EXT_PHY_SW_STATE(unit, port);
   1175     rv = SOC_E_NONE;
   1176 
   1177     if(PHY_COPPER_MODE(unit, port)) {
   1178         port_mode = BMACSEC_PHY_COPPER;
   1179     } else {
   1180         port_mode = BMACSEC_PHY_FIBER;
   1181         if (duplex == 0) {
   1182             return SOC_E_UNAVAIL;
   1183         }
   1184     }
   1185     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   1186     if (duplex) {
   1187         bmacsec_duplex = BMACSEC_PHY84334_FULL_DUPLEX;
   1188     } else {
   1189         bmacsec_duplex = BMACSEC_PHY84334_HALF_DUPLEX;
   1190     }
   1191     rv = bmacsec_phy84334_duplex_set(phy_dev_addr, port_mode, 
   1192                                      bmacsec_duplex);
   1193 
   1194     if(BMACSEC_E_SUCCESS(rv)) {
   1195         pc->copper.force_duplex = duplex;
   1196     }
   1197 
   1198     LOG_INFO(BSL_LS_SOC_PHY,
   1199              (BSL_META_U(unit,
   1200                          "phy_84334_duplex_set: u=%d p=%d d=%d rv=%d\n"),
   1201               unit, port, duplex, rv));
   1202     return (SOC_ERROR(rv));
   1203 }
   1204 
   1205 /*
   1206  * Function:
   1207  *      phy_84334_duplex_get
   1208  * Purpose:
   1209  *      Get the current operating duplex mode. If autoneg is enabled,
   1210  *      then operating mode is returned, otherwise forced mode is returned.
   1211  * Parameters:
   1212  *      unit - StrataSwitch unit #.
   1213  *      port - StrataSwitch port #.
   1214  *      duplex - (OUT) Boolean, true indicates full duplex, false
   1215  *              indicates half.
   1216  * Returns:
   1217  *      SOC_E_NONE
   1218  * Notes:
   1219  *      The duplex is retrieved for the ACTIVE medium.
   1220  *      No synchronization performed at this level. Autonegotiation is
   1221  *      not manipulated.
   1222  */
   1223 
   1224 STATIC int
   1225 phy_84334_duplex_get(int unit, soc_port_t port, int *duplex)
   1226 {
   1227 
   1228     int rv = SOC_E_NONE;
   1229     bmacsec_phy84334_port_mode_t port_mode = 0;
   1230     phy_ctrl_t                   *pc;
   1231     bmacsec_dev_addr_t phy_dev_addr;
   1232     bmacsec_phy84334_duplex_t bmacsec_duplex;
   1233 
   1234     pc = EXT_PHY_SW_STATE(unit, port);
   1235 
   1236     if(PHY_COPPER_MODE(unit, port)) {
   1237         port_mode = BMACSEC_PHY_COPPER;
   1238     } else {
   1239         port_mode = BMACSEC_PHY_FIBER;
   1240         *duplex = TRUE;
   1241         return SOC_E_NONE;
   1242     }
   1243     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   1244     rv = bmacsec_phy84334_duplex_get(phy_dev_addr, port_mode, 
   1245                                      &bmacsec_duplex);
   1246     if (rv != BMACSEC_E_NONE) {
   1247         return SOC_E_FAIL;
   1248     }
   1249     if (bmacsec_duplex == BMACSEC_PHY84334_FULL_DUPLEX) {
   1250         *duplex = TRUE;
   1251     } else {
   1252         *duplex = FALSE;
   1253     }
   1254 
   1255     return SOC_E_NONE;
   1256 }
   1257 
   1258 /*
   1259  * Function:
   1260  *      phy_84334_speed_set
   1261  * Purpose:
   1262  *      Set the current operating speed (forced).
   1263  * Parameters:
   1264  *      unit - StrataSwitch unit #.
   1265  *      port - StrataSwitch port #.
   1266  *      speed - Requested speed, only 1000 supported.
   1267  * Returns:
   1268  *      SOC_E_XXX
   1269  * Notes:
   1270  *      The speed is set only for the ACTIVE medium.
   1271  */
   1272 
   1273 STATIC int
   1274 phy_84334_speed_set(int unit, soc_port_t port, int speed)
   1275 {
   1276     int            rv; 
   1277     phy_ctrl_t    *pc;
   1278     bmacsec_dev_addr_t phy_dev_addr;
   1279     bmacsec_phy84334_port_mode_t port_mode = 0;
   1280 
   1281     pc = EXT_PHY_SW_STATE(unit, port);
   1282     rv = SOC_E_NONE;
   1283 
   1284     if(PHY_COPPER_MODE(unit, port)) {
   1285         port_mode = BMACSEC_PHY_COPPER;
   1286     } else {
   1287         port_mode = BMACSEC_PHY_FIBER;
   1288         if (speed == 10) {
   1289             return SOC_E_UNAVAIL;
   1290         }
   1291     }
   1292     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1);
   1293     rv = bmacsec_phy84334_speed_set(phy_dev_addr, port_mode, speed);
   1294 
   1295     if(BMACSEC_E_SUCCESS(rv)) {
   1296         if(PHY_COPPER_MODE(unit, port)) {
   1297             pc->copper.force_speed = speed;
   1298         } else {
   1299             pc->fiber.force_speed = speed;
   1300         }
   1301     }
   1302     LOG_INFO(BSL_LS_SOC_PHY,
   1303              (BSL_META_U(unit,
   1304                          "phy_84334_speed_set: u=%d p=%d s=%d fiber=%d rv=%d\n"),
   1305               unit, port, speed, PHY_FIBER_MODE(unit, port), rv));
   1306 
   1307     return SOC_ERROR(rv);
   1308 }
   1309 
   1310 /*
   1311  * Function:
   1312  *      phy_84334_speed_get
   1313  * Purpose:
   1314  *      Get the current operating speed for a 84334 device.
   1315  * Parameters:
   1316  *      unit - StrataSwitch unit #.
   1317  *      port - StrataSwitch port #.
   1318  *      duplex - (OUT) Boolean, true indicates full duplex, false
   1319  *              indicates half.
   1320  * Returns:
   1321  *      SOC_E_NONE
   1322  * Notes:
   1323  *      The speed is retrieved for the ACTIVE medium.
   1324  */
   1325 
   1326 STATIC int
   1327 phy_84334_speed_get(int unit, soc_port_t port, int *speed)
   1328 {
   1329     int rv = SOC_E_NONE;
   1330     bmacsec_phy84334_port_mode_t port_mode = 0;
   1331     bmacsec_dev_addr_t phy_dev_addr;
   1332     phy_ctrl_t    *pc;
   1333 
   1334     pc = EXT_PHY_SW_STATE(unit, port);
   1335 
   1336     if(PHY_COPPER_MODE(unit, port)) {
   1337         port_mode = BMACSEC_PHY_COPPER;
   1338     } else {
   1339             port_mode = BMACSEC_PHY_FIBER;
   1340     }
   1341     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1);
   1342     rv = bmacsec_phy84334_speed_get(phy_dev_addr, port_mode, speed);
   1343 
   1344     if(!BMACSEC_E_SUCCESS(rv)) {
   1345         LOG_WARN(BSL_LS_SOC_PHY,
   1346                  (BSL_META_U(unit,
   1347                              "phy_84334_speed_get: u=%d p=%d invalid speed\n"),
   1348                   unit, port));
   1349     } else {
   1350         LOG_INFO(BSL_LS_SOC_PHY,
   1351                  (BSL_META_U(unit,
   1352                              "phy_84334_speed_get: u=%d p=%d speed=%d"),
   1353                   unit, port, *speed));
   1354     }
   1355 
   1356     return SOC_ERROR(rv);
   1357 }
   1358 
   1359 /*
   1360  * Function:
   1361  *      phy_84334_master_set
   1362  * Purpose:
   1363  *      Set the current master mode
   1364  * Parameters:
   1365  *      unit - StrataSwitch unit #.
   1366  *      port - StrataSwitch port #.
   1367  *      master - SOC_PORT_MS_*
   1368  * Returns:
   1369  *      SOC_E_XXX
   1370  * Notes:
   1371  *      The master mode is set only for the ACTIVE medium.
   1372  */
   1373 STATIC int
   1374 phy_84334_master_set(int unit, soc_port_t port, int master)
   1375 {
   1376     int                  rv;
   1377     phy_ctrl_t    *pc;
   1378     bmacsec_phy84334_port_mode_t port_mode = 0;
   1379     bmacsec_dev_addr_t phy_dev_addr;
   1380 
   1381     pc = EXT_PHY_SW_STATE(unit, port);
   1382     rv = SOC_E_NONE;
   1383 
   1384     if(PHY_COPPER_MODE(unit, port)) {
   1385         port_mode = BMACSEC_PHY_COPPER;
   1386     } else {
   1387         port_mode = BMACSEC_PHY_FIBER;
   1388     }
   1389     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   1390     rv = bmacsec_phy84334_master_set(phy_dev_addr, port_mode, master);
   1391     if(BMACSEC_E_SUCCESS(rv) && PHY_COPPER_MODE(unit, port)) {
   1392         pc->copper.master = master;
   1393     }
   1394 
   1395     LOG_INFO(BSL_LS_SOC_PHY,
   1396              (BSL_META_U(unit,
   1397                          "phy_84334_master_set: u=%d p=%d master=%d fiber=%d rv=%d\n"),
   1398               unit, port, master, PHY_FIBER_MODE(unit, port), rv));
   1399 
   1400     return SOC_ERROR(rv);
   1401 }
   1402 
   1403 /*
   1404  * Function:
   1405  *      phy_84334_master_get
   1406  * Purpose:
   1407  *      Get the current master mode for a 84334 device.
   1408  * Parameters:
   1409  *      unit - StrataSwitch unit #.
   1410  *      port - StrataSwitch port #.
   1411  *      master - (OUT) SOC_PORT_MS_*
   1412  * Returns:
   1413  *      SOC_E_NONE
   1414  * Notes:
   1415  *      The master mode is retrieved for the ACTIVE medium.
   1416  */
   1417 
   1418 STATIC int
   1419 phy_84334_master_get(int unit, soc_port_t port, int *master)
   1420 {
   1421     int        rv;
   1422     phy_ctrl_t *pc;
   1423     bmacsec_phy84334_port_mode_t port_mode = 0;
   1424     bmacsec_dev_addr_t phy_dev_addr;
   1425 
   1426     pc = EXT_PHY_SW_STATE(unit, port);
   1427     rv = SOC_E_NONE;
   1428 
   1429     if(PHY_COPPER_MODE(unit, port)) {
   1430         port_mode = BMACSEC_PHY_COPPER;
   1431     } else {
   1432         port_mode = BMACSEC_PHY_FIBER;
   1433     }
   1434     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   1435     rv = bmacsec_phy84334_master_get(phy_dev_addr, port_mode, master);
   1436 
   1437     return SOC_ERROR(rv);
   1438 }
   1439 
   1440 /*
   1441  * Function:
   1442  *      phy_84334_autoneg_set
   1443  * Purpose:
   1444  *      Enable or disable auto-negotiation on the specified port.
   1445  * Parameters:
   1446  *      unit - StrataSwitch unit #.
   1447  *      port - StrataSwitch port #.
   1448  *      autoneg - Boolean, if true, auto-negotiation is enabled
   1449  *              (and/or restarted). If false, autonegotiation is disabled.
   1450  * Returns:
   1451  *      SOC_E_XXX
   1452  * Notes:
   1453  *      The autoneg mode is set only for the ACTIVE medium.
   1454  */
   1455 
   1456 STATIC int
   1457 phy_84334_autoneg_set(int unit, soc_port_t port, int autoneg)
   1458 {
   1459     int                 rv;
   1460     phy_ctrl_t   *pc;
   1461     bmacsec_phy84334_port_mode_t port_mode = 0;
   1462     bmacsec_dev_addr_t phy_dev_addr;
   1463 
   1464 
   1465     pc = EXT_PHY_SW_STATE(unit, port);
   1466     rv = SOC_E_NONE;
   1467 
   1468     if(PHY_COPPER_MODE(unit, port)) {
   1469         port_mode = BMACSEC_PHY_COPPER;
   1470     } else {
   1471         port_mode = BMACSEC_PHY_FIBER;
   1472     }
   1473     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   1474     rv = bmacsec_phy84334_an_set(phy_dev_addr, port_mode,autoneg);
   1475 
   1476     if(BMACSEC_E_SUCCESS(rv)) {
   1477         if(PHY_COPPER_MODE(unit, port)) {
   1478             pc->copper.autoneg_enable = autoneg ? TRUE : FALSE;
   1479         } else {
   1480             pc->fiber.autoneg_enable = autoneg ? TRUE : FALSE;
   1481         }
   1482     }
   1483 
   1484     LOG_INFO(BSL_LS_SOC_PHY,
   1485              (BSL_META_U(unit,
   1486                          "phy_84334_autoneg_set: u=%d p=%d autoneg=%d rv=%d\n"),
   1487               unit, port, autoneg, rv));
   1488     return SOC_ERROR(rv);
   1489 }
   1490 
   1491 /*
   1492  * Function:
   1493  *      phy_84334_autoneg_get
   1494  * Purpose:
   1495  *      Get the current auto-negotiation status (enabled/busy).
   1496  * Parameters:
   1497  *      unit - StrataSwitch unit #.
   1498  *      port - StrataSwitch port #.
   1499  *      autoneg - (OUT) if true, auto-negotiation is enabled.
   1500  *      autoneg_done - (OUT) if true, auto-negotiation is complete. This
   1501  *              value is undefined if autoneg == FALSE.
   1502  * Returns:
   1503  *      SOC_E_XXX
   1504  * Notes:
   1505  *      The autoneg mode is retrieved for the ACTIVE medium.
   1506  */
   1507 
   1508 STATIC int
   1509 phy_84334_autoneg_get(int unit, soc_port_t port,
   1510                      int *autoneg, int *autoneg_done)
   1511 {
   1512     int           rv;
   1513     phy_ctrl_t   *pc;
   1514     bmacsec_phy84334_port_mode_t port_mode = 0;
   1515     bmacsec_dev_addr_t phy_dev_addr;
   1516 
   1517     pc = EXT_PHY_SW_STATE(unit, port);
   1518 
   1519     rv            = SOC_E_NONE;
   1520     *autoneg      = FALSE;
   1521     *autoneg_done = FALSE;
   1522 
   1523     if(PHY_COPPER_MODE(unit, port)) {
   1524         port_mode = BMACSEC_PHY_COPPER;
   1525     } else {
   1526         port_mode = BMACSEC_PHY_FIBER;
   1527     }
   1528     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   1529     rv = bmacsec_phy84334_an_get(phy_dev_addr, port_mode, autoneg,
   1530                                  autoneg_done);
   1531 
   1532     return SOC_ERROR(rv);
   1533 }
   1534 
   1535 /*
   1536  * Function:
   1537  *      phy_84334_ability_advert_get
   1538  * Purpose:
   1539  *      Get the current advertisement for auto-negotiation.
   1540  * Parameters:
   1541  *      unit - StrataSwitch unit #.
   1542  *      port - StrataSwitch port #.
   1543  *      mode - (OUT) Port mode mask indicating supported options/speeds.
   1544  * Returns:
   1545  *      SOC_E_XXX
   1546  * Notes:
   1547  *      The advertisement is retrieved for the ACTIVE medium.
   1548  *      No synchronization performed at this level.
   1549  */
   1550 
   1551 STATIC int
   1552 phy_84334_ability_advert_get(int unit, soc_port_t port,soc_port_ability_t *ability)
   1553 {
   1554     phy_ctrl_t      *pc;
   1555     bmacsec_phy84334_port_mode_t port_mode;
   1556     bmacsec_phy84334_port_ability_t bmacsec_ability;
   1557     bmacsec_dev_addr_t phy_dev_addr;
   1558     int rv;
   1559 
   1560     pc = EXT_PHY_SW_STATE(unit, port);
   1561 
   1562     sal_memset(ability, 0, sizeof(*ability));
   1563 
   1564     if(PHY_COPPER_MODE(unit, port)) {
   1565         port_mode = BMACSEC_PHY_COPPER;
   1566     } else {
   1567         port_mode = BMACSEC_PHY_FIBER;
   1568     }
   1569     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1);
   1570     rv = bmacsec_phy84334_ability_advert_get(phy_dev_addr, port_mode,
   1571                                         &bmacsec_ability);
   1572     if (rv == BMACSEC_E_NONE) {
   1573         if(bmacsec_ability & BMACSEC_PHY84334_PA_10MB_HD) {
   1574             ability->speed_half_duplex |= SOC_PA_SPEED_10MB;
   1575         }
   1576         if(bmacsec_ability & BMACSEC_PHY84334_PA_10MB_FD) {
   1577             ability->speed_full_duplex |= SOC_PA_SPEED_10MB;
   1578         }
   1579         if(bmacsec_ability & BMACSEC_PHY84334_PA_100MB_HD) {
   1580             ability->speed_half_duplex |= SOC_PA_SPEED_100MB;
   1581         }
   1582         if(bmacsec_ability & BMACSEC_PHY84334_PA_100MB_FD) {
   1583             ability->speed_full_duplex |= SOC_PA_SPEED_100MB;
   1584         }
   1585         if(bmacsec_ability & BMACSEC_PHY84334_PA_1000MB_HD) {
   1586             ability->speed_half_duplex |= SOC_PA_SPEED_1000MB;
   1587         }
   1588         if(bmacsec_ability & BMACSEC_PHY84334_PA_1000MB_FD) {
   1589             ability->speed_full_duplex |= SOC_PA_SPEED_1000MB;
   1590         }
   1591         if(bmacsec_ability & BMACSEC_PHY84334_PA_10000MB_FD) {
   1592             ability->speed_full_duplex |= SOC_PA_SPEED_10GB;
   1593         }
   1594         if(bmacsec_ability & BMACSEC_PHY84334_PA_PAUSE_TX) {
   1595             ability->pause |= SOC_PA_PAUSE_TX;
   1596         }
   1597         if(bmacsec_ability & BMACSEC_PHY84334_PA_PAUSE_RX) {
   1598             ability->pause |= SOC_PA_PAUSE_RX;
   1599         }
   1600 
   1601         if(bmacsec_ability & BMACSEC_PHY84334_PA_EEE_100MB) {
   1602             ability->eee |= SOC_PA_EEE_100MB_BASETX;
   1603         }
   1604         if(bmacsec_ability & BMACSEC_PHY84334_PA_EEE_1000MB) {
   1605             ability->eee |= SOC_PA_EEE_1GB_BASET;
   1606         }
   1607         if(bmacsec_ability & BMACSEC_PHY84334_PA_EEE_10000MB) {
   1608             ability->eee |= SOC_PA_EEE_10GB_BASET;
   1609         }
   1610     }
   1611 
   1612     return (SOC_ERROR(rv));
   1613 }
   1614 
   1615 /*
   1616  * Function:
   1617  *      phy_84334_ability_advert_set
   1618  * Purpose:
   1619  *      Set the current advertisement for auto-negotiation.
   1620  * Parameters:
   1621  *      unit - StrataSwitch unit #.
   1622  *      port - StrataSwitch port #.
   1623  *      mode - Port mode mask indicating supported options/speeds.
   1624  * Returns:
   1625  *      SOC_E_XXX
   1626  * Notes:
   1627  *      The advertisement is set only for the ACTIVE medium.
   1628  *      No synchronization performed at this level.
   1629  */
   1630 
   1631 
   1632 STATIC int
   1633 phy_84334_ability_advert_set(int unit, soc_port_t port, soc_port_ability_t *ability)
   1634 {
   1635     phy_ctrl_t      *pc;
   1636     bmacsec_phy84334_port_mode_t port_mode;
   1637     bmacsec_phy84334_port_ability_t bmacsec_ability;
   1638     bmacsec_dev_addr_t phy_dev_addr;
   1639     int rv;
   1640 
   1641     pc = EXT_PHY_SW_STATE(unit, port);
   1642 
   1643     if(PHY_COPPER_MODE(unit, port)) {
   1644         port_mode = BMACSEC_PHY_COPPER;
   1645     } else {
   1646         port_mode = BMACSEC_PHY_FIBER;
   1647     }
   1648     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1);
   1649 
   1650     bmacsec_ability = 0;
   1651 
   1652     if (ability->speed_half_duplex & SOC_PA_SPEED_10MB)  {
   1653         bmacsec_ability |= BMACSEC_PHY84334_PA_10MB_HD;
   1654     }
   1655     if (ability->speed_half_duplex & SOC_PA_SPEED_100MB) {
   1656         bmacsec_ability |= BMACSEC_PHY84334_PA_100MB_HD;
   1657     }
   1658     if (ability->speed_half_duplex & SOC_PA_SPEED_1000MB) {
   1659         bmacsec_ability |= BMACSEC_PHY84334_PA_1000MB_HD;
   1660     }
   1661     if (ability->speed_full_duplex & SOC_PA_SPEED_10MB)  {
   1662         bmacsec_ability |= BMACSEC_PHY84334_PA_10MB_FD;
   1663     }
   1664     if (ability->speed_full_duplex & SOC_PA_SPEED_100MB) {
   1665         bmacsec_ability |= BMACSEC_PHY84334_PA_100MB_FD;
   1666     }
   1667     if (ability->speed_full_duplex & SOC_PA_SPEED_1000MB) {
   1668         bmacsec_ability |= BMACSEC_PHY84334_PA_1000MB_FD;
   1669     }
   1670     if (ability->speed_full_duplex & SOC_PA_SPEED_10GB) {
   1671         bmacsec_ability |= BMACSEC_PHY84334_PA_10000MB_FD;
   1672     }
   1673     if (ability->pause & SOC_PA_PAUSE_TX) {
   1674         bmacsec_ability |= BMACSEC_PHY84334_PA_PAUSE_TX;
   1675     }
   1676     if (ability->pause & SOC_PA_PAUSE_RX) {
   1677         bmacsec_ability |= BMACSEC_PHY84334_PA_PAUSE_RX;
   1678     }
   1679 
   1680     if (ability->eee & SOC_PA_EEE_100MB_BASETX) {
   1681         bmacsec_ability |= BMACSEC_PHY84334_PA_EEE_100MB;
   1682     }
   1683     if (ability->eee & SOC_PA_EEE_1GB_BASET) {
   1684         bmacsec_ability |= BMACSEC_PHY84334_PA_EEE_100MB;
   1685     }
   1686     if (ability->eee & SOC_PA_EEE_10GB_BASET) {
   1687         bmacsec_ability |= BMACSEC_PHY84334_PA_EEE_10000MB;
   1688     }
   1689 
   1690     rv = bmacsec_phy84334_ability_advert_set(phy_dev_addr, port_mode, bmacsec_ability);
   1691 
   1692     return (SOC_ERROR(rv));
   1693 }
   1694 
   1695 /*
   1696  * Function:
   1697  *      phy_84334_ability_remote_get
   1698  * Purpose:
   1699  *      Get the current remoteisement for auto-negotiation.
   1700  * Parameters:
   1701  *      unit - StrataSwitch unit #.
   1702  *      port - StrataSwitch port #.
   1703  *      mode - (OUT) Port mode mask indicating supported options/speeds.
   1704  * Returns:
   1705  *      SOC_E_XXX
   1706  * Notes:
   1707  *      The remoteisement is retrieved for the ACTIVE medium.
   1708  *      No synchronization performed at this level.
   1709  */
   1710 
   1711 STATIC int
   1712 phy_84334_ability_remote_get(int unit, soc_port_t port,soc_port_ability_t *ability)
   1713 {
   1714     phy_ctrl_t      *pc;
   1715     bmacsec_phy84334_port_mode_t port_mode;
   1716     bmacsec_phy84334_port_ability_t bmacsec_ability = 0;
   1717     bmacsec_dev_addr_t phy_dev_addr;
   1718     int rv;
   1719 
   1720     pc = EXT_PHY_SW_STATE(unit, port);
   1721 
   1722     sal_memset(ability, 0, sizeof(*ability));
   1723 
   1724     if(PHY_COPPER_MODE(unit, port)) {
   1725         port_mode = BMACSEC_PHY_COPPER;
   1726     } else {
   1727         port_mode = BMACSEC_PHY_FIBER;
   1728     }
   1729     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1);
   1730     rv = bmacsec_phy84334_remote_ability_advert_get(phy_dev_addr, port_mode,
   1731                                         &bmacsec_ability);
   1732     if (rv == BMACSEC_E_NONE) {
   1733         if(bmacsec_ability & BMACSEC_PHY84334_PA_10MB_HD) {
   1734             ability->speed_half_duplex |= SOC_PA_SPEED_10MB;
   1735         }
   1736         if(bmacsec_ability & BMACSEC_PHY84334_PA_10MB_FD) {
   1737             ability->speed_full_duplex |= SOC_PA_SPEED_10MB;
   1738         }
   1739         if(bmacsec_ability & BMACSEC_PHY84334_PA_100MB_HD) {
   1740             ability->speed_half_duplex |= SOC_PA_SPEED_100MB;
   1741         }
   1742         if(bmacsec_ability & BMACSEC_PHY84334_PA_100MB_FD) {
   1743             ability->speed_full_duplex |= SOC_PA_SPEED_100MB;
   1744         }
   1745         if(bmacsec_ability & BMACSEC_PHY84334_PA_1000MB_HD) {
   1746             ability->speed_half_duplex |= SOC_PA_SPEED_1000MB;
   1747         }
   1748         if(bmacsec_ability & BMACSEC_PHY84334_PA_1000MB_FD) {
   1749             ability->speed_full_duplex |= SOC_PA_SPEED_1000MB;
   1750         }
   1751         if(bmacsec_ability & BMACSEC_PHY84334_PA_10000MB_FD) {
   1752             ability->speed_full_duplex |= SOC_PA_SPEED_10GB;
   1753         }
   1754         if(bmacsec_ability & BMACSEC_PHY84334_PA_PAUSE_TX) {
   1755             ability->pause |= SOC_PA_PAUSE_TX;
   1756         }
   1757         if(bmacsec_ability & BMACSEC_PHY84334_PA_PAUSE_RX) {
   1758             ability->pause |= SOC_PA_PAUSE_RX;
   1759         }
   1760 
   1761         if(bmacsec_ability & BMACSEC_PHY84334_PA_EEE_100MB) {
   1762             ability->eee |= SOC_PA_EEE_100MB_BASETX;
   1763         }
   1764         if(bmacsec_ability & BMACSEC_PHY84334_PA_EEE_1000MB) {
   1765             ability->eee |= SOC_PA_EEE_1GB_BASET;
   1766         }
   1767         if(bmacsec_ability & BMACSEC_PHY84334_PA_EEE_10000MB) {
   1768             ability->eee |= SOC_PA_EEE_10GB_BASET;
   1769         }
   1770     }
   1771 
   1772     return (SOC_ERROR(rv));
   1773 }
   1774 
   1775 /*
   1776  * Function:
   1777  *      phy_84334_ability_local_get
   1778  * Purpose:
   1779  *      Get the device's complete abilities.
   1780  * Parameters:
   1781  *      unit - StrataSwitch unit #.
   1782  *      port - StrataSwitch port #.
   1783  *      ability - return device's abilities.
   1784  * Returns:
   1785  *      SOC_E_XXX
   1786  */
   1787 
   1788 STATIC int
   1789 phy_84334_ability_local_get(int unit, soc_port_t port,soc_port_ability_t *ability)
   1790 {
   1791     phy_ctrl_t      *pc;
   1792     bmacsec_phy84334_port_mode_t port_mode;
   1793     bmacsec_phy84334_port_ability_t bmacsec_ability;
   1794     bmacsec_dev_addr_t phy_dev_addr;
   1795     int rv;
   1796 
   1797     pc = EXT_PHY_SW_STATE(unit, port);
   1798 
   1799     sal_memset(ability, 0, sizeof(*ability));
   1800 
   1801     if(PHY_COPPER_MODE(unit, port)) {
   1802         port_mode = BMACSEC_PHY_COPPER;
   1803     } else {
   1804         port_mode = BMACSEC_PHY_FIBER;
   1805     }
   1806     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1);
   1807     rv = bmacsec_phy84334_ability_local_get(phy_dev_addr, port_mode,
   1808                                         &bmacsec_ability);
   1809     if (rv == BMACSEC_E_NONE) {
   1810         if(bmacsec_ability & BMACSEC_PHY84334_PA_10MB_HD) {
   1811             ability->speed_half_duplex |= SOC_PA_SPEED_10MB;
   1812         }
   1813         if(bmacsec_ability & BMACSEC_PHY84334_PA_10MB_FD) {
   1814             ability->speed_full_duplex |= SOC_PA_SPEED_10MB;
   1815         }
   1816         if(bmacsec_ability & BMACSEC_PHY84334_PA_100MB_HD) {
   1817             ability->speed_half_duplex |= SOC_PA_SPEED_100MB;
   1818         }
   1819         if(bmacsec_ability & BMACSEC_PHY84334_PA_100MB_FD) {
   1820             ability->speed_full_duplex |= SOC_PA_SPEED_100MB;
   1821         }
   1822         if(bmacsec_ability & BMACSEC_PHY84334_PA_1000MB_HD) {
   1823             ability->speed_half_duplex |= SOC_PA_SPEED_1000MB;
   1824         }
   1825         if(bmacsec_ability & BMACSEC_PHY84334_PA_1000MB_FD) {
   1826             ability->speed_full_duplex |= SOC_PA_SPEED_1000MB;
   1827         }
   1828         if(bmacsec_ability & BMACSEC_PHY84334_PA_10000MB_FD) {
   1829             ability->speed_full_duplex |= SOC_PA_SPEED_10GB;
   1830         }
   1831         if(bmacsec_ability & BMACSEC_PHY84334_PA_PAUSE_TX) {
   1832             ability->pause |= SOC_PA_PAUSE_TX;
   1833         }
   1834         if(bmacsec_ability & BMACSEC_PHY84334_PA_PAUSE_RX) {
   1835             ability->pause |= SOC_PA_PAUSE_RX;
   1836         }
   1837 
   1838         if(bmacsec_ability & BMACSEC_PHY84334_PA_EEE_100MB) {
   1839             ability->eee |= SOC_PA_EEE_100MB_BASETX;
   1840         }
   1841         if(bmacsec_ability & BMACSEC_PHY84334_PA_EEE_1000MB) {
   1842             ability->eee |= SOC_PA_EEE_1GB_BASET;
   1843         }
   1844         if(bmacsec_ability & BMACSEC_PHY84334_PA_EEE_10000MB) {
   1845             ability->eee |= SOC_PA_EEE_10GB_BASET;
   1846         }
   1847     }
   1848 
   1849     return (SOC_ERROR(rv));
   1850 }
   1851 
   1852 /*
   1853  * Function:
   1854  *      phy_84334_lb_set
   1855  * Purpose:
   1856  *      Set the local PHY loopback mode.
   1857  * Parameters:
   1858  *      unit - StrataSwitch unit #.
   1859  *      port - StrataSwitch port #.
   1860  *      loopback - Boolean: true = enable loopback, false = disable.
   1861  * Returns:
   1862  *      SOC_E_XXX
   1863  * Notes:
   1864  *      The loopback mode is set only for the ACTIVE medium.
   1865  *      No synchronization performed at this level.
   1866  */
   1867 
   1868 STATIC int
   1869 phy_84334_lb_set(int unit, soc_port_t port, int enable)
   1870 {
   1871     int           rv;
   1872     phy_ctrl_t    *pc;
   1873     bmacsec_phy84334_port_mode_t port_mode = BMACSEC_PHY_COPPER;
   1874     bmacsec_dev_addr_t phy_dev_addr;
   1875 
   1876     pc = EXT_PHY_SW_STATE(unit, port);
   1877     rv = SOC_E_NONE;
   1878 
   1879 #if AUTO_MDIX_WHEN_AN_DIS
   1880     {
   1881         /* Disable Auto-MDIX When autoneg disabled */
   1882         /* Enable Auto-MDIX When autoneg disabled */
   1883         data = (enable) ? 0x0000 : 0x0200;
   1884         rv = BMACSEC_MODIFY_PHY_84334_MII_MISC_CTRLr(pc->phy_id, data, 0x0200);
   1885         if(!BMACSEC_E_SUCCESS(rv)) {
   1886             return SOC_ERROR(rv);
   1887         }
   1888 
   1889     }
   1890 #endif
   1891 
   1892     pc = EXT_PHY_SW_STATE(unit, port);
   1893     rv = SOC_E_NONE;
   1894 
   1895     if(PHY_COPPER_MODE(unit, port)) {
   1896         port_mode = BMACSEC_PHY_COPPER;
   1897     } else {
   1898         port_mode = BMACSEC_PHY_FIBER;
   1899     }
   1900     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   1901     rv = bmacsec_phy84334_loopback_set(phy_dev_addr, port_mode, enable);
   1902 
   1903     if(!BMACSEC_E_SUCCESS(rv)) {
   1904         return SOC_E_FAIL;
   1905     }
   1906     sal_usleep(1000000);
   1907 
   1908     if (enable) {
   1909         SOC_IF_ERROR_RETURN
   1910             (phy_84334_linkup(unit, port));
   1911     }
   1912 
   1913     LOG_INFO(BSL_LS_SOC_PHY,
   1914              (BSL_META_U(unit,
   1915                          "phy_84334_lb_set: u=%d p=%d en=%d rv=%d\n"), 
   1916               unit, port, enable, rv));
   1917 
   1918     return SOC_ERROR(rv); 
   1919 }
   1920 
   1921 /*
   1922  * Function:
   1923  *      phy_84334_lb_get
   1924  * Purpose:
   1925  *      Get the local PHY loopback mode.
   1926  * Parameters:
   1927  *      unit - StrataSwitch unit #.
   1928  *      port - StrataSwitch port #.
   1929  *      loopback - (OUT) Boolean: true = enable loopback, false = disable.
   1930  * Returns:
   1931  *      SOC_E_XXX
   1932  * Notes:
   1933  *      The loopback mode is retrieved for the ACTIVE medium.
   1934  */
   1935 
   1936 STATIC int
   1937 phy_84334_lb_get(int unit, soc_port_t port, int *enable)
   1938 {
   1939     int                  rv;
   1940     phy_ctrl_t    *pc;
   1941     bmacsec_phy84334_port_mode_t port_mode = BMACSEC_PHY_COPPER;
   1942     bmacsec_dev_addr_t phy_dev_addr;
   1943 
   1944     pc = EXT_PHY_SW_STATE(unit, port);
   1945     rv = SOC_E_NONE;
   1946 
   1947     if(PHY_COPPER_MODE(unit, port)) {
   1948         port_mode = BMACSEC_PHY_COPPER;
   1949     } else {
   1950         port_mode = BMACSEC_PHY_FIBER;
   1951     }
   1952     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   1953     rv = bmacsec_phy84334_loopback_get(phy_dev_addr, port_mode, enable);
   1954 
   1955     return SOC_ERROR(rv); 
   1956 }
   1957 
   1958 /*
   1959  * Function:
   1960  *      phy_84334_mdix_set
   1961  * Description:
   1962  *      Set the Auto-MDIX mode of a port/PHY
   1963  * Parameters:
   1964  *      unit - Device number
   1965  *      port - Port number
   1966  *      mode - One of:
   1967  *              SOC_PORT_MDIX_AUTO
   1968  *                      Enable auto-MDIX when autonegotiation is enabled
   1969  *              SOC_PORT_MDIX_FORCE_AUTO
   1970  *                      Enable auto-MDIX always
   1971  *              SOC_PORT_MDIX_NORMAL
   1972  *                      Disable auto-MDIX
   1973  *              SOC_PORT_MDIX_XOVER
   1974  *                      Disable auto-MDIX, and swap cable pairs
   1975  * Return Value:
   1976  *      SOC_E_XXX
   1977  */
   1978 STATIC int
   1979 phy_84334_mdix_set(int unit, soc_port_t port, soc_port_mdix_t mode)
   1980 {
   1981 
   1982     int         rv;
   1983     phy_ctrl_t  *pc;
   1984     bmacsec_phy84334_port_mode_t port_mode = BMACSEC_PHY_COPPER;
   1985     bmacsec_dev_addr_t phy_dev_addr;
   1986     bmacsec_phy84334_port_mdix_t bmacsec_mode;
   1987 
   1988     pc = EXT_PHY_SW_STATE(unit, port);
   1989 
   1990     if(PHY_COPPER_MODE(unit, port)) {
   1991         port_mode = BMACSEC_PHY_COPPER;
   1992     } else {
   1993         port_mode = BMACSEC_PHY_FIBER;
   1994     }
   1995     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   1996     switch(mode) {
   1997     case SOC_PORT_MDIX_AUTO:
   1998         bmacsec_mode = BMACSEC_PHY84334_PORT_MDIX_AUTO;
   1999         break;
   2000     case SOC_PORT_MDIX_FORCE_AUTO:
   2001         bmacsec_mode = BMACSEC_PHY84334_PORT_MDIX_FORCE_AUTO;
   2002         break;
   2003     case SOC_PORT_MDIX_NORMAL:
   2004         bmacsec_mode = BMACSEC_PHY84334_PORT_MDIX_NORMAL;
   2005         break;
   2006     case SOC_PORT_MDIX_XOVER:
   2007         bmacsec_mode = BMACSEC_PHY84334_PORT_MDIX_XOVER;
   2008         break;
   2009     default :
   2010         return SOC_E_CONFIG;
   2011     }
   2012 
   2013     rv = bmacsec_phy84334_mdix_set(phy_dev_addr, port_mode, bmacsec_mode);
   2014 
   2015     if(BMACSEC_E_SUCCESS(rv) && PHY_COPPER_MODE(unit, port)) {
   2016         pc->copper.mdix = mode;
   2017     }
   2018     return SOC_ERROR(rv);
   2019 }        
   2020 
   2021 /*
   2022  * Function:
   2023  *      phy_84334_mdix_get
   2024  * Description:
   2025  *      Get the Auto-MDIX mode of a port/PHY
   2026  * Parameters:
   2027  *      unit - Device number
   2028  *      port - Port number
   2029  *      mode - (Out) One of:
   2030  *              SOC_PORT_MDIX_AUTO
   2031  *                      Enable auto-MDIX when autonegotiation is enabled
   2032  *              SOC_PORT_MDIX_FORCE_AUTO
   2033  *                      Enable auto-MDIX always
   2034  *              SOC_PORT_MDIX_NORMAL
   2035  *                      Disable auto-MDIX
   2036  *              SOC_PORT_MDIX_XOVER
   2037  *                      Disable auto-MDIX, and swap cable pairs
   2038  * Return Value:
   2039  *      SOC_E_XXX
   2040  */
   2041 STATIC int
   2042 phy_84334_mdix_get(int unit, soc_port_t port, soc_port_mdix_t *mode)
   2043 {
   2044     phy_ctrl_t    *pc;
   2045     int            speed;
   2046 
   2047     if (mode == NULL) {
   2048         return SOC_E_PARAM;
   2049     }
   2050 
   2051     pc = EXT_PHY_SW_STATE(unit, port);
   2052 
   2053     if (PHY_COPPER_MODE(unit, port)) {
   2054         SOC_IF_ERROR_RETURN(phy_84334_speed_get(unit, port, &speed));
   2055         if (speed == 1000) {
   2056            *mode = SOC_PORT_MDIX_AUTO;
   2057         } else {
   2058             *mode = pc->copper.mdix;
   2059         }
   2060     } else {
   2061         *mode = SOC_PORT_MDIX_NORMAL;
   2062     }
   2063 
   2064     return SOC_E_NONE;
   2065 }    
   2066 
   2067 /*
   2068  * Function:
   2069  *      phy_84334_mdix_status_get
   2070  * Description:
   2071  *      Get the current MDIX status on a port/PHY
   2072  * Parameters:
   2073  *      unit    - Device number
   2074  *      port    - Port number
   2075  *      status  - (OUT) One of:
   2076  *              SOC_PORT_MDIX_STATUS_NORMAL
   2077  *                      Straight connection
   2078  *              SOC_PORT_MDIX_STATUS_XOVER
   2079  *                      Crossover has been performed
   2080  * Return Value:
   2081  *      SOC_E_XXX
   2082  */
   2083 STATIC int
   2084 phy_84334_mdix_status_get(int unit, soc_port_t port, 
   2085                          soc_port_mdix_status_t *status)
   2086 {
   2087     int         rv;
   2088     phy_ctrl_t    *pc;
   2089 
   2090     bmacsec_phy84334_port_mode_t port_mode = BMACSEC_PHY_COPPER;
   2091     bmacsec_dev_addr_t phy_dev_addr;
   2092     bmacsec_phy84334_port_mdix_status_t mdix_status;
   2093 
   2094     if (status == NULL) {
   2095         return SOC_E_PARAM;
   2096     }
   2097 
   2098     pc = EXT_PHY_SW_STATE(unit, port);
   2099 
   2100     if(PHY_COPPER_MODE(unit, port)) {
   2101         port_mode = BMACSEC_PHY_COPPER;
   2102     } else {
   2103         port_mode = BMACSEC_PHY_FIBER;
   2104     }
   2105 
   2106     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   2107     rv = bmacsec_phy84334_mdix_status_get(phy_dev_addr, port_mode, 
   2108                                           &mdix_status);
   2109     if(BMACSEC_E_SUCCESS(rv)) {
   2110         if(mdix_status == BMACSEC_PHY84334_PORT_MDIX_STATUS_NORMAL) {
   2111             *status = SOC_PORT_MDIX_STATUS_NORMAL;
   2112         }
   2113         if(mdix_status == BMACSEC_PHY84334_PORT_MDIX_STATUS_XOVER) {
   2114             *status = SOC_PORT_MDIX_STATUS_XOVER;
   2115         }
   2116         return SOC_E_NONE;
   2117     }
   2118 
   2119     return SOC_ERROR(rv);
   2120 }    
   2121 
   2122 
   2123 /*
   2124  * Function:
   2125  *      phy_84334_timesync_config_set
   2126  * Description:
   2127  *      
   2128  * Parameters:
   2129  *
   2130  * Return Value:
   2131  *      SOC_E_XXX
   2132  */
   2133 
   2134 int
   2135 phy_84334_timesync_config_set(int unit, soc_port_t port, soc_port_phy_timesync_config_t *timesync_config)
   2136 {
   2137     int                          rv;
   2138     phy_ctrl_t                   *pc;
   2139     bmacsec_dev_addr_t phy_dev_addr;
   2140 
   2141     pc = EXT_PHY_SW_STATE(unit, port);
   2142     rv = SOC_E_NONE;
   2143     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 0); 
   2144  
   2145     rv = bmacsec_phy84334_timesync_config_set(phy_dev_addr, (bmacsec_port_phy_timesync_config_t *)timesync_config);
   2146     return (SOC_ERROR(rv));
   2147 
   2148 }
   2149 
   2150 
   2151 /*
   2152  * Function:
   2153  *     phy_84334_timesync_config_get 
   2154  * Description:
   2155  *     
   2156  * Parameters:
   2157  *
   2158  * Return Value:
   2159  *      SOC_E_XXX
   2160  */
   2161 
   2162 int
   2163 phy_84334_timesync_config_get(int unit, soc_port_t port, soc_port_phy_timesync_config_t *timesync_config)
   2164 {
   2165     int                          rv;
   2166     phy_ctrl_t                   *pc;
   2167     bmacsec_dev_addr_t phy_dev_addr;
   2168 
   2169     pc = EXT_PHY_SW_STATE(unit, port);
   2170     rv = SOC_E_NONE;
   2171     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 0); 
   2172  
   2173     rv = bmacsec_phy84334_timesync_config_get(phy_dev_addr, (bmacsec_port_phy_timesync_config_t *)timesync_config);
   2174     return (SOC_ERROR(rv));
   2175 
   2176 }
   2177 
   2178 
   2179 /*
   2180  * Function:
   2181  *      phy_84334_timesync_control_set
   2182  * Description:
   2183  *      
   2184  * Parameters:
   2185  *
   2186  * Return Value:
   2187  *      SOC_E_XXX
   2188  */
   2189 
   2190 int
   2191 phy_84334_timesync_control_set(int unit, soc_port_t port, soc_port_control_phy_timesync_t control_type, uint64 value)
   2192 {
   2193     int                          rv;
   2194     phy_ctrl_t                   *pc;
   2195     bmacsec_dev_addr_t phy_dev_addr;
   2196     buint64_t btemp64;
   2197 
   2198     COMPILER_64_SET(btemp64, COMPILER_64_HI(value), COMPILER_64_LO(value)); 
   2199 
   2200     pc = EXT_PHY_SW_STATE(unit, port);
   2201     rv = SOC_E_NONE;
   2202     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 0); 
   2203  
   2204     rv = bmacsec_phy84334_timesync_control_set(phy_dev_addr, control_type, btemp64);
   2205     return (SOC_ERROR(rv));
   2206 
   2207 }
   2208 
   2209 
   2210 
   2211 /*
   2212  * Function:
   2213  *      phy_84334_timesync_control_get
   2214  * Description:
   2215  *      
   2216  * Parameters:
   2217  *
   2218  * Return Value:
   2219  *      SOC_E_XXX
   2220  */
   2221 int
   2222 phy_84334_timesync_control_get(int unit, soc_port_t port, soc_port_control_phy_timesync_t control_type, uint64 *value)
   2223 {
   2224     int                          rv;
   2225     phy_ctrl_t                   *pc;
   2226     bmacsec_dev_addr_t phy_dev_addr;
   2227     buint64_t btemp64;
   2228 
   2229     COMPILER_64_ZERO(btemp64);
   2230     pc = EXT_PHY_SW_STATE(unit, port);
   2231     rv = SOC_E_NONE;
   2232     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 0); 
   2233  
   2234     rv = bmacsec_phy84334_timesync_control_get(phy_dev_addr, control_type, &btemp64);
   2235   
   2236     COMPILER_64_SET(*value, COMPILER_64_HI(btemp64), COMPILER_64_LO(btemp64));
   2237 
   2238     return (SOC_ERROR(rv));
   2239 
   2240 }
   2241 
   2242 
   2243 /*
   2244  * Function:
   2245  *      phy_84334_control_set
   2246  * Purpose:
   2247  *      Configure PHY device specific control fucntion.
   2248  * Parameters:
   2249  *      unit  - StrataSwitch unit #.
   2250  *      port  - StrataSwitch port #.
   2251  *      type  - Control to update
   2252  *      value - New setting for the control
   2253  * Returns:    
   2254  *      SOC_E_NONE
   2255  */
   2256 STATIC int
   2257 phy_84334_control_set(int unit, soc_port_t port,
   2258                      soc_phy_control_t type, uint32 value)
   2259 {
   2260     int rv, pause_fwd = 0, temp;
   2261     phy_ctrl_t    *pc;
   2262     bmacsec_dev_addr_t phy_dev_addr;
   2263 
   2264     pc = EXT_PHY_SW_STATE(unit, port);
   2265 
   2266 
   2267     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   2268 
   2269     rv = BMACSEC_E_NONE;    
   2270     switch(type) {
   2271         case SOC_PHY_CONTROL_MACSEC_SWITCH_FIXED:
   2272             pc->macsec_switch_fixed = value;
   2273             if(value) {
   2274                 rv = bmacsec_phy84334_switch_side_set_params(phy_dev_addr, 
   2275                                 BMACSEC_BCM84334_SWITCH_FIXED, 
   2276                                 pc->macsec_switch_fixed_speed,
   2277                                 pc->macsec_switch_fixed_duplex,
   2278                                 pc->macsec_switch_fixed_pause);
   2279             } else { /* Switch side follows line side */
   2280                 rv = bmacsec_phy84334_switch_side_set_params(phy_dev_addr, 
   2281                                 BMACSEC_BCM84334_SWITCH_FOLLOWS_LINE, 
   2282                                 -1, -1, -1);
   2283             }
   2284 
   2285             break;
   2286         case SOC_PHY_CONTROL_MACSEC_SWITCH_FIXED_SPEED:
   2287             /* Switch fixed speed is allowed only to be 1000Mbps */
   2288             if (value != 1000) {
   2289                 return SOC_E_CONFIG;
   2290             }
   2291             if(pc->macsec_switch_fixed_speed != value) {
   2292                 int line_speed;
   2293 
   2294                 pc->macsec_switch_fixed_speed = value;
   2295 
   2296                 SOC_IF_ERROR_RETURN
   2297                     (phy_84334_speed_get(unit, port, &line_speed));
   2298                 pc->macsec_switch_fixed_speed = line_speed;
   2299 
   2300             }
   2301             break;
   2302         case SOC_PHY_CONTROL_MACSEC_SWITCH_FIXED_DUPLEX:
   2303             /* Switch fixed Duplex is allowed only to be Full Duplex mode */
   2304             if (value != 1) {
   2305                 return SOC_E_CONFIG;
   2306             }
   2307             if(pc->macsec_switch_fixed_duplex != value) {
   2308                 pc->macsec_switch_fixed_duplex = value;
   2309             }
   2310             break;
   2311         case SOC_PHY_CONTROL_MACSEC_SWITCH_FIXED_PAUSE:
   2312             if(pc->macsec_switch_fixed_pause != value) {
   2313                 pc->macsec_switch_fixed_pause = value;
   2314             }
   2315             break;
   2316         case SOC_PHY_CONTROL_MACSEC_PAUSE_RX_FORWARD:
   2317             pc->macsec_pause_rx_fwd = value;
   2318             pause_fwd = (value == 1) ? 1 : 0;
   2319 
   2320             rv = bmacsec_phy84334_line_side_pause_forward(phy_dev_addr,
   2321                                                           pause_fwd);
   2322             if (rv == BMACSEC_E_NONE) {
   2323                 rv = bmacsec_phy84334_switch_side_pause_forward(
   2324                                                      phy_dev_addr, pause_fwd);
   2325             }
   2326             break;
   2327         case SOC_PHY_CONTROL_MACSEC_PAUSE_TX_FORWARD:
   2328             pc->macsec_pause_tx_fwd = value;
   2329             pause_fwd = (value == 1) ? 1 : 0;
   2330 
   2331             rv = bmacsec_phy84334_line_side_pause_forward(phy_dev_addr,
   2332                                                           pause_fwd);
   2333             if (rv == BMACSEC_E_NONE) {
   2334                 rv = bmacsec_phy84334_switch_side_pause_forward(phy_dev_addr,
   2335                                                                 pause_fwd);
   2336             }
   2337             break;
   2338         case SOC_PHY_CONTROL_MACSEC_LINE_IPG:
   2339             pc->macsec_line_ipg = value;
   2340             rv = bmacsec_phy84334_line_side_ipg_set(phy_dev_addr, value);
   2341             break;
   2342         case SOC_PHY_CONTROL_MACSEC_SWITCH_IPG:
   2343             pc->macsec_switch_ipg = value;
   2344             rv = bmacsec_phy84334_switch_side_ipg_set(phy_dev_addr, value);
   2345             break;
   2346 
   2347 
   2348 
   2349 
   2350     case SOC_PHY_CONTROL_EEE:
   2351         if (value) {
   2352                 SOC_IF_ERROR_RETURN
   2353                     (bmacsec_phy84334_eee_mode_set(phy_dev_addr, 1, 0x0000, 0x0000, 0x0000 ));
   2354 
   2355             pc->copper.advert_ability.eee |= (SOC_PA_EEE_10GB_BASET | SOC_PA_EEE_1GB_BASET | SOC_PA_EEE_100MB_BASETX);
   2356             temp = pc->copper.autoneg_enable;
   2357             /* Initiate AN */
   2358             SOC_IF_ERROR_RETURN
   2359                 (phy_84334_autoneg_set(unit, port, 1));
   2360             pc->copper.autoneg_enable = temp;
   2361             PHY_FLAGS_SET(unit, port, PHY_FLAGS_EEE_ENABLED);
   2362             PHY_FLAGS_CLR(unit, pc->port, PHY_FLAGS_EEE_MODE);
   2363         } else {
   2364                 SOC_IF_ERROR_RETURN
   2365                     (bmacsec_phy84334_eee_mode_set(phy_dev_addr, 0, 0x0000, 0x0000, 0x0000 ));
   2366             pc->copper.advert_ability.eee &= ~(SOC_PA_EEE_10GB_BASET | SOC_PA_EEE_1GB_BASET | SOC_PA_EEE_100MB_BASETX);
   2367             SOC_IF_ERROR_RETURN
   2368                 (phy_84334_autoneg_set(unit, port, pc->copper.autoneg_enable ? 1 : 0));
   2369             PHY_FLAGS_CLR(unit, port, PHY_FLAGS_EEE_ENABLED);
   2370         }
   2371         break;
   2372 
   2373     case SOC_PHY_CONTROL_EEE_AUTO:
   2374         if (value) {
   2375                 SOC_IF_ERROR_RETURN
   2376                     (bmacsec_phy84334_eee_mode_set(phy_dev_addr, 2, 0x0000, 0x047f, 0x047e ));
   2377 
   2378             pc->copper.advert_ability.eee |= (SOC_PA_EEE_10GB_BASET | SOC_PA_EEE_1GB_BASET | SOC_PA_EEE_100MB_BASETX);
   2379             temp = pc->copper.autoneg_enable;
   2380             /* Initiate AN */
   2381             SOC_IF_ERROR_RETURN
   2382                 (phy_84334_autoneg_set(unit, port, 1));
   2383             pc->copper.autoneg_enable = temp;
   2384             PHY_FLAGS_SET(unit, port, PHY_FLAGS_EEE_ENABLED);
   2385             PHY_FLAGS_SET(unit, pc->port, PHY_FLAGS_EEE_MODE);
   2386         } else {
   2387            SOC_IF_ERROR_RETURN
   2388                (bmacsec_phy84334_eee_mode_set(phy_dev_addr, 0, 0x0000, 0x0000, 0x0000 ));
   2389             pc->copper.advert_ability.eee &= ~(SOC_PA_EEE_10GB_BASET | SOC_PA_EEE_1GB_BASET | SOC_PA_EEE_100MB_BASETX);
   2390             SOC_IF_ERROR_RETURN
   2391                 (phy_84334_autoneg_set(unit, port, pc->copper.autoneg_enable ? 1 : 0));
   2392             PHY_FLAGS_CLR(unit, port, PHY_FLAGS_EEE_ENABLED);
   2393         }
   2394         break;
   2395 
   2396     case SOC_PHY_CONTROL_EEE_AUTO_FIXED_LATENCY:
   2397         { 
   2398             uint16 mode=0, latency=0, th_high=0, th_low=0;
   2399             SOC_IF_ERROR_RETURN
   2400                 (bmacsec_phy84334_eee_mode_get(phy_dev_addr, &mode, &th_high, &th_low, &latency ));
   2401             /* Fixed latency can have only 0 or 1 value  */
   2402             if ((value != FALSE) && (value != TRUE)) {
   2403                 return SOC_E_PARAM;
   2404             }
   2405             if (value == FALSE) {
   2406                 /* Variable latency  */
   2407                 SOC_IF_ERROR_RETURN
   2408                     (bmacsec_phy84334_eee_mode_set(phy_dev_addr, 3, th_high, th_low, latency ));
   2409             } else {
   2410                 /* Fixed latency  */ 
   2411                 SOC_IF_ERROR_RETURN
   2412                     (bmacsec_phy84334_eee_mode_set(phy_dev_addr, 2, th_high, th_low, latency ));
   2413             }
   2414         }
   2415         break;
   2416 
   2417     case SOC_PHY_CONTROL_EEE_AUTO_IDLE_THRESHOLD:
   2418         {
   2419             uint16 mode, buffer_len;
   2420             SOC_IF_ERROR_RETURN
   2421                 (bmacsec_phy84334_eee_mode_get(phy_dev_addr, &mode, NULL, NULL, &buffer_len ));
   2422             if ( (mode != 2) || (buffer_len > value)) {
   2423                 return SOC_E_PARAM;
   2424             }
   2425             SOC_IF_ERROR_RETURN
   2426                 (bmacsec_phy84334_eee_mode_set(phy_dev_addr, 2, (uint16)((value >> 16) & 0xffff), (uint16)(value & 0xffff), buffer_len ));
   2427         }
   2428         break;
   2429 
   2430     case SOC_PHY_CONTROL_EEE_STATISTICS_CLEAR:
   2431         SOC_IF_ERROR_RETURN
   2432             (bmacsec_phy84334_eee_statistics_clear(phy_dev_addr));
   2433 
   2434         break;
   2435 
   2436     case SOC_PHY_CONTROL_EEE_AUTO_BUFFER_LIMIT:
   2437     case SOC_PHY_CONTROL_EEE_TRANSMIT_WAKE_TIME:
   2438     case SOC_PHY_CONTROL_EEE_RECEIVE_WAKE_TIME:
   2439     case SOC_PHY_CONTROL_EEE_TRANSMIT_SLEEP_TIME:
   2440     case SOC_PHY_CONTROL_EEE_RECEIVE_SLEEP_TIME:
   2441     case SOC_PHY_CONTROL_EEE_TRANSMIT_QUIET_TIME:
   2442     case SOC_PHY_CONTROL_EEE_RECEIVE_QUIET_TIME:
   2443     case SOC_PHY_CONTROL_EEE_TRANSMIT_REFRESH_TIME:
   2444             return SOC_E_UNAVAIL;
   2445 
   2446 
   2447         default:
   2448             return SOC_E_UNAVAIL;
   2449     }
   2450 
   2451     if (rv != BMACSEC_E_NONE) {
   2452         return SOC_ERROR(rv);
   2453     }
   2454     return SOC_E_NONE;
   2455 }
   2456 
   2457 /*
   2458  * Function:
   2459  *      phy_84334_control_get
   2460  * Purpose:
   2461  *      Get current control settign of the PHY.                                
   2462  * Parameters:
   2463  *      unit  - StrataSwitch unit #.
   2464  *      port  - StrataSwitch port #.
   2465  *      type  - Control to update
   2466  *      value - (OUT)Current setting for the control
   2467  * Returns:
   2468  *      SOC_E_NONE
   2469  */
   2470 STATIC int 
   2471 phy_84334_control_get(int unit, soc_port_t port,
   2472                      soc_phy_control_t type, uint32 *value)
   2473 {
   2474     int rv;
   2475     phy_ctrl_t    *pc;
   2476     bmacsec_dev_addr_t phy_dev_addr;
   2477     buint16_t mode, temp, temp1;
   2478 
   2479     pc = EXT_PHY_SW_STATE(unit, port);
   2480 
   2481     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1); 
   2482 
   2483     if (NULL == value) {
   2484         return SOC_E_PARAM;
   2485     }
   2486 
   2487     if ((type < 0) || (type >= SOC_PHY_CONTROL_COUNT)) {
   2488         return SOC_E_PARAM;
   2489     }
   2490 
   2491     rv = SOC_E_NONE;
   2492     switch(type) {
   2493         case SOC_PHY_CONTROL_MACSEC_SWITCH_FIXED:
   2494             *value = pc->macsec_switch_fixed;
   2495             break;
   2496         case SOC_PHY_CONTROL_MACSEC_SWITCH_FIXED_SPEED:
   2497             *value = pc->macsec_switch_fixed_speed;
   2498             break;
   2499         case SOC_PHY_CONTROL_MACSEC_SWITCH_FIXED_DUPLEX:
   2500             *value = pc->macsec_switch_fixed_duplex;
   2501             break;
   2502         case SOC_PHY_CONTROL_MACSEC_SWITCH_FIXED_PAUSE:
   2503             *value = pc->macsec_switch_fixed_pause;
   2504             break;
   2505         case SOC_PHY_CONTROL_MACSEC_PAUSE_RX_FORWARD:
   2506             *value = pc->macsec_pause_rx_fwd;
   2507             break;
   2508         case SOC_PHY_CONTROL_MACSEC_PAUSE_TX_FORWARD:
   2509             *value = pc->macsec_pause_tx_fwd;
   2510             break;
   2511         case SOC_PHY_CONTROL_MACSEC_LINE_IPG:
   2512             *value = pc->macsec_line_ipg;
   2513             break;
   2514         case SOC_PHY_CONTROL_MACSEC_SWITCH_IPG:
   2515             *value = pc->macsec_switch_ipg;
   2516             break;
   2517 
   2518 
   2519     case SOC_PHY_CONTROL_EEE:
   2520         *value = (PHY_FLAGS_TST(unit, port, PHY_FLAGS_EEE_ENABLED) && 
   2521                  !PHY_FLAGS_TST(unit, port, PHY_FLAGS_EEE_MODE)) ? 1 : 0;
   2522         break;
   2523 
   2524     case SOC_PHY_CONTROL_EEE_AUTO:
   2525         *value = (PHY_FLAGS_TST(unit, port, PHY_FLAGS_EEE_ENABLED) && 
   2526                   PHY_FLAGS_TST(unit, port, PHY_FLAGS_EEE_MODE)) ? 1 : 0;
   2527         break;
   2528 
   2529     case SOC_PHY_CONTROL_EEE_AUTO_FIXED_LATENCY:
   2530         { 
   2531             uint16 mode=0 ,latency=0;
   2532             SOC_IF_ERROR_RETURN
   2533                 (bmacsec_phy84334_eee_mode_get(phy_dev_addr, &mode, NULL, NULL, &latency));
   2534             if (mode == 2 || mode == 6 || mode == 0xa) {
   2535                  *value = 1; 
   2536             }
   2537             else if (mode == 3 || mode == 7 || mode == 0xb) {
   2538                  *value = 0; 
   2539             }
   2540         }
   2541         break;
   2542 
   2543     case SOC_PHY_CONTROL_EEE_AUTO_IDLE_THRESHOLD:
   2544         SOC_IF_ERROR_RETURN
   2545             (bmacsec_phy84334_eee_mode_get(phy_dev_addr, &mode, &temp1, &temp, NULL));
   2546         if (mode != 2) {
   2547             return SOC_E_UNAVAIL;
   2548         }
   2549         *value = (((uint32) temp1) << 16) | temp;
   2550         break;
   2551 
   2552     case SOC_PHY_CONTROL_EEE_TRANSMIT_EVENTS:
   2553         SOC_IF_ERROR_RETURN
   2554             (bmacsec_phy84334_eee_tx_events_get(phy_dev_addr, value));
   2555         break;
   2556 
   2557     case SOC_PHY_CONTROL_EEE_TRANSMIT_DURATION:
   2558         SOC_IF_ERROR_RETURN
   2559             (bmacsec_phy84334_eee_tx_duration_get(phy_dev_addr, value));
   2560         break;
   2561 
   2562     case SOC_PHY_CONTROL_EEE_RECEIVE_EVENTS:
   2563         SOC_IF_ERROR_RETURN
   2564             (bmacsec_phy84334_eee_rx_events_get(phy_dev_addr, value));
   2565         break;
   2566 
   2567     case SOC_PHY_CONTROL_EEE_RECEIVE_DURATION:
   2568         SOC_IF_ERROR_RETURN
   2569             (bmacsec_phy84334_eee_tx_duration_get(phy_dev_addr, value));
   2570         break;
   2571 
   2572         default:
   2573             rv = SOC_E_UNAVAIL;
   2574             break; 
   2575     }
   2576     return rv;
   2577 }
   2578 
   2579 /*
   2580  * Function:
   2581  *      phy_84334_linkup
   2582  * Purpose:
   2583  *      Link up handler
   2584  * Parameters:
   2585  *      unit  - StrataSwitch unit #.
   2586  *      port  - StrataSwitch port #.
   2587  * Returns:
   2588  *      SOC_E_NONE
   2589  */
   2590 STATIC int 
   2591 phy_84334_linkup(int unit, soc_port_t port)
   2592 {
   2593     int rv;
   2594     int line_speed;
   2595     phy_ctrl_t    *pc;
   2596     bmacsec_dev_addr_t phy_dev_addr;
   2597 
   2598 
   2599     pc = EXT_PHY_SW_STATE(unit, port);
   2600 
   2601     SOC_IF_ERROR_RETURN
   2602         (phy_84334_speed_get(unit, port, &line_speed));
   2603 
   2604     switch (line_speed) {
   2605 
   2606     case 10000:
   2607         SOC_IF_ERROR_RETURN
   2608             (soc_phyctrl_notify(unit, port, phyEventInterface, SOC_PORT_IF_XAUI));
   2609         SOC_IF_ERROR_RETURN
   2610             (soc_phyctrl_notify(unit, port, phyEventSpeed, 10000));
   2611         SOC_IF_ERROR_RETURN
   2612             (soc_phyctrl_notify(unit, port, phyEventResume, 1));
   2613         break;
   2614 
   2615     case 1000:
   2616         if (PHY_COPPER_MODE(unit, port)) {
   2617             SOC_IF_ERROR_RETURN
   2618                 (soc_phyctrl_notify(unit, port, phyEventInterface, SOC_PORT_IF_SGMII));
   2619             SOC_IF_ERROR_RETURN
   2620                 (soc_phyctrl_notify(unit, port, phyEventSpeed, 1000));
   2621         } else {
   2622             SOC_IF_ERROR_RETURN
   2623                 (soc_phyctrl_notify(unit, port, phyEventInterface, SOC_PORT_IF_XAUI));
   2624         }
   2625         break;
   2626 
   2627     case 100:
   2628     case 10:
   2629         SOC_IF_ERROR_RETURN
   2630             (soc_phyctrl_notify(unit, port, phyEventInterface, SOC_PORT_IF_SGMII));
   2631         SOC_IF_ERROR_RETURN
   2632             (soc_phyctrl_notify(unit, port, phyEventSpeed, line_speed));
   2633         break;
   2634 
   2635     default:
   2636         break;
   2637     }
   2638 
   2639     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1);
   2640 
   2641     /* Call BMACSEC linkup routine */
   2642     rv = bmacsec_84334_phy_linkup(phy_dev_addr, pc->macsec_enable);
   2643 
   2644     if (BMACSEC_E_FAILURE(rv)) {
   2645         return SOC_E_FAIL;
   2646     }
   2647 
   2648     if (pc->macsec_enable != 1) {
   2649         return SOC_E_NONE;
   2650     }
   2651 
   2652     pc->macsec_switch_fixed_speed = line_speed;
   2653 
   2654 
   2655     /* wait for Power Down of unused MACSEC sub-blocks to complete */
   2656     sal_usleep(400000);
   2657 
   2658     rv = bmacsec_phy84334_switch_side_set_params(phy_dev_addr, 
   2659                                       BMACSEC_BCM84334_SWITCH_FIXED,
   2660                                       pc->macsec_switch_fixed_speed,
   2661                                       pc->macsec_switch_fixed_duplex,
   2662                                       pc->macsec_switch_fixed_pause);
   2663     if (BMACSEC_E_FAILURE(rv)) {
   2664         return SOC_E_FAIL;
   2665     }
   2666 
   2667     return SOC_E_NONE;
   2668 }
   2669 
   2670 /*
   2671  * Function:
   2672  *      phy_84334_firmware_set
   2673  * Purpose:
   2674  *      program the given firmware into the SPI-ROM
   2675  * Parameters:
   2676  *      unit - StrataSwitch unit #.
   2677  *      port - StrataSwitch port #.
   2678  *      offset - offset to the data stream
   2679  *      array  - the given data
   2680  *      datalen- the data length
   2681  * Returns:
   2682  *      SOC_E_NONE
   2683  */
   2684 
   2685 STATIC int
   2686 phy_84334_firmware_set(int unit, int port, int offset, uint8 *data,int len)
   2687 {
   2688     int            rv;
   2689     phy_ctrl_t *pc;
   2690     bmacsec_dev_addr_t phy_dev_addr;
   2691 
   2692     pc = EXT_PHY_SW_STATE(unit, port);
   2693 
   2694     phy_dev_addr = SOC_MACSECPHY_MDIO_ADDR(unit, pc->phy_id, 1);
   2695 
   2696     offset = (data == 0) ? BMACSEC_PHY84334_MAP_UCODE_OFFSET(offset) : 0 ;
   2697     len    = (data == 0) ? (PHY_MODEL(pc->phy_id0, pc->phy_id1))     : len;
   2698 
   2699     rv = bmacsec_phy84334_firmware_set(phy_dev_addr, offset, data, len);
   2700     if (rv != BMACSEC_E_NONE) {
   2701             LOG_WARN(BSL_LS_SOC_PHY,
   2702                      (BSL_META_U(unit,
   2703                                  "PHY84334 firmware upgrade possibly failed:"
   2704                                  "u=%d p=%d\n"), unit, port));
   2705         return (SOC_E_FAIL);
   2706     }
   2707     LOG_INFO(BSL_LS_SOC_PHY,
   2708              (BSL_META_U(unit,
   2709                          "PHY84334 firmware upgrade successful:"
   2710                          "u=%d p=%d\n"), unit, port));
   2711 
   2712 #if 0
   2713     if (data == 0 && offset == BMACSEC_PHY84334_UCODE_BCST_END) {
   2714         soc_timeout_init(&TO(pc), 2000000, 0);
   2715     }
   2716 #endif
   2717 
   2718     return SOC_E_NONE;
   2719 }
   2720 
   2721 /*
   2722  * Function:
   2723  *      phy_84334_probe
   2724  * Purpose:
   2725  *      Complement the generic phy probe routine to identify this phy when its
   2726  *      phy id0 and id1 is same as some other phy's.
   2727  * Parameters:
   2728  *      unit - StrataSwitch unit #.
   2729  *      pc   - phy ctrl descriptor.
   2730  * Returns:
   2731  *      SOC_E_NONE,SOC_E_NOT_FOUND and SOC_E_<error>
   2732  */
   2733 
   2734 STATIC int
   2735 phy_84334_probe(int unit, phy_ctrl_t *pc)
   2736 {
   2737     uint16  id0, id1;
   2738 
   2739     if (READ_PHY84334_PMA_PMD_REG(unit, pc, 0x2, &id0) < 0) {
   2740         return SOC_E_NOT_FOUND;
   2741     }
   2742 
   2743     if (READ_PHY84334_PMA_PMD_REG(unit, pc, 0x3, &id1) < 0) {
   2744         return SOC_E_NOT_FOUND;
   2745     }
   2746 
   2747     switch (PHY_MODEL(id0, id1)) {
   2748 
   2749     case PHY_BCM84334_MODEL:
   2750         if (id1 & 0x8) {
   2751             if (!soc_property_port_get(unit, pc->port, spn_MACSEC_ENABLE, 0)) {
   2752                 break;
   2753             }
   2754             PHY_FLAGS_SET(unit, pc->port, PHY_FLAGS_FORCED_COPPER);
   2755             pc->size = sizeof(PHY8433_PRIV_t);
   2756             return SOC_E_NONE;
   2757         }
   2758     break;
   2759 
   2760     case PHY_BCM84333_MODEL:
   2761     case PHY_BCM84336_MODEL:
   2762         if (id1 & 0x8) {
   2763             if (!soc_property_port_get(unit, pc->port, spn_MACSEC_ENABLE, 0)) {
   2764                 break;
   2765             }
   2766             pc->size = sizeof(PHY8433_PRIV_t);
   2767             return SOC_E_NONE;
   2768         }
   2769     break;
   2770 
   2771     case PHY_BCM84844_MODEL:
   2772     case PHY_BCM84848_MODEL:
   2773 #if 1
   2774         if (!soc_property_port_get(unit, pc->port, spn_MACSEC_ENABLE, 0)) {
   2775             break;
   2776         }
   2777 #endif
   2778         PHY_FLAGS_SET(unit, pc->port, PHY_FLAGS_FORCED_COPPER);
   2779         pc->size = sizeof(PHY8433_PRIV_t);
   2780         return SOC_E_NONE;
   2781     break;
   2782 
   2783     case PHY_BCM84846_MODEL:
   2784 #if 1
   2785         if (!soc_property_port_get(unit, pc->port, spn_MACSEC_ENABLE, 0)) {
   2786             break;
   2787         }
   2788 #endif
   2789         pc->size = sizeof(PHY8433_PRIV_t);
   2790         return SOC_E_NONE;
   2791     break;
   2792 
   2793     default:
   2794     break;
   2795     }
   2796     return SOC_E_NOT_FOUND;
   2797 }
   2798 
   2799 
   2800 #ifdef BROADCOM_DEBUG
   2801 
   2802 /*
   2803  * Function:
   2804  *      phy_84334_shadow_dump
   2805  * Purpose:
   2806  *      Debug routine to dump all shadow registers.
   2807  * Parameters:
   2808  *      unit - StrataSwitch unit #.
   2809  *      port - StrataSwitch port #.
   2810  */
   2811 
   2812 void
   2813 phy_84334_shadow_dump(int unit, soc_port_t port)
   2814 {
   2815     phy_ctrl_t *pc;
   2816     uint16      tmp;
   2817     int         i;
   2818 
   2819     pc       = EXT_PHY_SW_STATE(unit, port);
   2820 
   2821     /* Register 0x18 Shadows */
   2822     for (i = 0; i <= 7; i++) {
   2823         WRITE_PHY_REG(unit, pc, 0x18, (i << 12) | 0x7);
   2824         READ_PHY_REG(unit, pc, 0x18, &tmp);
   2825         if ((tmp & ~7) == 0x0000) {
   2826             continue;
   2827         }
   2828         LOG_CLI((BSL_META_U(unit,
   2829                             "0x18[0x%x]=0x%04x\n"), i, tmp));
   2830     }
   2831 
   2832     /* Register 0x1c Shadows */
   2833     for (i = 0; i <= 0x1f; i++) {
   2834         WRITE_PHY_REG(unit, pc, 0x1c, i << 10);
   2835         READ_PHY_REG(unit, pc, 0x1c, &tmp);
   2836         if ((tmp & ~0x7c00) == 0x0000) {
   2837             continue;
   2838         }
   2839         LOG_CLI((BSL_META_U(unit,
   2840                             "0x1c[0x%x]=0x%04x\n"), i, tmp));
   2841     }
   2842 
   2843     /* Register 0x17/0x15 Shadows */
   2844     for (i = 0; i <= 0x13; i++) {
   2845         WRITE_PHY_REG(unit, pc, 0x17, 0xf00 | i);
   2846         READ_PHY_REG(unit, pc, 0x15, &tmp);
   2847         if (tmp  == 0x0000) {
   2848             continue;
   2849         }
   2850         LOG_CLI((BSL_META_U(unit,
   2851                             "0x17[0x%x]=0x%04x\n"), i, tmp));
   2852     }
   2853 }
   2854 
   2855 #endif /* BROADCOM_DEBUG */
   2856 
   2857 /*
   2858  * Variable:    phy_84334drv_ge
   2859  * Purpose:     PHY driver for 84334
   2860  */
   2861 phy_driver_t phy_84334drv_xe = {
   2862     "84334 (MACSec PHY) Gigabit PHY Driver",
   2863     phy_84334_init,
   2864     phy_84334_reset,
   2865     phy_84334_link_get,
   2866     phy_84334_enable_set,
   2867     phy_84334_enable_get,
   2868     phy_84334_duplex_set,
   2869     phy_84334_duplex_get,
   2870     phy_84334_speed_set,
   2871     phy_84334_speed_get,
   2872     phy_84334_master_set,
   2873     phy_84334_master_get,
   2874     phy_84334_autoneg_set,
   2875     phy_84334_autoneg_get,
   2876     NULL,
   2877     NULL,
   2878     NULL,
   2879     phy_84334_lb_set,
   2880     phy_84334_lb_get,
   2881     phy_null_interface_set,
   2882     phy_xehg_interface_get,
   2883     NULL,
   2884     phy_84334_linkup,            /* Phy link up event */
   2885     NULL,                        /* Phy link down event */
   2886     phy_84334_mdix_set,
   2887     phy_84334_mdix_get,
   2888     phy_84334_mdix_status_get,
   2889     phy_84334_medium_config_set,
   2890     phy_84334_medium_config_get,
   2891     phy_84334_medium_status,
   2892     NULL,                       /* cable diag */
   2893     NULL,                       /* phy_link_change */
   2894     phy_84334_control_set,      /* phy_control_set */ 
   2895     phy_84334_control_get,      /* phy_control_get */
   2896     NULL,            /* phy_ge_reg_read */
   2897     NULL,           /* phy_ge_reg_write */
   2898     NULL,          /* phy_ge_reg_modify */
   2899     NULL,          /* Phy event notify */
   2900     phy_84334_probe,          /* pd_probe  */
   2901     phy_84334_ability_advert_set,  /* pd_ability_advert_set */
   2902     phy_84334_ability_advert_get,  /* pd_ability_advert_get */
   2903     phy_84334_ability_remote_get,  /* pd_ability_remote_get */
   2904     phy_84334_ability_local_get,   /* pd_ability_local_get  */
   2905     phy_84334_firmware_set,
   2906     phy_84334_timesync_config_set,
   2907     phy_84334_timesync_config_get,
   2908     phy_84334_timesync_control_set,
   2909     phy_84334_timesync_control_get
   2910 };
   2911 
   2912 #else /* INCLUDE_PHY_84334 */
   2913 int _soc_phy_84334_not_empty;
   2914 #endif /* INCLUDE_PHY_84334 */
   2915 #endif /* INCLUDE_MACSEC */