1/* Copyright 2008-2009 Broadcom Corporation 2 * 3 * Unless you and Broadcom execute a separate written software license 4 * agreement governing use of this software, this software is licensed to you 5 * under the terms of the GNU General Public License version 2, available 6 * at http://www.gnu.org/licenses/old-licenses/gpl-2.0.html (the "GPL"). 7 * 8 * Notwithstanding the above, under no circumstances may you combine this 9 * software in any way with any other Broadcom software provided under a 10 * license other than the GPL, without Broadcom's express prior written 11 * consent. 12 * 13 * Written by Yaniv Rosner 14 * 15 */ 16 17#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt 18 19#include <linux/kernel.h> 20#include <linux/errno.h> 21#include <linux/pci.h> 22#include <linux/netdevice.h> 23#include <linux/delay.h> 24#include <linux/ethtool.h> 25#include <linux/mutex.h> 26 27#include "bnx2x.h" 28 29/********************************************************/ 30#define ETH_HLEN 14 31#define ETH_OVREHEAD (ETH_HLEN + 8)/* 8 for CRC + VLAN*/ 32#define ETH_MIN_PACKET_SIZE 60 33#define ETH_MAX_PACKET_SIZE 1500 34#define ETH_MAX_JUMBO_PACKET_SIZE 9600 35#define MDIO_ACCESS_TIMEOUT 1000 36#define BMAC_CONTROL_RX_ENABLE 2 37 38/***********************************************************/ 39/* Shortcut definitions */ 40/***********************************************************/ 41 42#define NIG_LATCH_BC_ENABLE_MI_INT 0 43 44#define NIG_STATUS_EMAC0_MI_INT \ 45 NIG_STATUS_INTERRUPT_PORT0_REG_STATUS_EMAC0_MISC_MI_INT 46#define NIG_STATUS_XGXS0_LINK10G \ 47 NIG_STATUS_INTERRUPT_PORT0_REG_STATUS_XGXS0_LINK10G 48#define NIG_STATUS_XGXS0_LINK_STATUS \ 49 NIG_STATUS_INTERRUPT_PORT0_REG_STATUS_XGXS0_LINK_STATUS 50#define NIG_STATUS_XGXS0_LINK_STATUS_SIZE \ 51 NIG_STATUS_INTERRUPT_PORT0_REG_STATUS_XGXS0_LINK_STATUS_SIZE 52#define NIG_STATUS_SERDES0_LINK_STATUS \ 53 NIG_STATUS_INTERRUPT_PORT0_REG_STATUS_SERDES0_LINK_STATUS 54#define NIG_MASK_MI_INT \ 55 NIG_MASK_INTERRUPT_PORT0_REG_MASK_EMAC0_MISC_MI_INT 56#define NIG_MASK_XGXS0_LINK10G \ 57 NIG_MASK_INTERRUPT_PORT0_REG_MASK_XGXS0_LINK10G 58#define NIG_MASK_XGXS0_LINK_STATUS \ 59 NIG_MASK_INTERRUPT_PORT0_REG_MASK_XGXS0_LINK_STATUS 60#define NIG_MASK_SERDES0_LINK_STATUS \ 61 NIG_MASK_INTERRUPT_PORT0_REG_MASK_SERDES0_LINK_STATUS 62 63#define MDIO_AN_CL73_OR_37_COMPLETE \ 64 (MDIO_GP_STATUS_TOP_AN_STATUS1_CL73_AUTONEG_COMPLETE | \ 65 MDIO_GP_STATUS_TOP_AN_STATUS1_CL37_AUTONEG_COMPLETE) 66 67#define XGXS_RESET_BITS \ 68 (MISC_REGISTERS_RESET_REG_3_MISC_NIG_MUX_XGXS0_RSTB_HW | \ 69 MISC_REGISTERS_RESET_REG_3_MISC_NIG_MUX_XGXS0_IDDQ | \ 70 MISC_REGISTERS_RESET_REG_3_MISC_NIG_MUX_XGXS0_PWRDWN | \ 71 MISC_REGISTERS_RESET_REG_3_MISC_NIG_MUX_XGXS0_PWRDWN_SD | \ 72 MISC_REGISTERS_RESET_REG_3_MISC_NIG_MUX_XGXS0_TXD_FIFO_RSTB) 73 74#define SERDES_RESET_BITS \ 75 (MISC_REGISTERS_RESET_REG_3_MISC_NIG_MUX_SERDES0_RSTB_HW | \ 76 MISC_REGISTERS_RESET_REG_3_MISC_NIG_MUX_SERDES0_IDDQ | \ 77 MISC_REGISTERS_RESET_REG_3_MISC_NIG_MUX_SERDES0_PWRDWN | \ 78 MISC_REGISTERS_RESET_REG_3_MISC_NIG_MUX_SERDES0_PWRDWN_SD) 79 80#define AUTONEG_CL37 SHARED_HW_CFG_AN_ENABLE_CL37 81#define AUTONEG_CL73 SHARED_HW_CFG_AN_ENABLE_CL73 82#define AUTONEG_BAM SHARED_HW_CFG_AN_ENABLE_BAM 83#define AUTONEG_PARALLEL \ 84 SHARED_HW_CFG_AN_ENABLE_PARALLEL_DETECTION 85#define AUTONEG_SGMII_FIBER_AUTODET \ 86 SHARED_HW_CFG_AN_EN_SGMII_FIBER_AUTO_DETECT 87#define AUTONEG_REMOTE_PHY SHARED_HW_CFG_AN_ENABLE_REMOTE_PHY 88 89#define GP_STATUS_PAUSE_RSOLUTION_TXSIDE \ 90 MDIO_GP_STATUS_TOP_AN_STATUS1_PAUSE_RSOLUTION_TXSIDE 91#define GP_STATUS_PAUSE_RSOLUTION_RXSIDE \ 92 MDIO_GP_STATUS_TOP_AN_STATUS1_PAUSE_RSOLUTION_RXSIDE 93#define GP_STATUS_SPEED_MASK \ 94 MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_MASK 95#define GP_STATUS_10M MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_10M 96#define GP_STATUS_100M MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_100M 97#define GP_STATUS_1G MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_1G 98#define GP_STATUS_2_5G MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_2_5G 99#define GP_STATUS_5G MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_5G 100#define GP_STATUS_6G MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_6G 101#define GP_STATUS_10G_HIG \ 102 MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_10G_HIG 103#define GP_STATUS_10G_CX4 \ 104 MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_10G_CX4 105#define GP_STATUS_12G_HIG \ 106 MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_12G_HIG 107#define GP_STATUS_12_5G MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_12_5G 108#define GP_STATUS_13G MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_13G 109#define GP_STATUS_15G MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_15G 110#define GP_STATUS_16G MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_16G 111#define GP_STATUS_1G_KX MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_1G_KX 112#define GP_STATUS_10G_KX4 \ 113 MDIO_GP_STATUS_TOP_AN_STATUS1_ACTUAL_SPEED_10G_KX4 114 115#define LINK_10THD LINK_STATUS_SPEED_AND_DUPLEX_10THD 116#define LINK_10TFD LINK_STATUS_SPEED_AND_DUPLEX_10TFD 117#define LINK_100TXHD LINK_STATUS_SPEED_AND_DUPLEX_100TXHD 118#define LINK_100T4 LINK_STATUS_SPEED_AND_DUPLEX_100T4 119#define LINK_100TXFD LINK_STATUS_SPEED_AND_DUPLEX_100TXFD 120#define LINK_1000THD LINK_STATUS_SPEED_AND_DUPLEX_1000THD 121#define LINK_1000TFD LINK_STATUS_SPEED_AND_DUPLEX_1000TFD 122#define LINK_1000XFD LINK_STATUS_SPEED_AND_DUPLEX_1000XFD 123#define LINK_2500THD LINK_STATUS_SPEED_AND_DUPLEX_2500THD 124#define LINK_2500TFD LINK_STATUS_SPEED_AND_DUPLEX_2500TFD 125#define LINK_2500XFD LINK_STATUS_SPEED_AND_DUPLEX_2500XFD 126#define LINK_10GTFD LINK_STATUS_SPEED_AND_DUPLEX_10GTFD 127#define LINK_10GXFD LINK_STATUS_SPEED_AND_DUPLEX_10GXFD 128#define LINK_12GTFD LINK_STATUS_SPEED_AND_DUPLEX_12GTFD 129#define LINK_12GXFD LINK_STATUS_SPEED_AND_DUPLEX_12GXFD 130#define LINK_12_5GTFD LINK_STATUS_SPEED_AND_DUPLEX_12_5GTFD 131#define LINK_12_5GXFD LINK_STATUS_SPEED_AND_DUPLEX_12_5GXFD 132#define LINK_13GTFD LINK_STATUS_SPEED_AND_DUPLEX_13GTFD 133#define LINK_13GXFD LINK_STATUS_SPEED_AND_DUPLEX_13GXFD 134#define LINK_15GTFD LINK_STATUS_SPEED_AND_DUPLEX_15GTFD 135#define LINK_15GXFD LINK_STATUS_SPEED_AND_DUPLEX_15GXFD 136#define LINK_16GTFD LINK_STATUS_SPEED_AND_DUPLEX_16GTFD 137#define LINK_16GXFD LINK_STATUS_SPEED_AND_DUPLEX_16GXFD 138 139#define PHY_XGXS_FLAG 0x1 140#define PHY_SGMII_FLAG 0x2 141#define PHY_SERDES_FLAG 0x4 142 143/* */ 144#define SFP_EEPROM_CON_TYPE_ADDR 0x2 145 #define SFP_EEPROM_CON_TYPE_VAL_LC 0x7 146 #define SFP_EEPROM_CON_TYPE_VAL_COPPER 0x21 147 148 149#define SFP_EEPROM_COMP_CODE_ADDR 0x3 150 #define SFP_EEPROM_COMP_CODE_SR_MASK (1<<4) 151 #define SFP_EEPROM_COMP_CODE_LR_MASK (1<<5) 152 #define SFP_EEPROM_COMP_CODE_LRM_MASK (1<<6) 153 154#define SFP_EEPROM_FC_TX_TECH_ADDR 0x8 155 #define SFP_EEPROM_FC_TX_TECH_BITMASK_COPPER_PASSIVE 0x4 156 #define SFP_EEPROM_FC_TX_TECH_BITMASK_COPPER_ACTIVE 0x8 157 158#define SFP_EEPROM_OPTIONS_ADDR 0x40 159 #define SFP_EEPROM_OPTIONS_LINEAR_RX_OUT_MASK 0x1 160#define SFP_EEPROM_OPTIONS_SIZE 2 161 162#define EDC_MODE_LINEAR 0x0022 163#define EDC_MODE_LIMITING 0x0044 164#define EDC_MODE_PASSIVE_DAC 0x0055 165 166 167 168/**********************************************************/ 169/* INTERFACE */ 170/**********************************************************/ 171#define CL45_WR_OVER_CL22(_bp, _port, _phy_addr, _bank, _addr, _val) \ 172 bnx2x_cl45_write(_bp, _port, 0, _phy_addr, \ 173 DEFAULT_PHY_DEV_ADDR, \ 174 (_bank + (_addr & 0xf)), \ 175 _val) 176 177#define CL45_RD_OVER_CL22(_bp, _port, _phy_addr, _bank, _addr, _val) \ 178 bnx2x_cl45_read(_bp, _port, 0, _phy_addr, \ 179 DEFAULT_PHY_DEV_ADDR, \ 180 (_bank + (_addr & 0xf)), \ 181 _val) 182 183static void bnx2x_set_serdes_access(struct link_params *params) 184{ 185 struct bnx2x *bp = params->bp; 186 u32 emac_base = (params->port) ? GRCBASE_EMAC1 : GRCBASE_EMAC0; 187 188 /* Set Clause 22 */ 189 REG_WR(bp, NIG_REG_SERDES0_CTRL_MD_ST + params->port*0x10, 1); 190 REG_WR(bp, emac_base + EMAC_REG_EMAC_MDIO_COMM, 0x245f8000); 191 udelay(500); 192 REG_WR(bp, emac_base + EMAC_REG_EMAC_MDIO_COMM, 0x245d000f); 193 udelay(500); 194 /* Set Clause 45 */ 195 REG_WR(bp, NIG_REG_SERDES0_CTRL_MD_ST + params->port*0x10, 0); 196} 197static void bnx2x_set_phy_mdio(struct link_params *params, u8 phy_flags) 198{ 199 struct bnx2x *bp = params->bp; 200 201 if (phy_flags & PHY_XGXS_FLAG) { 202 REG_WR(bp, NIG_REG_XGXS0_CTRL_MD_ST + 203 params->port*0x18, 0); 204 REG_WR(bp, NIG_REG_XGXS0_CTRL_MD_DEVAD + params->port*0x18, 205 DEFAULT_PHY_DEV_ADDR); 206 } else { 207 bnx2x_set_serdes_access(params); 208 209 REG_WR(bp, NIG_REG_SERDES0_CTRL_MD_DEVAD + 210 params->port*0x10, 211 DEFAULT_PHY_DEV_ADDR); 212 } 213} 214 215static u32 bnx2x_bits_en(struct bnx2x *bp, u32 reg, u32 bits) 216{ 217 u32 val = REG_RD(bp, reg); 218 219 val |= bits; 220 REG_WR(bp, reg, val); 221 return val; 222} 223 224static u32 bnx2x_bits_dis(struct bnx2x *bp, u32 reg, u32 bits) 225{ 226 u32 val = REG_RD(bp, reg); 227 228 val &= ~bits; 229 REG_WR(bp, reg, val); 230 return val; 231} 232 233static void bnx2x_emac_init(struct link_params *params, 234 struct link_vars *vars) 235{ 236 /* reset and unreset the emac core */ 237 struct bnx2x *bp = params->bp; 238 u8 port = params->port; 239 u32 emac_base = port ? GRCBASE_EMAC1 : GRCBASE_EMAC0; 240 u32 val; 241 u16 timeout; 242 243 REG_WR(bp, GRCBASE_MISC + MISC_REGISTERS_RESET_REG_2_CLEAR, 244 (MISC_REGISTERS_RESET_REG_2_RST_EMAC0_HARD_CORE << port)); 245 udelay(5); 246 REG_WR(bp, GRCBASE_MISC + MISC_REGISTERS_RESET_REG_2_SET, 247 (MISC_REGISTERS_RESET_REG_2_RST_EMAC0_HARD_CORE << port)); 248 249 /* init emac - use read-modify-write */ 250 /* self clear reset */ 251 val = REG_RD(bp, emac_base + EMAC_REG_EMAC_MODE); 252 EMAC_WR(bp, EMAC_REG_EMAC_MODE, (val | EMAC_MODE_RESET)); 253 254 timeout = 200; 255 do { 256 val = REG_RD(bp, emac_base + EMAC_REG_EMAC_MODE); 257 DP(NETIF_MSG_LINK, "EMAC reset reg is %u\n", val); 258 if (!timeout) { 259 DP(NETIF_MSG_LINK, "EMAC timeout!\n"); 260 return; 261 } 262 timeout--; 263 } while (val & EMAC_MODE_RESET); 264 265 /* Set mac address */ 266 val = ((params->mac_addr[0] << 8) | 267 params->mac_addr[1]); 268 EMAC_WR(bp, EMAC_REG_EMAC_MAC_MATCH, val); 269 270 val = ((params->mac_addr[2] << 24) | 271 (params->mac_addr[3] << 16) | 272 (params->mac_addr[4] << 8) | 273 params->mac_addr[5]); 274 EMAC_WR(bp, EMAC_REG_EMAC_MAC_MATCH + 4, val); 275} 276 277static u8 bnx2x_emac_enable(struct link_params *params, 278 struct link_vars *vars, u8 lb) 279{ 280 struct bnx2x *bp = params->bp; 281 u8 port = params->port; 282 u32 emac_base = port ? GRCBASE_EMAC1 : GRCBASE_EMAC0; 283 u32 val; 284 285 DP(NETIF_MSG_LINK, "enabling EMAC\n"); 286 287 /* enable emac and not bmac */ 288 REG_WR(bp, NIG_REG_EGRESS_EMAC0_PORT + port*4, 1); 289 290 /* for paladium */ 291 if (CHIP_REV_IS_EMUL(bp)) { 292 /* Use lane 1 (of lanes 0-3) */ 293 REG_WR(bp, NIG_REG_XGXS_LANE_SEL_P0 + port*4, 1); 294 REG_WR(bp, NIG_REG_XGXS_SERDES0_MODE_SEL + 295 port*4, 1); 296 } 297 /* for fpga */ 298 else 299 300 if (CHIP_REV_IS_FPGA(bp)) { 301 /* Use lane 1 (of lanes 0-3) */ 302 DP(NETIF_MSG_LINK, "bnx2x_emac_enable: Setting FPGA\n"); 303 304 REG_WR(bp, NIG_REG_XGXS_LANE_SEL_P0 + port*4, 1); 305 REG_WR(bp, NIG_REG_XGXS_SERDES0_MODE_SEL + port*4, 306 0); 307 } else 308 /* ASIC */ 309 if (vars->phy_flags & PHY_XGXS_FLAG) { 310 u32 ser_lane = ((params->lane_config & 311 PORT_HW_CFG_LANE_SWAP_CFG_MASTER_MASK) >> 312 PORT_HW_CFG_LANE_SWAP_CFG_MASTER_SHIFT); 313 314 DP(NETIF_MSG_LINK, "XGXS\n"); 315 /* select the master lanes (out of 0-3) */ 316 REG_WR(bp, NIG_REG_XGXS_LANE_SEL_P0 + 317 port*4, ser_lane); 318 /* select XGXS */ 319 REG_WR(bp, NIG_REG_XGXS_SERDES0_MODE_SEL + 320 port*4, 1); 321 322 } else { /* SerDes */ 323 DP(NETIF_MSG_LINK, "SerDes\n"); 324 /* select SerDes */ 325 REG_WR(bp, NIG_REG_XGXS_SERDES0_MODE_SEL + 326 port*4, 0); 327 } 328 329 bnx2x_bits_en(bp, emac_base + EMAC_REG_EMAC_RX_MODE, 330 EMAC_RX_MODE_RESET); 331 bnx2x_bits_en(bp, emac_base + EMAC_REG_EMAC_TX_MODE, 332 EMAC_TX_MODE_RESET); 333 334 if (CHIP_REV_IS_SLOW(bp)) { 335 /* config GMII mode */ 336 val = REG_RD(bp, emac_base + EMAC_REG_EMAC_MODE); 337 EMAC_WR(bp, EMAC_REG_EMAC_MODE, 338 (val | EMAC_MODE_PORT_GMII)); 339 } else { /* ASIC */ 340 /* pause enable/disable */ 341 bnx2x_bits_dis(bp, emac_base + EMAC_REG_EMAC_RX_MODE, 342 EMAC_RX_MODE_FLOW_EN); 343 if (vars->flow_ctrl & BNX2X_FLOW_CTRL_RX) 344 bnx2x_bits_en(bp, emac_base + 345 EMAC_REG_EMAC_RX_MODE, 346 EMAC_RX_MODE_FLOW_EN); 347 348 bnx2x_bits_dis(bp, emac_base + EMAC_REG_EMAC_TX_MODE, 349 (EMAC_TX_MODE_EXT_PAUSE_EN | 350 EMAC_TX_MODE_FLOW_EN)); 351 if (vars->flow_ctrl & BNX2X_FLOW_CTRL_TX) 352 bnx2x_bits_en(bp, emac_base + 353 EMAC_REG_EMAC_TX_MODE, 354 (EMAC_TX_MODE_EXT_PAUSE_EN | 355 EMAC_TX_MODE_FLOW_EN)); 356 } 357 358 /* KEEP_VLAN_TAG, promiscuous */ 359 val = REG_RD(bp, emac_base + EMAC_REG_EMAC_RX_MODE); 360 val |= EMAC_RX_MODE_KEEP_VLAN_TAG | EMAC_RX_MODE_PROMISCUOUS; 361 EMAC_WR(bp, EMAC_REG_EMAC_RX_MODE, val); 362 363 /* Set Loopback */ 364 val = REG_RD(bp, emac_base + EMAC_REG_EMAC_MODE); 365 if (lb) 366 val |= 0x810; 367 else 368 val &= ~0x810; 369 EMAC_WR(bp, EMAC_REG_EMAC_MODE, val); 370 371 /* enable emac */ 372 REG_WR(bp, NIG_REG_NIG_EMAC0_EN + port*4, 1); 373 374 /* enable emac for jumbo packets */ 375 EMAC_WR(bp, EMAC_REG_EMAC_RX_MTU_SIZE, 376 (EMAC_RX_MTU_SIZE_JUMBO_ENA | 377 (ETH_MAX_JUMBO_PACKET_SIZE + ETH_OVREHEAD))); 378 379 /* strip CRC */ 380 REG_WR(bp, NIG_REG_NIG_INGRESS_EMAC0_NO_CRC + port*4, 0x1); 381 382 /* disable the NIG in/out to the bmac */ 383 REG_WR(bp, NIG_REG_BMAC0_IN_EN + port*4, 0x0); 384 REG_WR(bp, NIG_REG_BMAC0_PAUSE_OUT_EN + port*4, 0x0); 385 REG_WR(bp, NIG_REG_BMAC0_OUT_EN + port*4, 0x0); 386 387 /* enable the NIG in/out to the emac */ 388 REG_WR(bp, NIG_REG_EMAC0_IN_EN + port*4, 0x1); 389 val = 0; 390 if (vars->flow_ctrl & BNX2X_FLOW_CTRL_TX) 391 val = 1; 392 393 REG_WR(bp, NIG_REG_EMAC0_PAUSE_OUT_EN + port*4, val); 394 REG_WR(bp, NIG_REG_EGRESS_EMAC0_OUT_EN + port*4, 0x1); 395 396 if (CHIP_REV_IS_EMUL(bp)) { 397 /* take the BigMac out of reset */ 398 REG_WR(bp, 399 GRCBASE_MISC + MISC_REGISTERS_RESET_REG_2_SET, 400 (MISC_REGISTERS_RESET_REG_2_RST_BMAC0 << port)); 401 402 /* enable access for bmac registers */ 403 REG_WR(bp, NIG_REG_BMAC0_REGS_OUT_EN + port*4, 0x1); 404 } else 405 REG_WR(bp, NIG_REG_BMAC0_REGS_OUT_EN + port*4, 0x0); 406 407 vars->mac_type = MAC_TYPE_EMAC; 408 return 0; 409} 410 411 412 413static u8 bnx2x_bmac_enable(struct link_params *params, struct link_vars *vars, 414 u8 is_lb) 415{ 416 struct bnx2x *bp = params->bp; 417 u8 port = params->port; 418 u32 bmac_addr = port ? NIG_REG_INGRESS_BMAC1_MEM : 419 NIG_REG_INGRESS_BMAC0_MEM; 420 u32 wb_data[2]; 421 u32 val; 422 423 DP(NETIF_MSG_LINK, "Enabling BigMAC\n"); 424 /* reset and unreset the BigMac */ 425 REG_WR(bp, GRCBASE_MISC + MISC_REGISTERS_RESET_REG_2_CLEAR, 426 (MISC_REGISTERS_RESET_REG_2_RST_BMAC0 << port)); 427 msleep(1); 428 429 REG_WR(bp, GRCBASE_MISC + MISC_REGISTERS_RESET_REG_2_SET, 430 (MISC_REGISTERS_RESET_REG_2_RST_BMAC0 << port)); 431 432 /* enable access for bmac registers */ 433 REG_WR(bp, NIG_REG_BMAC0_REGS_OUT_EN + port*4, 0x1); 434 435 /* XGXS control */ 436 wb_data[0] = 0x3c; 437 wb_data[1] = 0; 438 REG_WR_DMAE(bp, bmac_addr + 439 BIGMAC_REGISTER_BMAC_XGXS_CONTROL, 440 wb_data, 2); 441 442 /* tx MAC SA */ 443 wb_data[0] = ((params->mac_addr[2] << 24) | 444 (params->mac_addr[3] << 16) | 445 (params->mac_addr[4] << 8) | 446 params->mac_addr[5]); 447 wb_data[1] = ((params->mac_addr[0] << 8) | 448 params->mac_addr[1]); 449 REG_WR_DMAE(bp, bmac_addr + BIGMAC_REGISTER_TX_SOURCE_ADDR, 450 wb_data, 2); 451 452 /* tx control */ 453 val = 0xc0; 454 if (vars->flow_ctrl & BNX2X_FLOW_CTRL_TX) 455 val |= 0x800000; 456 wb_data[0] = val; 457 wb_data[1] = 0; 458 REG_WR_DMAE(bp, bmac_addr + BIGMAC_REGISTER_TX_CONTROL, 459 wb_data, 2); 460 461 /* mac control */ 462 val = 0x3; 463 if (is_lb) { 464 val |= 0x4; 465 DP(NETIF_MSG_LINK, "enable bmac loopback\n"); 466 } 467 wb_data[0] = val; 468 wb_data[1] = 0; 469 REG_WR_DMAE(bp, bmac_addr + BIGMAC_REGISTER_BMAC_CONTROL, 470 wb_data, 2); 471 472 /* set rx mtu */ 473 wb_data[0] = ETH_MAX_JUMBO_PACKET_SIZE + ETH_OVREHEAD; 474 wb_data[1] = 0; 475 REG_WR_DMAE(bp, bmac_addr + BIGMAC_REGISTER_RX_MAX_SIZE, 476 wb_data, 2); 477 478 /* rx control set to don't strip crc */ 479 val = 0x14; 480 if (vars->flow_ctrl & BNX2X_FLOW_CTRL_RX) 481 val |= 0x20; 482 wb_data[0] = val; 483 wb_data[1] = 0; 484 REG_WR_DMAE(bp, bmac_addr + BIGMAC_REGISTER_RX_CONTROL, 485 wb_data, 2); 486 487 /* set tx mtu */ 488 wb_data[0] = ETH_MAX_JUMBO_PACKET_SIZE + ETH_OVREHEAD; 489 wb_data[1] = 0; 490 REG_WR_DMAE(bp, bmac_addr + BIGMAC_REGISTER_TX_MAX_SIZE, 491 wb_data, 2); 492 493 /* set cnt max size */ 494 wb_data[0] = ETH_MAX_JUMBO_PACKET_SIZE + ETH_OVREHEAD; 495 wb_data[1] = 0; 496 REG_WR_DMAE(bp, bmac_addr + BIGMAC_REGISTER_CNT_MAX_SIZE, 497 wb_data, 2); 498 499 /* configure safc */ 500 wb_data[0] = 0x1000200; 501 wb_data[1] = 0; 502 REG_WR_DMAE(bp, bmac_addr + BIGMAC_REGISTER_RX_LLFC_MSG_FLDS, 503 wb_data, 2); 504 /* fix for emulation */ 505 if (CHIP_REV_IS_EMUL(bp)) { 506 wb_data[0] = 0xf000; 507 wb_data[1] = 0; 508 REG_WR_DMAE(bp, 509 bmac_addr + BIGMAC_REGISTER_TX_PAUSE_THRESHOLD, 510 wb_data, 2); 511 } 512 513 REG_WR(bp, NIG_REG_XGXS_SERDES0_MODE_SEL + port*4, 0x1); 514 REG_WR(bp, NIG_REG_XGXS_LANE_SEL_P0 + port*4, 0x0); 515 REG_WR(bp, NIG_REG_EGRESS_EMAC0_PORT + port*4, 0x0); 516 val = 0; 517 if (vars->flow_ctrl & BNX2X_FLOW_CTRL_TX) 518 val = 1; 519 REG_WR(bp, NIG_REG_BMAC0_PAUSE_OUT_EN + port*4, val); 520 REG_WR(bp, NIG_REG_EGRESS_EMAC0_OUT_EN + port*4, 0x0); 521 REG_WR(bp, NIG_REG_EMAC0_IN_EN + port*4, 0x0); 522 REG_WR(bp, NIG_REG_EMAC0_PAUSE_OUT_EN + port*4, 0x0); 523 REG_WR(bp, NIG_REG_BMAC0_IN_EN + port*4, 0x1); 524 REG_WR(bp, NIG_REG_BMAC0_OUT_EN + port*4, 0x1); 525 526 vars->mac_type = MAC_TYPE_BMAC; 527 return 0; 528} 529 530static void bnx2x_phy_deassert(struct link_params *params, u8 phy_flags) 531{ 532 struct bnx2x *bp = params->bp; 533 u32 val; 534 535 if (phy_flags & PHY_XGXS_FLAG) { 536 DP(NETIF_MSG_LINK, "bnx2x_phy_deassert:XGXS\n"); 537 val = XGXS_RESET_BITS; 538 539 } else { /* SerDes */ 540 DP(NETIF_MSG_LINK, "bnx2x_phy_deassert:SerDes\n"); 541 val = SERDES_RESET_BITS; 542 } 543 544 val = val << (params->port*16); 545 546 /* reset and unreset the SerDes/XGXS */ 547 REG_WR(bp, GRCBASE_MISC + MISC_REGISTERS_RESET_REG_3_CLEAR, 548 val); 549 udelay(500); 550 REG_WR(bp, GRCBASE_MISC + MISC_REGISTERS_RESET_REG_3_SET, 551 val); 552 bnx2x_set_phy_mdio(params, phy_flags); 553} 554 555void bnx2x_link_status_update(struct link_params *params, 556 struct link_vars *vars) 557{ 558 struct bnx2x *bp = params->bp; 559 u8 link_10g; 560 u8 port = params->port; 561 562 if (params->switch_cfg == SWITCH_CFG_1G) 563 vars->phy_flags = PHY_SERDES_FLAG; 564 else 565 vars->phy_flags = PHY_XGXS_FLAG; 566 vars->link_status = REG_RD(bp, params->shmem_base + 567 offsetof(struct shmem_region, 568 port_mb[port].link_status)); 569 570 vars->link_up = (vars->link_status & LINK_STATUS_LINK_UP); 571 572 if (vars->link_up) { 573 DP(NETIF_MSG_LINK, "phy link up\n"); 574 575 vars->phy_link_up = 1; 576 vars->duplex = DUPLEX_FULL; 577 switch (vars->link_status & 578 LINK_STATUS_SPEED_AND_DUPLEX_MASK) { 579 case LINK_10THD: 580 vars->duplex = DUPLEX_HALF; 581 /* fall thru */ 582 case LINK_10TFD: 583 vars->line_speed = SPEED_10; 584 break; 585 586 case LINK_100TXHD: 587 vars->duplex = DUPLEX_HALF; 588 /* fall thru */ 589 case LINK_100T4: 590 case LINK_100TXFD: 591 vars->line_speed = SPEED_100; 592 break; 593 594 case LINK_1000THD: 595 vars->duplex = DUPLEX_HALF; 596 /* fall thru */ 597 case LINK_1000TFD: 598 vars->line_speed = SPEED_1000; 599 break; 600 601 case LINK_2500THD: 602 vars->duplex = DUPLEX_HALF; 603 /* fall thru */ 604 case LINK_2500TFD: 605 vars->line_speed = SPEED_2500; 606 break; 607 608 case LINK_10GTFD: 609 vars->line_speed = SPEED_10000; 610 break; 611 612 case LINK_12GTFD: 613 vars->line_speed = SPEED_12000; 614 break; 615 616 case LINK_12_5GTFD: 617 vars->line_speed = SPEED_12500; 618 break; 619 620 case LINK_13GTFD: 621 vars->line_speed = SPEED_13000; 622 break; 623 624 case LINK_15GTFD: 625 vars->line_speed = SPEED_15000; 626 break; 627 628 case LINK_16GTFD: 629 vars->line_speed = SPEED_16000; 630 break; 631 632 default: 633 break; 634 } 635 636 if (vars->link_status & LINK_STATUS_TX_FLOW_CONTROL_ENABLED) 637 vars->flow_ctrl |= BNX2X_FLOW_CTRL_TX; 638 else 639 vars->flow_ctrl &= ~BNX2X_FLOW_CTRL_TX; 640 641 if (vars->link_status & LINK_STATUS_RX_FLOW_CONTROL_ENABLED) 642 vars->flow_ctrl |= BNX2X_FLOW_CTRL_RX; 643 else 644 vars->flow_ctrl &= ~BNX2X_FLOW_CTRL_RX; 645 646 if (vars->phy_flags & PHY_XGXS_FLAG) { 647 if (vars->line_speed && 648 ((vars->line_speed == SPEED_10) || 649 (vars->line_speed == SPEED_100))) { 650 vars->phy_flags |= PHY_SGMII_FLAG; 651 } else { 652 vars->phy_flags &= ~PHY_SGMII_FLAG; 653 } 654 } 655 656 /* anything 10 and over uses the bmac */ 657 link_10g = ((vars->line_speed == SPEED_10000) || 658 (vars->line_speed == SPEED_12000) || 659 (vars->line_speed == SPEED_12500) || 660 (vars->line_speed == SPEED_13000) || 661 (vars->line_speed == SPEED_15000) || 662 (vars->line_speed == SPEED_16000)); 663 if (link_10g) 664 vars->mac_type = MAC_TYPE_BMAC; 665 else 666 vars->mac_type = MAC_TYPE_EMAC; 667 668 } else { /* link down */ 669 DP(NETIF_MSG_LINK, "phy link down\n"); 670 671 vars->phy_link_up = 0; 672 673 vars->line_speed = 0; 674 vars->duplex = DUPLEX_FULL; 675 vars->flow_ctrl = BNX2X_FLOW_CTRL_NONE; 676 677 /* indicate no mac active */ 678 vars->mac_type = MAC_TYPE_NONE; 679 } 680 681 DP(NETIF_MSG_LINK, "link_status 0x%x phy_link_up %x\n", 682 vars->link_status, vars->phy_link_up); 683 DP(NETIF_MSG_LINK, "line_speed %x duplex %x flow_ctrl 0x%x\n", 684 vars->line_speed, vars->duplex, vars->flow_ctrl); 685} 686 687static void bnx2x_update_mng(struct link_params *params, u32 link_status) 688{ 689 struct bnx2x *bp = params->bp; 690 691 REG_WR(bp, params->shmem_base + 692 offsetof(struct shmem_region, 693 port_mb[params->port].link_status), 694 link_status); 695} 696 697static void bnx2x_bmac_rx_disable(struct bnx2x *bp, u8 port) 698{ 699 u32 bmac_addr = port ? NIG_REG_INGRESS_BMAC1_MEM : 700 NIG_REG_INGRESS_BMAC0_MEM; 701 u32 wb_data[2]; 702 u32 nig_bmac_enable = REG_RD(bp, NIG_REG_BMAC0_REGS_OUT_EN + port*4); 703 704 /* Only if the bmac is out of reset */ 705 if (REG_RD(bp, MISC_REG_RESET_REG_2) & 706 (MISC_REGISTERS_RESET_REG_2_RST_BMAC0 << port) && 707 nig_bmac_enable) { 708 709 /* Clear Rx Enable bit in BMAC_CONTROL register */ 710 REG_RD_DMAE(bp, bmac_addr + BIGMAC_REGISTER_BMAC_CONTROL, 711 wb_data, 2); 712 wb_data[0] &= ~BMAC_CONTROL_RX_ENABLE; 713 REG_WR_DMAE(bp, bmac_addr + BIGMAC_REGISTER_BMAC_CONTROL, 714 wb_data, 2); 715 716 msleep(1); 717 } 718} 719 720static u8 bnx2x_pbf_update(struct link_params *params, u32 flow_ctrl, 721 u32 line_speed) 722{ 723 struct bnx2x *bp = params->bp; 724 u8 port = params->port; 725 u32 init_crd, crd; 726 u32 count = 1000; 727 728 /* disable port */ 729 REG_WR(bp, PBF_REG_DISABLE_NEW_TASK_PROC_P0 + port*4, 0x1); 730 731 /* wait for init credit */ 732 init_crd = REG_RD(bp, PBF_REG_P0_INIT_CRD + port*4); 733 crd = REG_RD(bp, PBF_REG_P0_CREDIT + port*8); 734 DP(NETIF_MSG_LINK, "init_crd 0x%x crd 0x%x\n", init_crd, crd); 735 736 while ((init_crd != crd) && count) { 737 msleep(5); 738 739 crd = REG_RD(bp, PBF_REG_P0_CREDIT + port*8); 740 count--; 741 } 742 crd = REG_RD(bp, PBF_REG_P0_CREDIT + port*8); 743 if (init_crd != crd) { 744 DP(NETIF_MSG_LINK, "BUG! init_crd 0x%x != crd 0x%x\n", 745 init_crd, crd); 746 return -EINVAL; 747 } 748 749 if (flow_ctrl & BNX2X_FLOW_CTRL_RX || 750 line_speed == SPEED_10 || 751 line_speed == SPEED_100 || 752 line_speed == SPEED_1000 || 753 line_speed == SPEED_2500) { 754 REG_WR(bp, PBF_REG_P0_PAUSE_ENABLE + port*4, 1); 755 /* update threshold */ 756 REG_WR(bp, PBF_REG_P0_ARB_THRSH + port*4, 0); 757 /* update init credit */ 758 init_crd = 778; /* (800-18-4) */ 759 760 } else { 761 u32 thresh = (ETH_MAX_JUMBO_PACKET_SIZE + 762 ETH_OVREHEAD)/16; 763 REG_WR(bp, PBF_REG_P0_PAUSE_ENABLE + port*4, 0); 764 /* update threshold */ 765 REG_WR(bp, PBF_REG_P0_ARB_THRSH + port*4, thresh); 766 /* update init credit */ 767 switch (line_speed) { 768 case SPEED_10000: 769 init_crd = thresh + 553 - 22; 770 break; 771 772 case SPEED_12000: 773 init_crd = thresh + 664 - 22; 774 break; 775 776 case SPEED_13000: 777 init_crd = thresh + 742 - 22; 778 break; 779 780 case SPEED_16000: 781 init_crd = thresh + 778 - 22; 782 break; 783 default: 784 DP(NETIF_MSG_LINK, "Invalid line_speed 0x%x\n", 785 line_speed); 786 return -EINVAL; 787 } 788 } 789 REG_WR(bp, PBF_REG_P0_INIT_CRD + port*4, init_crd); 790 DP(NETIF_MSG_LINK, "PBF updated to speed %d credit %d\n", 791 line_speed, init_crd); 792 793 /* probe the credit changes */ 794 REG_WR(bp, PBF_REG_INIT_P0 + port*4, 0x1); 795 msleep(5); 796 REG_WR(bp, PBF_REG_INIT_P0 + port*4, 0x0); 797 798 /* enable port */ 799 REG_WR(bp, PBF_REG_DISABLE_NEW_TASK_PROC_P0 + port*4, 0x0); 800 return 0; 801} 802 803static u32 bnx2x_get_emac_base(struct bnx2x *bp, u32 ext_phy_type, u8 port) 804{ 805 u32 emac_base; 806 807 switch (ext_phy_type) { 808 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072: 809 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726: 810 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727: 811 /* All MDC/MDIO is directed through single EMAC */ 812 if (REG_RD(bp, NIG_REG_PORT_SWAP)) 813 emac_base = GRCBASE_EMAC0; 814 else 815 emac_base = GRCBASE_EMAC1; 816 break; 817 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073: 818 emac_base = (port) ? GRCBASE_EMAC0 : GRCBASE_EMAC1; 819 break; 820 default: 821 emac_base = (port) ? GRCBASE_EMAC1 : GRCBASE_EMAC0; 822 break; 823 } 824 return emac_base; 825 826} 827 828u8 bnx2x_cl45_write(struct bnx2x *bp, u8 port, u32 ext_phy_type, 829 u8 phy_addr, u8 devad, u16 reg, u16 val) 830{ 831 u32 tmp, saved_mode; 832 u8 i, rc = 0; 833 u32 mdio_ctrl = bnx2x_get_emac_base(bp, ext_phy_type, port); 834 835 /* set clause 45 mode, slow down the MDIO clock to 2.5MHz 836 * (a value of 49==0x31) and make sure that the AUTO poll is off 837 */ 838 839 saved_mode = REG_RD(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_MODE); 840 tmp = saved_mode & ~(EMAC_MDIO_MODE_AUTO_POLL | 841 EMAC_MDIO_MODE_CLOCK_CNT); 842 tmp |= (EMAC_MDIO_MODE_CLAUSE_45 | 843 (49 << EMAC_MDIO_MODE_CLOCK_CNT_BITSHIFT)); 844 REG_WR(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_MODE, tmp); 845 REG_RD(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_MODE); 846 udelay(40); 847 848 /* address */ 849 850 tmp = ((phy_addr << 21) | (devad << 16) | reg | 851 EMAC_MDIO_COMM_COMMAND_ADDRESS | 852 EMAC_MDIO_COMM_START_BUSY); 853 REG_WR(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_COMM, tmp); 854 855 for (i = 0; i < 50; i++) { 856 udelay(10); 857 858 tmp = REG_RD(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_COMM); 859 if (!(tmp & EMAC_MDIO_COMM_START_BUSY)) { 860 udelay(5); 861 break; 862 } 863 } 864 if (tmp & EMAC_MDIO_COMM_START_BUSY) { 865 DP(NETIF_MSG_LINK, "write phy register failed\n"); 866 rc = -EFAULT; 867 } else { 868 /* data */ 869 tmp = ((phy_addr << 21) | (devad << 16) | val | 870 EMAC_MDIO_COMM_COMMAND_WRITE_45 | 871 EMAC_MDIO_COMM_START_BUSY); 872 REG_WR(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_COMM, tmp); 873 874 for (i = 0; i < 50; i++) { 875 udelay(10); 876 877 tmp = REG_RD(bp, mdio_ctrl + 878 EMAC_REG_EMAC_MDIO_COMM); 879 if (!(tmp & EMAC_MDIO_COMM_START_BUSY)) { 880 udelay(5); 881 break; 882 } 883 } 884 if (tmp & EMAC_MDIO_COMM_START_BUSY) { 885 DP(NETIF_MSG_LINK, "write phy register failed\n"); 886 rc = -EFAULT; 887 } 888 } 889 890 /* Restore the saved mode */ 891 REG_WR(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_MODE, saved_mode); 892 893 return rc; 894} 895 896u8 bnx2x_cl45_read(struct bnx2x *bp, u8 port, u32 ext_phy_type, 897 u8 phy_addr, u8 devad, u16 reg, u16 *ret_val) 898{ 899 u32 val, saved_mode; 900 u16 i; 901 u8 rc = 0; 902 903 u32 mdio_ctrl = bnx2x_get_emac_base(bp, ext_phy_type, port); 904 /* set clause 45 mode, slow down the MDIO clock to 2.5MHz 905 * (a value of 49==0x31) and make sure that the AUTO poll is off 906 */ 907 908 saved_mode = REG_RD(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_MODE); 909 val = saved_mode & ((EMAC_MDIO_MODE_AUTO_POLL | 910 EMAC_MDIO_MODE_CLOCK_CNT)); 911 val |= (EMAC_MDIO_MODE_CLAUSE_45 | 912 (49L << EMAC_MDIO_MODE_CLOCK_CNT_BITSHIFT)); 913 REG_WR(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_MODE, val); 914 REG_RD(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_MODE); 915 udelay(40); 916 917 /* address */ 918 val = ((phy_addr << 21) | (devad << 16) | reg | 919 EMAC_MDIO_COMM_COMMAND_ADDRESS | 920 EMAC_MDIO_COMM_START_BUSY); 921 REG_WR(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_COMM, val); 922 923 for (i = 0; i < 50; i++) { 924 udelay(10); 925 926 val = REG_RD(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_COMM); 927 if (!(val & EMAC_MDIO_COMM_START_BUSY)) { 928 udelay(5); 929 break; 930 } 931 } 932 if (val & EMAC_MDIO_COMM_START_BUSY) { 933 DP(NETIF_MSG_LINK, "read phy register failed\n"); 934 935 *ret_val = 0; 936 rc = -EFAULT; 937 938 } else { 939 /* data */ 940 val = ((phy_addr << 21) | (devad << 16) | 941 EMAC_MDIO_COMM_COMMAND_READ_45 | 942 EMAC_MDIO_COMM_START_BUSY); 943 REG_WR(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_COMM, val); 944 945 for (i = 0; i < 50; i++) { 946 udelay(10); 947 948 val = REG_RD(bp, mdio_ctrl + 949 EMAC_REG_EMAC_MDIO_COMM); 950 if (!(val & EMAC_MDIO_COMM_START_BUSY)) { 951 *ret_val = (u16)(val & EMAC_MDIO_COMM_DATA); 952 break; 953 } 954 } 955 if (val & EMAC_MDIO_COMM_START_BUSY) { 956 DP(NETIF_MSG_LINK, "read phy register failed\n"); 957 958 *ret_val = 0; 959 rc = -EFAULT; 960 } 961 } 962 963 /* Restore the saved mode */ 964 REG_WR(bp, mdio_ctrl + EMAC_REG_EMAC_MDIO_MODE, saved_mode); 965 966 return rc; 967} 968 969static void bnx2x_set_aer_mmd(struct link_params *params, 970 struct link_vars *vars) 971{ 972 struct bnx2x *bp = params->bp; 973 u32 ser_lane; 974 u16 offset; 975 976 ser_lane = ((params->lane_config & 977 PORT_HW_CFG_LANE_SWAP_CFG_MASTER_MASK) >> 978 PORT_HW_CFG_LANE_SWAP_CFG_MASTER_SHIFT); 979 980 offset = (vars->phy_flags & PHY_XGXS_FLAG) ? 981 (params->phy_addr + ser_lane) : 0; 982 983 CL45_WR_OVER_CL22(bp, params->port, 984 params->phy_addr, 985 MDIO_REG_BANK_AER_BLOCK, 986 MDIO_AER_BLOCK_AER_REG, 0x3800 + offset); 987} 988 989static void bnx2x_set_master_ln(struct link_params *params) 990{ 991 struct bnx2x *bp = params->bp; 992 u16 new_master_ln, ser_lane; 993 ser_lane = ((params->lane_config & 994 PORT_HW_CFG_LANE_SWAP_CFG_MASTER_MASK) >> 995 PORT_HW_CFG_LANE_SWAP_CFG_MASTER_SHIFT); 996 997 /* set the master_ln for AN */ 998 CL45_RD_OVER_CL22(bp, params->port, 999 params->phy_addr, 1000 MDIO_REG_BANK_XGXS_BLOCK2, 1001 MDIO_XGXS_BLOCK2_TEST_MODE_LANE, 1002 &new_master_ln); 1003 1004 CL45_WR_OVER_CL22(bp, params->port, 1005 params->phy_addr, 1006 MDIO_REG_BANK_XGXS_BLOCK2 , 1007 MDIO_XGXS_BLOCK2_TEST_MODE_LANE, 1008 (new_master_ln | ser_lane)); 1009} 1010 1011static u8 bnx2x_reset_unicore(struct link_params *params) 1012{ 1013 struct bnx2x *bp = params->bp; 1014 u16 mii_control; 1015 u16 i; 1016 1017 CL45_RD_OVER_CL22(bp, params->port, 1018 params->phy_addr, 1019 MDIO_REG_BANK_COMBO_IEEE0, 1020 MDIO_COMBO_IEEE0_MII_CONTROL, &mii_control); 1021 1022 /* reset the unicore */ 1023 CL45_WR_OVER_CL22(bp, params->port, 1024 params->phy_addr, 1025 MDIO_REG_BANK_COMBO_IEEE0, 1026 MDIO_COMBO_IEEE0_MII_CONTROL, 1027 (mii_control | 1028 MDIO_COMBO_IEEO_MII_CONTROL_RESET)); 1029 if (params->switch_cfg == SWITCH_CFG_1G) 1030 bnx2x_set_serdes_access(params); 1031 1032 /* wait for the reset to self clear */ 1033 for (i = 0; i < MDIO_ACCESS_TIMEOUT; i++) { 1034 udelay(5); 1035 1036 /* the reset erased the previous bank value */ 1037 CL45_RD_OVER_CL22(bp, params->port, 1038 params->phy_addr, 1039 MDIO_REG_BANK_COMBO_IEEE0, 1040 MDIO_COMBO_IEEE0_MII_CONTROL, 1041 &mii_control); 1042 1043 if (!(mii_control & MDIO_COMBO_IEEO_MII_CONTROL_RESET)) { 1044 udelay(5); 1045 return 0; 1046 } 1047 } 1048 1049 DP(NETIF_MSG_LINK, "BUG! XGXS is still in reset!\n"); 1050 return -EINVAL; 1051 1052} 1053 1054static void bnx2x_set_swap_lanes(struct link_params *params) 1055{ 1056 struct bnx2x *bp = params->bp; 1057 /* Each two bits represents a lane number: 1058 No swap is 0123 => 0x1b no need to enable the swap */ 1059 u16 ser_lane, rx_lane_swap, tx_lane_swap; 1060 1061 ser_lane = ((params->lane_config & 1062 PORT_HW_CFG_LANE_SWAP_CFG_MASTER_MASK) >> 1063 PORT_HW_CFG_LANE_SWAP_CFG_MASTER_SHIFT); 1064 rx_lane_swap = ((params->lane_config & 1065 PORT_HW_CFG_LANE_SWAP_CFG_RX_MASK) >> 1066 PORT_HW_CFG_LANE_SWAP_CFG_RX_SHIFT); 1067 tx_lane_swap = ((params->lane_config & 1068 PORT_HW_CFG_LANE_SWAP_CFG_TX_MASK) >> 1069 PORT_HW_CFG_LANE_SWAP_CFG_TX_SHIFT); 1070 1071 if (rx_lane_swap != 0x1b) { 1072 CL45_WR_OVER_CL22(bp, params->port, 1073 params->phy_addr, 1074 MDIO_REG_BANK_XGXS_BLOCK2, 1075 MDIO_XGXS_BLOCK2_RX_LN_SWAP, 1076 (rx_lane_swap | 1077 MDIO_XGXS_BLOCK2_RX_LN_SWAP_ENABLE | 1078 MDIO_XGXS_BLOCK2_RX_LN_SWAP_FORCE_ENABLE)); 1079 } else { 1080 CL45_WR_OVER_CL22(bp, params->port, 1081 params->phy_addr, 1082 MDIO_REG_BANK_XGXS_BLOCK2, 1083 MDIO_XGXS_BLOCK2_RX_LN_SWAP, 0); 1084 } 1085 1086 if (tx_lane_swap != 0x1b) { 1087 CL45_WR_OVER_CL22(bp, params->port, 1088 params->phy_addr, 1089 MDIO_REG_BANK_XGXS_BLOCK2, 1090 MDIO_XGXS_BLOCK2_TX_LN_SWAP, 1091 (tx_lane_swap | 1092 MDIO_XGXS_BLOCK2_TX_LN_SWAP_ENABLE)); 1093 } else { 1094 CL45_WR_OVER_CL22(bp, params->port, 1095 params->phy_addr, 1096 MDIO_REG_BANK_XGXS_BLOCK2, 1097 MDIO_XGXS_BLOCK2_TX_LN_SWAP, 0); 1098 } 1099} 1100 1101static void bnx2x_set_parallel_detection(struct link_params *params, 1102 u8 phy_flags) 1103{ 1104 struct bnx2x *bp = params->bp; 1105 u16 control2; 1106 1107 CL45_RD_OVER_CL22(bp, params->port, 1108 params->phy_addr, 1109 MDIO_REG_BANK_SERDES_DIGITAL, 1110 MDIO_SERDES_DIGITAL_A_1000X_CONTROL2, 1111 &control2); 1112 if (params->speed_cap_mask & PORT_HW_CFG_SPEED_CAPABILITY_D0_1G) 1113 control2 |= MDIO_SERDES_DIGITAL_A_1000X_CONTROL2_PRL_DT_EN; 1114 else 1115 control2 &= ~MDIO_SERDES_DIGITAL_A_1000X_CONTROL2_PRL_DT_EN; 1116 DP(NETIF_MSG_LINK, "params->speed_cap_mask = 0x%x, control2 = 0x%x\n", 1117 params->speed_cap_mask, control2); 1118 CL45_WR_OVER_CL22(bp, params->port, 1119 params->phy_addr, 1120 MDIO_REG_BANK_SERDES_DIGITAL, 1121 MDIO_SERDES_DIGITAL_A_1000X_CONTROL2, 1122 control2); 1123 1124 if ((phy_flags & PHY_XGXS_FLAG) && 1125 (params->speed_cap_mask & 1126 PORT_HW_CFG_SPEED_CAPABILITY_D0_10G)) { 1127 DP(NETIF_MSG_LINK, "XGXS\n"); 1128 1129 CL45_WR_OVER_CL22(bp, params->port, 1130 params->phy_addr, 1131 MDIO_REG_BANK_10G_PARALLEL_DETECT, 1132 MDIO_10G_PARALLEL_DETECT_PAR_DET_10G_LINK, 1133 MDIO_10G_PARALLEL_DETECT_PAR_DET_10G_LINK_CNT); 1134 1135 CL45_RD_OVER_CL22(bp, params->port, 1136 params->phy_addr, 1137 MDIO_REG_BANK_10G_PARALLEL_DETECT, 1138 MDIO_10G_PARALLEL_DETECT_PAR_DET_10G_CONTROL, 1139 &control2); 1140 1141 1142 control2 |= 1143 MDIO_10G_PARALLEL_DETECT_PAR_DET_10G_CONTROL_PARDET10G_EN; 1144 1145 CL45_WR_OVER_CL22(bp, params->port, 1146 params->phy_addr, 1147 MDIO_REG_BANK_10G_PARALLEL_DETECT, 1148 MDIO_10G_PARALLEL_DETECT_PAR_DET_10G_CONTROL, 1149 control2); 1150 1151 /* Disable parallel detection of HiG */ 1152 CL45_WR_OVER_CL22(bp, params->port, 1153 params->phy_addr, 1154 MDIO_REG_BANK_XGXS_BLOCK2, 1155 MDIO_XGXS_BLOCK2_UNICORE_MODE_10G, 1156 MDIO_XGXS_BLOCK2_UNICORE_MODE_10G_CX4_XGXS | 1157 MDIO_XGXS_BLOCK2_UNICORE_MODE_10G_HIGIG_XGXS); 1158 } 1159} 1160 1161static void bnx2x_set_autoneg(struct link_params *params, 1162 struct link_vars *vars, 1163 u8 enable_cl73) 1164{ 1165 struct bnx2x *bp = params->bp; 1166 u16 reg_val; 1167 1168 /* CL37 Autoneg */ 1169 1170 CL45_RD_OVER_CL22(bp, params->port, 1171 params->phy_addr, 1172 MDIO_REG_BANK_COMBO_IEEE0, 1173 MDIO_COMBO_IEEE0_MII_CONTROL, ®_val); 1174 1175 /* CL37 Autoneg Enabled */ 1176 if (vars->line_speed == SPEED_AUTO_NEG) 1177 reg_val |= MDIO_COMBO_IEEO_MII_CONTROL_AN_EN; 1178 else /* CL37 Autoneg Disabled */ 1179 reg_val &= ~(MDIO_COMBO_IEEO_MII_CONTROL_AN_EN | 1180 MDIO_COMBO_IEEO_MII_CONTROL_RESTART_AN); 1181 1182 CL45_WR_OVER_CL22(bp, params->port, 1183 params->phy_addr, 1184 MDIO_REG_BANK_COMBO_IEEE0, 1185 MDIO_COMBO_IEEE0_MII_CONTROL, reg_val); 1186 1187 /* Enable/Disable Autodetection */ 1188 1189 CL45_RD_OVER_CL22(bp, params->port, 1190 params->phy_addr, 1191 MDIO_REG_BANK_SERDES_DIGITAL, 1192 MDIO_SERDES_DIGITAL_A_1000X_CONTROL1, ®_val); 1193 reg_val &= ~(MDIO_SERDES_DIGITAL_A_1000X_CONTROL1_SIGNAL_DETECT_EN | 1194 MDIO_SERDES_DIGITAL_A_1000X_CONTROL1_INVERT_SIGNAL_DETECT); 1195 reg_val |= MDIO_SERDES_DIGITAL_A_1000X_CONTROL1_FIBER_MODE; 1196 if (vars->line_speed == SPEED_AUTO_NEG) 1197 reg_val |= MDIO_SERDES_DIGITAL_A_1000X_CONTROL1_AUTODET; 1198 else 1199 reg_val &= ~MDIO_SERDES_DIGITAL_A_1000X_CONTROL1_AUTODET; 1200 1201 CL45_WR_OVER_CL22(bp, params->port, 1202 params->phy_addr, 1203 MDIO_REG_BANK_SERDES_DIGITAL, 1204 MDIO_SERDES_DIGITAL_A_1000X_CONTROL1, reg_val); 1205 1206 /* Enable TetonII and BAM autoneg */ 1207 CL45_RD_OVER_CL22(bp, params->port, 1208 params->phy_addr, 1209 MDIO_REG_BANK_BAM_NEXT_PAGE, 1210 MDIO_BAM_NEXT_PAGE_MP5_NEXT_PAGE_CTRL, 1211 ®_val); 1212 if (vars->line_speed == SPEED_AUTO_NEG) { 1213 /* Enable BAM aneg Mode and TetonII aneg Mode */ 1214 reg_val |= (MDIO_BAM_NEXT_PAGE_MP5_NEXT_PAGE_CTRL_BAM_MODE | 1215 MDIO_BAM_NEXT_PAGE_MP5_NEXT_PAGE_CTRL_TETON_AN); 1216 } else { 1217 /* TetonII and BAM Autoneg Disabled */ 1218 reg_val &= ~(MDIO_BAM_NEXT_PAGE_MP5_NEXT_PAGE_CTRL_BAM_MODE | 1219 MDIO_BAM_NEXT_PAGE_MP5_NEXT_PAGE_CTRL_TETON_AN); 1220 } 1221 CL45_WR_OVER_CL22(bp, params->port, 1222 params->phy_addr, 1223 MDIO_REG_BANK_BAM_NEXT_PAGE, 1224 MDIO_BAM_NEXT_PAGE_MP5_NEXT_PAGE_CTRL, 1225 reg_val); 1226 1227 if (enable_cl73) { 1228 /* Enable Cl73 FSM status bits */ 1229 CL45_WR_OVER_CL22(bp, params->port, 1230 params->phy_addr, 1231 MDIO_REG_BANK_CL73_USERB0, 1232 MDIO_CL73_USERB0_CL73_UCTRL, 1233 0xe); 1234 1235 /* Enable BAM Station Manager*/ 1236 CL45_WR_OVER_CL22(bp, params->port, 1237 params->phy_addr, 1238 MDIO_REG_BANK_CL73_USERB0, 1239 MDIO_CL73_USERB0_CL73_BAM_CTRL1, 1240 MDIO_CL73_USERB0_CL73_BAM_CTRL1_BAM_EN | 1241 MDIO_CL73_USERB0_CL73_BAM_CTRL1_BAM_STATION_MNGR_EN | 1242 MDIO_CL73_USERB0_CL73_BAM_CTRL1_BAM_NP_AFTER_BP_EN); 1243 1244 /* Advertise CL73 link speeds */ 1245 CL45_RD_OVER_CL22(bp, params->port, 1246 params->phy_addr, 1247 MDIO_REG_BANK_CL73_IEEEB1, 1248 MDIO_CL73_IEEEB1_AN_ADV2, 1249 ®_val); 1250 if (params->speed_cap_mask & 1251 PORT_HW_CFG_SPEED_CAPABILITY_D0_10G) 1252 reg_val |= MDIO_CL73_IEEEB1_AN_ADV2_ADVR_10G_KX4; 1253 if (params->speed_cap_mask & 1254 PORT_HW_CFG_SPEED_CAPABILITY_D0_1G) 1255 reg_val |= MDIO_CL73_IEEEB1_AN_ADV2_ADVR_1000M_KX; 1256 1257 CL45_WR_OVER_CL22(bp, params->port, 1258 params->phy_addr, 1259 MDIO_REG_BANK_CL73_IEEEB1, 1260 MDIO_CL73_IEEEB1_AN_ADV2, 1261 reg_val); 1262 1263 /* CL73 Autoneg Enabled */ 1264 reg_val = MDIO_CL73_IEEEB0_CL73_AN_CONTROL_AN_EN; 1265 1266 } else /* CL73 Autoneg Disabled */ 1267 reg_val = 0; 1268 1269 CL45_WR_OVER_CL22(bp, params->port, 1270 params->phy_addr, 1271 MDIO_REG_BANK_CL73_IEEEB0, 1272 MDIO_CL73_IEEEB0_CL73_AN_CONTROL, reg_val); 1273} 1274 1275/* program SerDes, forced speed */ 1276static void bnx2x_program_serdes(struct link_params *params, 1277 struct link_vars *vars) 1278{ 1279 struct bnx2x *bp = params->bp; 1280 u16 reg_val; 1281 1282 /* program duplex, disable autoneg and sgmii*/ 1283 CL45_RD_OVER_CL22(bp, params->port, 1284 params->phy_addr, 1285 MDIO_REG_BANK_COMBO_IEEE0, 1286 MDIO_COMBO_IEEE0_MII_CONTROL, ®_val); 1287 reg_val &= ~(MDIO_COMBO_IEEO_MII_CONTROL_FULL_DUPLEX | 1288 MDIO_COMBO_IEEO_MII_CONTROL_AN_EN | 1289 MDIO_COMBO_IEEO_MII_CONTROL_MAN_SGMII_SP_MASK); 1290 if (params->req_duplex == DUPLEX_FULL) 1291 reg_val |= MDIO_COMBO_IEEO_MII_CONTROL_FULL_DUPLEX; 1292 CL45_WR_OVER_CL22(bp, params->port, 1293 params->phy_addr, 1294 MDIO_REG_BANK_COMBO_IEEE0, 1295 MDIO_COMBO_IEEE0_MII_CONTROL, reg_val); 1296 1297 /* program speed 1298 - needed only if the speed is greater than 1G (2.5G or 10G) */ 1299 CL45_RD_OVER_CL22(bp, params->port, 1300 params->phy_addr, 1301 MDIO_REG_BANK_SERDES_DIGITAL, 1302 MDIO_SERDES_DIGITAL_MISC1, ®_val); 1303 /* clearing the speed value before setting the right speed */ 1304 DP(NETIF_MSG_LINK, "MDIO_REG_BANK_SERDES_DIGITAL = 0x%x\n", reg_val); 1305 1306 reg_val &= ~(MDIO_SERDES_DIGITAL_MISC1_FORCE_SPEED_MASK | 1307 MDIO_SERDES_DIGITAL_MISC1_FORCE_SPEED_SEL); 1308 1309 if (!((vars->line_speed == SPEED_1000) || 1310 (vars->line_speed == SPEED_100) || 1311 (vars->line_speed == SPEED_10))) { 1312 1313 reg_val |= (MDIO_SERDES_DIGITAL_MISC1_REFCLK_SEL_156_25M | 1314 MDIO_SERDES_DIGITAL_MISC1_FORCE_SPEED_SEL); 1315 if (vars->line_speed == SPEED_10000) 1316 reg_val |= 1317 MDIO_SERDES_DIGITAL_MISC1_FORCE_SPEED_10G_CX4; 1318 if (vars->line_speed == SPEED_13000) 1319 reg_val |= 1320 MDIO_SERDES_DIGITAL_MISC1_FORCE_SPEED_13G; 1321 } 1322 1323 CL45_WR_OVER_CL22(bp, params->port, 1324 params->phy_addr, 1325 MDIO_REG_BANK_SERDES_DIGITAL, 1326 MDIO_SERDES_DIGITAL_MISC1, reg_val); 1327 1328} 1329 1330static void bnx2x_set_brcm_cl37_advertisment(struct link_params *params) 1331{ 1332 struct bnx2x *bp = params->bp; 1333 u16 val = 0; 1334 1335 /* configure the 48 bits for BAM AN */ 1336 1337 /* set extended capabilities */ 1338 if (params->speed_cap_mask & PORT_HW_CFG_SPEED_CAPABILITY_D0_2_5G) 1339 val |= MDIO_OVER_1G_UP1_2_5G; 1340 if (params->speed_cap_mask & PORT_HW_CFG_SPEED_CAPABILITY_D0_10G) 1341 val |= MDIO_OVER_1G_UP1_10G; 1342 CL45_WR_OVER_CL22(bp, params->port, 1343 params->phy_addr, 1344 MDIO_REG_BANK_OVER_1G, 1345 MDIO_OVER_1G_UP1, val); 1346 1347 CL45_WR_OVER_CL22(bp, params->port, 1348 params->phy_addr, 1349 MDIO_REG_BANK_OVER_1G, 1350 MDIO_OVER_1G_UP3, 0x400); 1351} 1352 1353static void bnx2x_calc_ieee_aneg_adv(struct link_params *params, u16 *ieee_fc) 1354{ 1355 struct bnx2x *bp = params->bp; 1356 *ieee_fc = MDIO_COMBO_IEEE0_AUTO_NEG_ADV_FULL_DUPLEX; 1357 /* resolve pause mode and advertisement 1358 * Please refer to Table 28B-3 of the 802.3ab-1999 spec */ 1359 1360 switch (params->req_flow_ctrl) { 1361 case BNX2X_FLOW_CTRL_AUTO: 1362 if (params->req_fc_auto_adv == BNX2X_FLOW_CTRL_BOTH) { 1363 *ieee_fc |= 1364 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_BOTH; 1365 } else { 1366 *ieee_fc |= 1367 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_ASYMMETRIC; 1368 } 1369 break; 1370 case BNX2X_FLOW_CTRL_TX: 1371 *ieee_fc |= 1372 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_ASYMMETRIC; 1373 break; 1374 1375 case BNX2X_FLOW_CTRL_RX: 1376 case BNX2X_FLOW_CTRL_BOTH: 1377 *ieee_fc |= MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_BOTH; 1378 break; 1379 1380 case BNX2X_FLOW_CTRL_NONE: 1381 default: 1382 *ieee_fc |= MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_NONE; 1383 break; 1384 } 1385 DP(NETIF_MSG_LINK, "ieee_fc = 0x%x\n", *ieee_fc); 1386} 1387 1388static void bnx2x_set_ieee_aneg_advertisment(struct link_params *params, 1389 u16 ieee_fc) 1390{ 1391 struct bnx2x *bp = params->bp; 1392 u16 val; 1393 /* for AN, we are always publishing full duplex */ 1394 1395 CL45_WR_OVER_CL22(bp, params->port, 1396 params->phy_addr, 1397 MDIO_REG_BANK_COMBO_IEEE0, 1398 MDIO_COMBO_IEEE0_AUTO_NEG_ADV, ieee_fc); 1399 CL45_RD_OVER_CL22(bp, params->port, 1400 params->phy_addr, 1401 MDIO_REG_BANK_CL73_IEEEB1, 1402 MDIO_CL73_IEEEB1_AN_ADV1, &val); 1403 val &= ~MDIO_CL73_IEEEB1_AN_ADV1_PAUSE_BOTH; 1404 val |= ((ieee_fc<<3) & MDIO_CL73_IEEEB1_AN_ADV1_PAUSE_MASK); 1405 CL45_WR_OVER_CL22(bp, params->port, 1406 params->phy_addr, 1407 MDIO_REG_BANK_CL73_IEEEB1, 1408 MDIO_CL73_IEEEB1_AN_ADV1, val); 1409} 1410 1411static void bnx2x_restart_autoneg(struct link_params *params, u8 enable_cl73) 1412{ 1413 struct bnx2x *bp = params->bp; 1414 u16 mii_control; 1415 1416 DP(NETIF_MSG_LINK, "bnx2x_restart_autoneg\n"); 1417 /* Enable and restart BAM/CL37 aneg */ 1418 1419 if (enable_cl73) { 1420 CL45_RD_OVER_CL22(bp, params->port, 1421 params->phy_addr, 1422 MDIO_REG_BANK_CL73_IEEEB0, 1423 MDIO_CL73_IEEEB0_CL73_AN_CONTROL, 1424 &mii_control); 1425 1426 CL45_WR_OVER_CL22(bp, params->port, 1427 params->phy_addr, 1428 MDIO_REG_BANK_CL73_IEEEB0, 1429 MDIO_CL73_IEEEB0_CL73_AN_CONTROL, 1430 (mii_control | 1431 MDIO_CL73_IEEEB0_CL73_AN_CONTROL_AN_EN | 1432 MDIO_CL73_IEEEB0_CL73_AN_CONTROL_RESTART_AN)); 1433 } else { 1434 1435 CL45_RD_OVER_CL22(bp, params->port, 1436 params->phy_addr, 1437 MDIO_REG_BANK_COMBO_IEEE0, 1438 MDIO_COMBO_IEEE0_MII_CONTROL, 1439 &mii_control); 1440 DP(NETIF_MSG_LINK, 1441 "bnx2x_restart_autoneg mii_control before = 0x%x\n", 1442 mii_control); 1443 CL45_WR_OVER_CL22(bp, params->port, 1444 params->phy_addr, 1445 MDIO_REG_BANK_COMBO_IEEE0, 1446 MDIO_COMBO_IEEE0_MII_CONTROL, 1447 (mii_control | 1448 MDIO_COMBO_IEEO_MII_CONTROL_AN_EN | 1449 MDIO_COMBO_IEEO_MII_CONTROL_RESTART_AN)); 1450 } 1451} 1452 1453static void bnx2x_initialize_sgmii_process(struct link_params *params, 1454 struct link_vars *vars) 1455{ 1456 struct bnx2x *bp = params->bp; 1457 u16 control1; 1458 1459 /* in SGMII mode, the unicore is always slave */ 1460 1461 CL45_RD_OVER_CL22(bp, params->port, 1462 params->phy_addr, 1463 MDIO_REG_BANK_SERDES_DIGITAL, 1464 MDIO_SERDES_DIGITAL_A_1000X_CONTROL1, 1465 &control1); 1466 control1 |= MDIO_SERDES_DIGITAL_A_1000X_CONTROL1_INVERT_SIGNAL_DETECT; 1467 /* set sgmii mode (and not fiber) */ 1468 control1 &= ~(MDIO_SERDES_DIGITAL_A_1000X_CONTROL1_FIBER_MODE | 1469 MDIO_SERDES_DIGITAL_A_1000X_CONTROL1_AUTODET | 1470 MDIO_SERDES_DIGITAL_A_1000X_CONTROL1_MSTR_MODE); 1471 CL45_WR_OVER_CL22(bp, params->port, 1472 params->phy_addr, 1473 MDIO_REG_BANK_SERDES_DIGITAL, 1474 MDIO_SERDES_DIGITAL_A_1000X_CONTROL1, 1475 control1); 1476 1477 /* if forced speed */ 1478 if (!(vars->line_speed == SPEED_AUTO_NEG)) { 1479 /* set speed, disable autoneg */ 1480 u16 mii_control; 1481 1482 CL45_RD_OVER_CL22(bp, params->port, 1483 params->phy_addr, 1484 MDIO_REG_BANK_COMBO_IEEE0, 1485 MDIO_COMBO_IEEE0_MII_CONTROL, 1486 &mii_control); 1487 mii_control &= ~(MDIO_COMBO_IEEO_MII_CONTROL_AN_EN | 1488 MDIO_COMBO_IEEO_MII_CONTROL_MAN_SGMII_SP_MASK| 1489 MDIO_COMBO_IEEO_MII_CONTROL_FULL_DUPLEX); 1490 1491 switch (vars->line_speed) { 1492 case SPEED_100: 1493 mii_control |= 1494 MDIO_COMBO_IEEO_MII_CONTROL_MAN_SGMII_SP_100; 1495 break; 1496 case SPEED_1000: 1497 mii_control |= 1498 MDIO_COMBO_IEEO_MII_CONTROL_MAN_SGMII_SP_1000; 1499 break; 1500 case SPEED_10: 1501 /* there is nothing to set for 10M */ 1502 break; 1503 default: 1504 /* invalid speed for SGMII */ 1505 DP(NETIF_MSG_LINK, "Invalid line_speed 0x%x\n", 1506 vars->line_speed); 1507 break; 1508 } 1509 1510 /* setting the full duplex */ 1511 if (params->req_duplex == DUPLEX_FULL) 1512 mii_control |= 1513 MDIO_COMBO_IEEO_MII_CONTROL_FULL_DUPLEX; 1514 CL45_WR_OVER_CL22(bp, params->port, 1515 params->phy_addr, 1516 MDIO_REG_BANK_COMBO_IEEE0, 1517 MDIO_COMBO_IEEE0_MII_CONTROL, 1518 mii_control); 1519 1520 } else { /* AN mode */ 1521 /* enable and restart AN */ 1522 bnx2x_restart_autoneg(params, 0); 1523 } 1524} 1525 1526 1527/* 1528 * link management 1529 */ 1530 1531static void bnx2x_pause_resolve(struct link_vars *vars, u32 pause_result) 1532{ /* LD LP */ 1533 switch (pause_result) { /* ASYM P ASYM P */ 1534 case 0xb: /* 1 0 1 1 */ 1535 vars->flow_ctrl = BNX2X_FLOW_CTRL_TX; 1536 break; 1537 1538 case 0xe: /* 1 1 1 0 */ 1539 vars->flow_ctrl = BNX2X_FLOW_CTRL_RX; 1540 break; 1541 1542 case 0x5: /* 0 1 0 1 */ 1543 case 0x7: /* 0 1 1 1 */ 1544 case 0xd: /* 1 1 0 1 */ 1545 case 0xf: /* 1 1 1 1 */ 1546 vars->flow_ctrl = BNX2X_FLOW_CTRL_BOTH; 1547 break; 1548 1549 default: 1550 break; 1551 } 1552} 1553 1554static u8 bnx2x_ext_phy_resolve_fc(struct link_params *params, 1555 struct link_vars *vars) 1556{ 1557 struct bnx2x *bp = params->bp; 1558 u8 ext_phy_addr; 1559 u16 ld_pause; /* local */ 1560 u16 lp_pause; /* link partner */ 1561 u16 an_complete; /* AN complete */ 1562 u16 pause_result; 1563 u8 ret = 0; 1564 u32 ext_phy_type; 1565 u8 port = params->port; 1566 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 1567 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 1568 /* read twice */ 1569 1570 bnx2x_cl45_read(bp, port, 1571 ext_phy_type, 1572 ext_phy_addr, 1573 MDIO_AN_DEVAD, 1574 MDIO_AN_REG_STATUS, &an_complete); 1575 bnx2x_cl45_read(bp, port, 1576 ext_phy_type, 1577 ext_phy_addr, 1578 MDIO_AN_DEVAD, 1579 MDIO_AN_REG_STATUS, &an_complete); 1580 1581 if (an_complete & MDIO_AN_REG_STATUS_AN_COMPLETE) { 1582 ret = 1; 1583 bnx2x_cl45_read(bp, port, 1584 ext_phy_type, 1585 ext_phy_addr, 1586 MDIO_AN_DEVAD, 1587 MDIO_AN_REG_ADV_PAUSE, &ld_pause); 1588 bnx2x_cl45_read(bp, port, 1589 ext_phy_type, 1590 ext_phy_addr, 1591 MDIO_AN_DEVAD, 1592 MDIO_AN_REG_LP_AUTO_NEG, &lp_pause); 1593 pause_result = (ld_pause & 1594 MDIO_AN_REG_ADV_PAUSE_MASK) >> 8; 1595 pause_result |= (lp_pause & 1596 MDIO_AN_REG_ADV_PAUSE_MASK) >> 10; 1597 DP(NETIF_MSG_LINK, "Ext PHY pause result 0x%x\n", 1598 pause_result); 1599 bnx2x_pause_resolve(vars, pause_result); 1600 if (vars->flow_ctrl == BNX2X_FLOW_CTRL_NONE && 1601 ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073) { 1602 bnx2x_cl45_read(bp, port, 1603 ext_phy_type, 1604 ext_phy_addr, 1605 MDIO_AN_DEVAD, 1606 MDIO_AN_REG_CL37_FC_LD, &ld_pause); 1607 1608 bnx2x_cl45_read(bp, port, 1609 ext_phy_type, 1610 ext_phy_addr, 1611 MDIO_AN_DEVAD, 1612 MDIO_AN_REG_CL37_FC_LP, &lp_pause); 1613 pause_result = (ld_pause & 1614 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_BOTH) >> 5; 1615 pause_result |= (lp_pause & 1616 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_BOTH) >> 7; 1617 1618 bnx2x_pause_resolve(vars, pause_result); 1619 DP(NETIF_MSG_LINK, "Ext PHY CL37 pause result 0x%x\n", 1620 pause_result); 1621 } 1622 } 1623 return ret; 1624} 1625 1626static u8 bnx2x_direct_parallel_detect_used(struct link_params *params) 1627{ 1628 struct bnx2x *bp = params->bp; 1629 u16 pd_10g, status2_1000x; 1630 CL45_RD_OVER_CL22(bp, params->port, 1631 params->phy_addr, 1632 MDIO_REG_BANK_SERDES_DIGITAL, 1633 MDIO_SERDES_DIGITAL_A_1000X_STATUS2, 1634 &status2_1000x); 1635 CL45_RD_OVER_CL22(bp, params->port, 1636 params->phy_addr, 1637 MDIO_REG_BANK_SERDES_DIGITAL, 1638 MDIO_SERDES_DIGITAL_A_1000X_STATUS2, 1639 &status2_1000x); 1640 if (status2_1000x & MDIO_SERDES_DIGITAL_A_1000X_STATUS2_AN_DISABLED) { 1641 DP(NETIF_MSG_LINK, "1G parallel detect link on port %d\n", 1642 params->port); 1643 return 1; 1644 } 1645 1646 CL45_RD_OVER_CL22(bp, params->port, 1647 params->phy_addr, 1648 MDIO_REG_BANK_10G_PARALLEL_DETECT, 1649 MDIO_10G_PARALLEL_DETECT_PAR_DET_10G_STATUS, 1650 &pd_10g); 1651 1652 if (pd_10g & MDIO_10G_PARALLEL_DETECT_PAR_DET_10G_STATUS_PD_LINK) { 1653 DP(NETIF_MSG_LINK, "10G parallel detect link on port %d\n", 1654 params->port); 1655 return 1; 1656 } 1657 return 0; 1658} 1659 1660static void bnx2x_flow_ctrl_resolve(struct link_params *params, 1661 struct link_vars *vars, 1662 u32 gp_status) 1663{ 1664 struct bnx2x *bp = params->bp; 1665 u16 ld_pause; /* local driver */ 1666 u16 lp_pause; /* link partner */ 1667 u16 pause_result; 1668 1669 vars->flow_ctrl = BNX2X_FLOW_CTRL_NONE; 1670 1671 /* resolve from gp_status in case of AN complete and not sgmii */ 1672 if ((params->req_flow_ctrl == BNX2X_FLOW_CTRL_AUTO) && 1673 (gp_status & MDIO_AN_CL73_OR_37_COMPLETE) && 1674 (!(vars->phy_flags & PHY_SGMII_FLAG)) && 1675 (XGXS_EXT_PHY_TYPE(params->ext_phy_config) == 1676 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT)) { 1677 if (bnx2x_direct_parallel_detect_used(params)) { 1678 vars->flow_ctrl = params->req_fc_auto_adv; 1679 return; 1680 } 1681 if ((gp_status & 1682 (MDIO_GP_STATUS_TOP_AN_STATUS1_CL73_AUTONEG_COMPLETE | 1683 MDIO_GP_STATUS_TOP_AN_STATUS1_CL73_MR_LP_NP_AN_ABLE)) == 1684 (MDIO_GP_STATUS_TOP_AN_STATUS1_CL73_AUTONEG_COMPLETE | 1685 MDIO_GP_STATUS_TOP_AN_STATUS1_CL73_MR_LP_NP_AN_ABLE)) { 1686 1687 CL45_RD_OVER_CL22(bp, params->port, 1688 params->phy_addr, 1689 MDIO_REG_BANK_CL73_IEEEB1, 1690 MDIO_CL73_IEEEB1_AN_ADV1, 1691 &ld_pause); 1692 CL45_RD_OVER_CL22(bp, params->port, 1693 params->phy_addr, 1694 MDIO_REG_BANK_CL73_IEEEB1, 1695 MDIO_CL73_IEEEB1_AN_LP_ADV1, 1696 &lp_pause); 1697 pause_result = (ld_pause & 1698 MDIO_CL73_IEEEB1_AN_ADV1_PAUSE_MASK) 1699 >> 8; 1700 pause_result |= (lp_pause & 1701 MDIO_CL73_IEEEB1_AN_LP_ADV1_PAUSE_MASK) 1702 >> 10; 1703 DP(NETIF_MSG_LINK, "pause_result CL73 0x%x\n", 1704 pause_result); 1705 } else { 1706 1707 CL45_RD_OVER_CL22(bp, params->port, 1708 params->phy_addr, 1709 MDIO_REG_BANK_COMBO_IEEE0, 1710 MDIO_COMBO_IEEE0_AUTO_NEG_ADV, 1711 &ld_pause); 1712 CL45_RD_OVER_CL22(bp, params->port, 1713 params->phy_addr, 1714 MDIO_REG_BANK_COMBO_IEEE0, 1715 MDIO_COMBO_IEEE0_AUTO_NEG_LINK_PARTNER_ABILITY1, 1716 &lp_pause); 1717 pause_result = (ld_pause & 1718 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_MASK)>>5; 1719 pause_result |= (lp_pause & 1720 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_MASK)>>7; 1721 DP(NETIF_MSG_LINK, "pause_result CL37 0x%x\n", 1722 pause_result); 1723 } 1724 bnx2x_pause_resolve(vars, pause_result); 1725 } else if ((params->req_flow_ctrl == BNX2X_FLOW_CTRL_AUTO) && 1726 (bnx2x_ext_phy_resolve_fc(params, vars))) { 1727 return; 1728 } else { 1729 if (params->req_flow_ctrl == BNX2X_FLOW_CTRL_AUTO) 1730 vars->flow_ctrl = params->req_fc_auto_adv; 1731 else 1732 vars->flow_ctrl = params->req_flow_ctrl; 1733 } 1734 DP(NETIF_MSG_LINK, "flow_ctrl 0x%x\n", vars->flow_ctrl); 1735} 1736 1737static void bnx2x_check_fallback_to_cl37(struct link_params *params) 1738{ 1739 struct bnx2x *bp = params->bp; 1740 u16 rx_status, ustat_val, cl37_fsm_recieved; 1741 DP(NETIF_MSG_LINK, "bnx2x_check_fallback_to_cl37\n"); 1742 /* Step 1: Make sure signal is detected */ 1743 CL45_RD_OVER_CL22(bp, params->port, 1744 params->phy_addr, 1745 MDIO_REG_BANK_RX0, 1746 MDIO_RX0_RX_STATUS, 1747 &rx_status); 1748 if ((rx_status & MDIO_RX0_RX_STATUS_SIGDET) != 1749 (MDIO_RX0_RX_STATUS_SIGDET)) { 1750 DP(NETIF_MSG_LINK, "Signal is not detected. Restoring CL73." 1751 "rx_status(0x80b0) = 0x%x\n", rx_status); 1752 CL45_WR_OVER_CL22(bp, params->port, 1753 params->phy_addr, 1754 MDIO_REG_BANK_CL73_IEEEB0, 1755 MDIO_CL73_IEEEB0_CL73_AN_CONTROL, 1756 MDIO_CL73_IEEEB0_CL73_AN_CONTROL_AN_EN); 1757 return; 1758 } 1759 /* Step 2: Check CL73 state machine */ 1760 CL45_RD_OVER_CL22(bp, params->port, 1761 params->phy_addr, 1762 MDIO_REG_BANK_CL73_USERB0, 1763 MDIO_CL73_USERB0_CL73_USTAT1, 1764 &ustat_val); 1765 if ((ustat_val & 1766 (MDIO_CL73_USERB0_CL73_USTAT1_LINK_STATUS_CHECK | 1767 MDIO_CL73_USERB0_CL73_USTAT1_AN_GOOD_CHECK_BAM37)) != 1768 (MDIO_CL73_USERB0_CL73_USTAT1_LINK_STATUS_CHECK | 1769 MDIO_CL73_USERB0_CL73_USTAT1_AN_GOOD_CHECK_BAM37)) { 1770 DP(NETIF_MSG_LINK, "CL73 state-machine is not stable. " 1771 "ustat_val(0x8371) = 0x%x\n", ustat_val); 1772 return; 1773 } 1774 /* Step 3: Check CL37 Message Pages received to indicate LP 1775 supports only CL37 */ 1776 CL45_RD_OVER_CL22(bp, params->port, 1777 params->phy_addr, 1778 MDIO_REG_BANK_REMOTE_PHY, 1779 MDIO_REMOTE_PHY_MISC_RX_STATUS, 1780 &cl37_fsm_recieved); 1781 if ((cl37_fsm_recieved & 1782 (MDIO_REMOTE_PHY_MISC_RX_STATUS_CL37_FSM_RECEIVED_OVER1G_MSG | 1783 MDIO_REMOTE_PHY_MISC_RX_STATUS_CL37_FSM_RECEIVED_BRCM_OUI_MSG)) != 1784 (MDIO_REMOTE_PHY_MISC_RX_STATUS_CL37_FSM_RECEIVED_OVER1G_MSG | 1785 MDIO_REMOTE_PHY_MISC_RX_STATUS_CL37_FSM_RECEIVED_BRCM_OUI_MSG)) { 1786 DP(NETIF_MSG_LINK, "No CL37 FSM were received. " 1787 "misc_rx_status(0x8330) = 0x%x\n", 1788 cl37_fsm_recieved); 1789 return; 1790 } 1791 /* The combined cl37/cl73 fsm state information indicating that we are 1792 connected to a device which does not support cl73, but does support 1793 cl37 BAM. In this case we disable cl73 and restart cl37 auto-neg */ 1794 /* Disable CL73 */ 1795 CL45_WR_OVER_CL22(bp, params->port, 1796 params->phy_addr, 1797 MDIO_REG_BANK_CL73_IEEEB0, 1798 MDIO_CL73_IEEEB0_CL73_AN_CONTROL, 1799 0); 1800 /* Restart CL37 autoneg */ 1801 bnx2x_restart_autoneg(params, 0); 1802 DP(NETIF_MSG_LINK, "Disabling CL73, and restarting CL37 autoneg\n"); 1803} 1804static u8 bnx2x_link_settings_status(struct link_params *params, 1805 struct link_vars *vars, 1806 u32 gp_status, 1807 u8 ext_phy_link_up) 1808{ 1809 struct bnx2x *bp = params->bp; 1810 u16 new_line_speed; 1811 u8 rc = 0; 1812 vars->link_status = 0; 1813 1814 if (gp_status & MDIO_GP_STATUS_TOP_AN_STATUS1_LINK_STATUS) { 1815 DP(NETIF_MSG_LINK, "phy link up gp_status=0x%x\n", 1816 gp_status); 1817 1818 vars->phy_link_up = 1; 1819 vars->link_status |= LINK_STATUS_LINK_UP; 1820 1821 if (gp_status & MDIO_GP_STATUS_TOP_AN_STATUS1_DUPLEX_STATUS) 1822 vars->duplex = DUPLEX_FULL; 1823 else 1824 vars->duplex = DUPLEX_HALF; 1825 1826 bnx2x_flow_ctrl_resolve(params, vars, gp_status); 1827 1828 switch (gp_status & GP_STATUS_SPEED_MASK) { 1829 case GP_STATUS_10M: 1830 new_line_speed = SPEED_10; 1831 if (vars->duplex == DUPLEX_FULL) 1832 vars->link_status |= LINK_10TFD; 1833 else 1834 vars->link_status |= LINK_10THD; 1835 break; 1836 1837 case GP_STATUS_100M: 1838 new_line_speed = SPEED_100; 1839 if (vars->duplex == DUPLEX_FULL) 1840 vars->link_status |= LINK_100TXFD; 1841 else 1842 vars->link_status |= LINK_100TXHD; 1843 break; 1844 1845 case GP_STATUS_1G: 1846 case GP_STATUS_1G_KX: 1847 new_line_speed = SPEED_1000; 1848 if (vars->duplex == DUPLEX_FULL) 1849 vars->link_status |= LINK_1000TFD; 1850 else 1851 vars->link_status |= LINK_1000THD; 1852 break; 1853 1854 case GP_STATUS_2_5G: 1855 new_line_speed = SPEED_2500; 1856 if (vars->duplex == DUPLEX_FULL) 1857 vars->link_status |= LINK_2500TFD; 1858 else 1859 vars->link_status |= LINK_2500THD; 1860 break; 1861 1862 case GP_STATUS_5G: 1863 case GP_STATUS_6G: 1864 DP(NETIF_MSG_LINK, 1865 "link speed unsupported gp_status 0x%x\n", 1866 gp_status); 1867 return -EINVAL; 1868 1869 case GP_STATUS_10G_KX4: 1870 case GP_STATUS_10G_HIG: 1871 case GP_STATUS_10G_CX4: 1872 new_line_speed = SPEED_10000; 1873 vars->link_status |= LINK_10GTFD; 1874 break; 1875 1876 case GP_STATUS_12G_HIG: 1877 new_line_speed = SPEED_12000; 1878 vars->link_status |= LINK_12GTFD; 1879 break; 1880 1881 case GP_STATUS_12_5G: 1882 new_line_speed = SPEED_12500; 1883 vars->link_status |= LINK_12_5GTFD; 1884 break; 1885 1886 case GP_STATUS_13G: 1887 new_line_speed = SPEED_13000; 1888 vars->link_status |= LINK_13GTFD; 1889 break; 1890 1891 case GP_STATUS_15G: 1892 new_line_speed = SPEED_15000; 1893 vars->link_status |= LINK_15GTFD; 1894 break; 1895 1896 case GP_STATUS_16G: 1897 new_line_speed = SPEED_16000; 1898 vars->link_status |= LINK_16GTFD; 1899 break; 1900 1901 default: 1902 DP(NETIF_MSG_LINK, 1903 "link speed unsupported gp_status 0x%x\n", 1904 gp_status); 1905 return -EINVAL; 1906 } 1907 1908 /* Upon link speed change set the NIG into drain mode. 1909 Comes to deals with possible FIFO glitch due to clk change 1910 when speed is decreased without link down indicator */ 1911 if (new_line_speed != vars->line_speed) { 1912 if (XGXS_EXT_PHY_TYPE(params->ext_phy_config) != 1913 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT && 1914 ext_phy_link_up) { 1915 DP(NETIF_MSG_LINK, "Internal link speed %d is" 1916 " different than the external" 1917 " link speed %d\n", new_line_speed, 1918 vars->line_speed); 1919 vars->phy_link_up = 0; 1920 return 0; 1921 } 1922 REG_WR(bp, NIG_REG_EGRESS_DRAIN0_MODE 1923 + params->port*4, 0); 1924 msleep(1); 1925 } 1926 vars->line_speed = new_line_speed; 1927 vars->link_status |= LINK_STATUS_SERDES_LINK; 1928 1929 if ((params->req_line_speed == SPEED_AUTO_NEG) && 1930 ((XGXS_EXT_PHY_TYPE(params->ext_phy_config) == 1931 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT) || 1932 (XGXS_EXT_PHY_TYPE(params->ext_phy_config) == 1933 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705) || 1934 (XGXS_EXT_PHY_TYPE(params->ext_phy_config) == 1935 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706) || 1936 (XGXS_EXT_PHY_TYPE(params->ext_phy_config) == 1937 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726))) { 1938 vars->autoneg = AUTO_NEG_ENABLED; 1939 1940 if (gp_status & MDIO_AN_CL73_OR_37_COMPLETE) { 1941 vars->autoneg |= AUTO_NEG_COMPLETE; 1942 vars->link_status |= 1943 LINK_STATUS_AUTO_NEGOTIATE_COMPLETE; 1944 } 1945 1946 vars->autoneg |= AUTO_NEG_PARALLEL_DETECTION_USED; 1947 vars->link_status |= 1948 LINK_STATUS_PARALLEL_DETECTION_USED; 1949 1950 } 1951 if (vars->flow_ctrl & BNX2X_FLOW_CTRL_TX) 1952 vars->link_status |= 1953 LINK_STATUS_TX_FLOW_CONTROL_ENABLED; 1954 1955 if (vars->flow_ctrl & BNX2X_FLOW_CTRL_RX) 1956 vars->link_status |= 1957 LINK_STATUS_RX_FLOW_CONTROL_ENABLED; 1958 1959 } else { /* link_down */ 1960 DP(NETIF_MSG_LINK, "phy link down\n"); 1961 1962 vars->phy_link_up = 0; 1963 1964 vars->duplex = DUPLEX_FULL; 1965 vars->flow_ctrl = BNX2X_FLOW_CTRL_NONE; 1966 vars->autoneg = AUTO_NEG_DISABLED; 1967 vars->mac_type = MAC_TYPE_NONE; 1968 1969 if ((params->req_line_speed == SPEED_AUTO_NEG) && 1970 ((XGXS_EXT_PHY_TYPE(params->ext_phy_config) == 1971 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT))) { 1972 /* Check signal is detected */ 1973 bnx2x_check_fallback_to_cl37(params); 1974 } 1975 } 1976 1977 DP(NETIF_MSG_LINK, "gp_status 0x%x phy_link_up %x line_speed %x\n", 1978 gp_status, vars->phy_link_up, vars->line_speed); 1979 DP(NETIF_MSG_LINK, "duplex %x flow_ctrl 0x%x" 1980 " autoneg 0x%x\n", 1981 vars->duplex, 1982 vars->flow_ctrl, vars->autoneg); 1983 DP(NETIF_MSG_LINK, "link_status 0x%x\n", vars->link_status); 1984 1985 return rc; 1986} 1987 1988static void bnx2x_set_gmii_tx_driver(struct link_params *params) 1989{ 1990 struct bnx2x *bp = params->bp; 1991 u16 lp_up2; 1992 u16 tx_driver; 1993 u16 bank; 1994 1995 /* read precomp */ 1996 CL45_RD_OVER_CL22(bp, params->port, 1997 params->phy_addr, 1998 MDIO_REG_BANK_OVER_1G, 1999 MDIO_OVER_1G_LP_UP2, &lp_up2); 2000 2001 /* bits [10:7] at lp_up2, positioned at [15:12] */ 2002 lp_up2 = (((lp_up2 & MDIO_OVER_1G_LP_UP2_PREEMPHASIS_MASK) >> 2003 MDIO_OVER_1G_LP_UP2_PREEMPHASIS_SHIFT) << 2004 MDIO_TX0_TX_DRIVER_PREEMPHASIS_SHIFT); 2005 2006 if (lp_up2 == 0) 2007 return; 2008 2009 for (bank = MDIO_REG_BANK_TX0; bank <= MDIO_REG_BANK_TX3; 2010 bank += (MDIO_REG_BANK_TX1 - MDIO_REG_BANK_TX0)) { 2011 CL45_RD_OVER_CL22(bp, params->port, 2012 params->phy_addr, 2013 bank, 2014 MDIO_TX0_TX_DRIVER, &tx_driver); 2015 2016 /* replace tx_driver bits [15:12] */ 2017 if (lp_up2 != 2018 (tx_driver & MDIO_TX0_TX_DRIVER_PREEMPHASIS_MASK)) { 2019 tx_driver &= ~MDIO_TX0_TX_DRIVER_PREEMPHASIS_MASK; 2020 tx_driver |= lp_up2; 2021 CL45_WR_OVER_CL22(bp, params->port, 2022 params->phy_addr, 2023 bank, 2024 MDIO_TX0_TX_DRIVER, tx_driver); 2025 } 2026 } 2027} 2028 2029static u8 bnx2x_emac_program(struct link_params *params, 2030 u32 line_speed, u32 duplex) 2031{ 2032 struct bnx2x *bp = params->bp; 2033 u8 port = params->port; 2034 u16 mode = 0; 2035 2036 DP(NETIF_MSG_LINK, "setting link speed & duplex\n"); 2037 bnx2x_bits_dis(bp, GRCBASE_EMAC0 + port*0x400 + 2038 EMAC_REG_EMAC_MODE, 2039 (EMAC_MODE_25G_MODE | 2040 EMAC_MODE_PORT_MII_10M | 2041 EMAC_MODE_HALF_DUPLEX)); 2042 switch (line_speed) { 2043 case SPEED_10: 2044 mode |= EMAC_MODE_PORT_MII_10M; 2045 break; 2046 2047 case SPEED_100: 2048 mode |= EMAC_MODE_PORT_MII; 2049 break; 2050 2051 case SPEED_1000: 2052 mode |= EMAC_MODE_PORT_GMII; 2053 break; 2054 2055 case SPEED_2500: 2056 mode |= (EMAC_MODE_25G_MODE | EMAC_MODE_PORT_GMII); 2057 break; 2058 2059 default: 2060 /* 10G not valid for EMAC */ 2061 DP(NETIF_MSG_LINK, "Invalid line_speed 0x%x\n", line_speed); 2062 return -EINVAL; 2063 } 2064 2065 if (duplex == DUPLEX_HALF) 2066 mode |= EMAC_MODE_HALF_DUPLEX; 2067 bnx2x_bits_en(bp, 2068 GRCBASE_EMAC0 + port*0x400 + EMAC_REG_EMAC_MODE, 2069 mode); 2070 2071 bnx2x_set_led(params, LED_MODE_OPER, line_speed); 2072 return 0; 2073} 2074 2075/*****************************************************************************/ 2076/* External Phy section */ 2077/*****************************************************************************/ 2078void bnx2x_ext_phy_hw_reset(struct bnx2x *bp, u8 port) 2079{ 2080 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_1, 2081 MISC_REGISTERS_GPIO_OUTPUT_LOW, port); 2082 msleep(1); 2083 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_1, 2084 MISC_REGISTERS_GPIO_OUTPUT_HIGH, port); 2085} 2086 2087static void bnx2x_ext_phy_reset(struct link_params *params, 2088 struct link_vars *vars) 2089{ 2090 struct bnx2x *bp = params->bp; 2091 u32 ext_phy_type; 2092 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 2093 2094 DP(NETIF_MSG_LINK, "Port %x: bnx2x_ext_phy_reset\n", params->port); 2095 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 2096 /* The PHY reset is controled by GPIO 1 2097 * Give it 1ms of reset pulse 2098 */ 2099 if (vars->phy_flags & PHY_XGXS_FLAG) { 2100 2101 switch (ext_phy_type) { 2102 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT: 2103 DP(NETIF_MSG_LINK, "XGXS Direct\n"); 2104 break; 2105 2106 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705: 2107 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706: 2108 DP(NETIF_MSG_LINK, "XGXS 8705/8706\n"); 2109 2110 /* Restore normal power mode*/ 2111 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_2, 2112 MISC_REGISTERS_GPIO_OUTPUT_HIGH, 2113 params->port); 2114 2115 /* HW reset */ 2116 bnx2x_ext_phy_hw_reset(bp, params->port); 2117 2118 bnx2x_cl45_write(bp, params->port, 2119 ext_phy_type, 2120 ext_phy_addr, 2121 MDIO_PMA_DEVAD, 2122 MDIO_PMA_REG_CTRL, 0xa040); 2123 break; 2124 2125 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727: 2126 break; 2127 2128 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726: 2129 2130 /* Restore normal power mode*/ 2131 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_2, 2132 MISC_REGISTERS_GPIO_OUTPUT_HIGH, 2133 params->port); 2134 2135 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_1, 2136 MISC_REGISTERS_GPIO_OUTPUT_HIGH, 2137 params->port); 2138 2139 bnx2x_cl45_write(bp, params->port, 2140 ext_phy_type, 2141 ext_phy_addr, 2142 MDIO_PMA_DEVAD, 2143 MDIO_PMA_REG_CTRL, 2144 1<<15); 2145 break; 2146 2147 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072: 2148 DP(NETIF_MSG_LINK, "XGXS 8072\n"); 2149 2150 /* Unset Low Power Mode and SW reset */ 2151 /* Restore normal power mode*/ 2152 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_2, 2153 MISC_REGISTERS_GPIO_OUTPUT_HIGH, 2154 params->port); 2155 2156 bnx2x_cl45_write(bp, params->port, 2157 ext_phy_type, 2158 ext_phy_addr, 2159 MDIO_PMA_DEVAD, 2160 MDIO_PMA_REG_CTRL, 2161 1<<15); 2162 break; 2163 2164 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073: 2165 DP(NETIF_MSG_LINK, "XGXS 8073\n"); 2166 2167 /* Restore normal power mode*/ 2168 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_2, 2169 MISC_REGISTERS_GPIO_OUTPUT_HIGH, 2170 params->port); 2171 2172 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_1, 2173 MISC_REGISTERS_GPIO_OUTPUT_HIGH, 2174 params->port); 2175 break; 2176 2177 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_SFX7101: 2178 DP(NETIF_MSG_LINK, "XGXS SFX7101\n"); 2179 2180 /* Restore normal power mode*/ 2181 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_2, 2182 MISC_REGISTERS_GPIO_OUTPUT_HIGH, 2183 params->port); 2184 2185 /* HW reset */ 2186 bnx2x_ext_phy_hw_reset(bp, params->port); 2187 break; 2188 2189 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481: 2190 /* Restore normal power mode*/ 2191 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_2, 2192 MISC_REGISTERS_GPIO_OUTPUT_HIGH, 2193 params->port); 2194 2195 /* HW reset */ 2196 bnx2x_ext_phy_hw_reset(bp, params->port); 2197 2198 bnx2x_cl45_write(bp, params->port, 2199 ext_phy_type, 2200 ext_phy_addr, 2201 MDIO_PMA_DEVAD, 2202 MDIO_PMA_REG_CTRL, 2203 1<<15); 2204 break; 2205 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM84823: 2206 break; 2207 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_FAILURE: 2208 DP(NETIF_MSG_LINK, "XGXS PHY Failure detected\n"); 2209 break; 2210 2211 default: 2212 DP(NETIF_MSG_LINK, "BAD XGXS ext_phy_config 0x%x\n", 2213 params->ext_phy_config); 2214 break; 2215 } 2216 2217 } else { /* SerDes */ 2218 ext_phy_type = SERDES_EXT_PHY_TYPE(params->ext_phy_config); 2219 switch (ext_phy_type) { 2220 case PORT_HW_CFG_SERDES_EXT_PHY_TYPE_DIRECT: 2221 DP(NETIF_MSG_LINK, "SerDes Direct\n"); 2222 break; 2223 2224 case PORT_HW_CFG_SERDES_EXT_PHY_TYPE_BCM5482: 2225 DP(NETIF_MSG_LINK, "SerDes 5482\n"); 2226 bnx2x_ext_phy_hw_reset(bp, params->port); 2227 break; 2228 2229 default: 2230 DP(NETIF_MSG_LINK, "BAD SerDes ext_phy_config 0x%x\n", 2231 params->ext_phy_config); 2232 break; 2233 } 2234 } 2235} 2236 2237static void bnx2x_save_spirom_version(struct bnx2x *bp, u8 port, 2238 u32 shmem_base, u32 spirom_ver) 2239{ 2240 DP(NETIF_MSG_LINK, "FW version 0x%x:0x%x for port %d\n", 2241 (u16)(spirom_ver>>16), (u16)spirom_ver, port); 2242 REG_WR(bp, shmem_base + 2243 offsetof(struct shmem_region, 2244 port_mb[port].ext_phy_fw_version), 2245 spirom_ver); 2246} 2247 2248static void bnx2x_save_bcm_spirom_ver(struct bnx2x *bp, u8 port, 2249 u32 ext_phy_type, u8 ext_phy_addr, 2250 u32 shmem_base) 2251{ 2252 u16 fw_ver1, fw_ver2; 2253 2254 bnx2x_cl45_read(bp, port, ext_phy_type, ext_phy_addr, MDIO_PMA_DEVAD, 2255 MDIO_PMA_REG_ROM_VER1, &fw_ver1); 2256 bnx2x_cl45_read(bp, port, ext_phy_type, ext_phy_addr, MDIO_PMA_DEVAD, 2257 MDIO_PMA_REG_ROM_VER2, &fw_ver2); 2258 bnx2x_save_spirom_version(bp, port, shmem_base, 2259 (u32)(fw_ver1<<16 | fw_ver2)); 2260} 2261 2262 2263static void bnx2x_save_8481_spirom_version(struct bnx2x *bp, u8 port, 2264 u8 ext_phy_addr, u32 shmem_base) 2265{ 2266 u16 val, fw_ver1, fw_ver2, cnt; 2267 /* For the 32 bits registers in 8481, access via MDIO2ARM interface.*/ 2268 /* (1) set register 0xc200_0014(SPI_BRIDGE_CTRL_2) to 0x03000000 */ 2269 bnx2x_cl45_write(bp, port, 2270 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2271 ext_phy_addr, MDIO_PMA_DEVAD, 2272 0xA819, 0x0014); 2273 bnx2x_cl45_write(bp, port, 2274 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2275 ext_phy_addr, 2276 MDIO_PMA_DEVAD, 2277 0xA81A, 2278 0xc200); 2279 bnx2x_cl45_write(bp, port, 2280 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2281 ext_phy_addr, 2282 MDIO_PMA_DEVAD, 2283 0xA81B, 2284 0x0000); 2285 bnx2x_cl45_write(bp, port, 2286 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2287 ext_phy_addr, 2288 MDIO_PMA_DEVAD, 2289 0xA81C, 2290 0x0300); 2291 bnx2x_cl45_write(bp, port, 2292 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2293 ext_phy_addr, 2294 MDIO_PMA_DEVAD, 2295 0xA817, 2296 0x0009); 2297 2298 for (cnt = 0; cnt < 100; cnt++) { 2299 bnx2x_cl45_read(bp, port, 2300 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2301 ext_phy_addr, 2302 MDIO_PMA_DEVAD, 2303 0xA818, 2304 &val); 2305 if (val & 1) 2306 break; 2307 udelay(5); 2308 } 2309 if (cnt == 100) { 2310 DP(NETIF_MSG_LINK, "Unable to read 8481 phy fw version(1)\n"); 2311 bnx2x_save_spirom_version(bp, port, 2312 shmem_base, 0); 2313 return; 2314 } 2315 2316 2317 /* 2) read register 0xc200_0000 (SPI_FW_STATUS) */ 2318 bnx2x_cl45_write(bp, port, 2319 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2320 ext_phy_addr, MDIO_PMA_DEVAD, 2321 0xA819, 0x0000); 2322 bnx2x_cl45_write(bp, port, 2323 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2324 ext_phy_addr, MDIO_PMA_DEVAD, 2325 0xA81A, 0xc200); 2326 bnx2x_cl45_write(bp, port, 2327 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2328 ext_phy_addr, MDIO_PMA_DEVAD, 2329 0xA817, 0x000A); 2330 for (cnt = 0; cnt < 100; cnt++) { 2331 bnx2x_cl45_read(bp, port, 2332 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2333 ext_phy_addr, 2334 MDIO_PMA_DEVAD, 2335 0xA818, 2336 &val); 2337 if (val & 1) 2338 break; 2339 udelay(5); 2340 } 2341 if (cnt == 100) { 2342 DP(NETIF_MSG_LINK, "Unable to read 8481 phy fw version(2)\n"); 2343 bnx2x_save_spirom_version(bp, port, 2344 shmem_base, 0); 2345 return; 2346 } 2347 2348 /* lower 16 bits of the register SPI_FW_STATUS */ 2349 bnx2x_cl45_read(bp, port, 2350 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2351 ext_phy_addr, 2352 MDIO_PMA_DEVAD, 2353 0xA81B, 2354 &fw_ver1); 2355 /* upper 16 bits of register SPI_FW_STATUS */ 2356 bnx2x_cl45_read(bp, port, 2357 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 2358 ext_phy_addr, 2359 MDIO_PMA_DEVAD, 2360 0xA81C, 2361 &fw_ver2); 2362 2363 bnx2x_save_spirom_version(bp, port, 2364 shmem_base, (fw_ver2<<16) | fw_ver1); 2365} 2366 2367static void bnx2x_bcm8072_external_rom_boot(struct link_params *params) 2368{ 2369 struct bnx2x *bp = params->bp; 2370 u8 port = params->port; 2371 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 2372 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 2373 2374 /* Need to wait 200ms after reset */ 2375 msleep(200); 2376 /* Boot port from external ROM 2377 * Set ser_boot_ctl bit in the MISC_CTRL1 register 2378 */ 2379 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 2380 MDIO_PMA_DEVAD, 2381 MDIO_PMA_REG_MISC_CTRL1, 0x0001); 2382 2383 /* Reset internal microprocessor */ 2384 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 2385 MDIO_PMA_DEVAD, 2386 MDIO_PMA_REG_GEN_CTRL, 2387 MDIO_PMA_REG_GEN_CTRL_ROM_RESET_INTERNAL_MP); 2388 /* set micro reset = 0 */ 2389 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 2390 MDIO_PMA_DEVAD, 2391 MDIO_PMA_REG_GEN_CTRL, 2392 MDIO_PMA_REG_GEN_CTRL_ROM_MICRO_RESET); 2393 /* Reset internal microprocessor */ 2394 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 2395 MDIO_PMA_DEVAD, 2396 MDIO_PMA_REG_GEN_CTRL, 2397 MDIO_PMA_REG_GEN_CTRL_ROM_RESET_INTERNAL_MP); 2398 /* wait for 100ms for code download via SPI port */ 2399 msleep(100); 2400 2401 /* Clear ser_boot_ctl bit */ 2402 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 2403 MDIO_PMA_DEVAD, 2404 MDIO_PMA_REG_MISC_CTRL1, 0x0000); 2405 /* Wait 100ms */ 2406 msleep(100); 2407 2408 bnx2x_save_bcm_spirom_ver(bp, port, 2409 ext_phy_type, 2410 ext_phy_addr, 2411 params->shmem_base); 2412} 2413 2414static u8 bnx2x_8073_is_snr_needed(struct link_params *params) 2415{ 2416 /* This is only required for 8073A1, version 102 only */ 2417 2418 struct bnx2x *bp = params->bp; 2419 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 2420 u16 val; 2421 2422 /* Read 8073 HW revision*/ 2423 bnx2x_cl45_read(bp, params->port, 2424 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 2425 ext_phy_addr, 2426 MDIO_PMA_DEVAD, 2427 MDIO_PMA_REG_8073_CHIP_REV, &val); 2428 2429 if (val != 1) { 2430 return 0; 2431 } 2432 2433 bnx2x_cl45_read(bp, params->port, 2434 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 2435 ext_phy_addr, 2436 MDIO_PMA_DEVAD, 2437 MDIO_PMA_REG_ROM_VER2, &val); 2438 2439 /* SNR should be applied only for version 0x102 */ 2440 if (val != 0x102) 2441 return 0; 2442 2443 return 1; 2444} 2445 2446static u8 bnx2x_bcm8073_xaui_wa(struct link_params *params) 2447{ 2448 struct bnx2x *bp = params->bp; 2449 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 2450 u16 val, cnt, cnt1 ; 2451 2452 bnx2x_cl45_read(bp, params->port, 2453 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 2454 ext_phy_addr, 2455 MDIO_PMA_DEVAD, 2456 MDIO_PMA_REG_8073_CHIP_REV, &val); 2457 2458 if (val > 0) { 2459 return 0; 2460 } 2461 2462 /* After loading the boot ROM and restarting Autoneg, 2463 poll Dev1, Reg $C820: */ 2464 2465 for (cnt = 0; cnt < 1000; cnt++) { 2466 bnx2x_cl45_read(bp, params->port, 2467 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 2468 ext_phy_addr, 2469 MDIO_PMA_DEVAD, 2470 MDIO_PMA_REG_8073_SPEED_LINK_STATUS, 2471 &val); 2472 if (!(val & (1<<14)) || !(val & (1<<13))) { 2473 DP(NETIF_MSG_LINK, "XAUI work-around not required\n"); 2474 return 0; 2475 } else if (!(val & (1<<15))) { 2476 DP(NETIF_MSG_LINK, "clc bit 15 went off\n"); 2477 for (cnt1 = 0; cnt1 < 1000; cnt1++) { 2478 bnx2x_cl45_read(bp, params->port, 2479 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 2480 ext_phy_addr, 2481 MDIO_PMA_DEVAD, 2482 MDIO_PMA_REG_8073_XAUI_WA, &val); 2483 if (val & (1<<15)) { 2484 DP(NETIF_MSG_LINK, 2485 "XAUI workaround has completed\n"); 2486 return 0; 2487 } 2488 msleep(3); 2489 } 2490 break; 2491 } 2492 msleep(3); 2493 } 2494 DP(NETIF_MSG_LINK, "Warning: XAUI work-around timeout !!!\n"); 2495 return -EINVAL; 2496} 2497 2498static void bnx2x_bcm8073_bcm8727_external_rom_boot(struct bnx2x *bp, u8 port, 2499 u8 ext_phy_addr, 2500 u32 ext_phy_type, 2501 u32 shmem_base) 2502{ 2503 /* Boot port from external ROM */ 2504 /* EDC grst */ 2505 bnx2x_cl45_write(bp, port, 2506 ext_phy_type, 2507 ext_phy_addr, 2508 MDIO_PMA_DEVAD, 2509 MDIO_PMA_REG_GEN_CTRL, 2510 0x0001); 2511 2512 /* ucode reboot and rst */ 2513 bnx2x_cl45_write(bp, port, 2514 ext_phy_type, 2515 ext_phy_addr, 2516 MDIO_PMA_DEVAD, 2517 MDIO_PMA_REG_GEN_CTRL, 2518 0x008c); 2519 2520 bnx2x_cl45_write(bp, port, 2521 ext_phy_type, 2522 ext_phy_addr, 2523 MDIO_PMA_DEVAD, 2524 MDIO_PMA_REG_MISC_CTRL1, 0x0001); 2525 2526 /* Reset internal microprocessor */ 2527 bnx2x_cl45_write(bp, port, 2528 ext_phy_type, 2529 ext_phy_addr, 2530 MDIO_PMA_DEVAD, 2531 MDIO_PMA_REG_GEN_CTRL, 2532 MDIO_PMA_REG_GEN_CTRL_ROM_MICRO_RESET); 2533 2534 /* Release srst bit */ 2535 bnx2x_cl45_write(bp, port, 2536 ext_phy_type, 2537 ext_phy_addr, 2538 MDIO_PMA_DEVAD, 2539 MDIO_PMA_REG_GEN_CTRL, 2540 MDIO_PMA_REG_GEN_CTRL_ROM_RESET_INTERNAL_MP); 2541 2542 /* wait for 100ms for code download via SPI port */ 2543 msleep(100); 2544 2545 /* Clear ser_boot_ctl bit */ 2546 bnx2x_cl45_write(bp, port, 2547 ext_phy_type, 2548 ext_phy_addr, 2549 MDIO_PMA_DEVAD, 2550 MDIO_PMA_REG_MISC_CTRL1, 0x0000); 2551 2552 bnx2x_save_bcm_spirom_ver(bp, port, 2553 ext_phy_type, 2554 ext_phy_addr, 2555 shmem_base); 2556} 2557 2558static void bnx2x_bcm8073_external_rom_boot(struct bnx2x *bp, u8 port, 2559 u8 ext_phy_addr, 2560 u32 shmem_base) 2561{ 2562 bnx2x_bcm8073_bcm8727_external_rom_boot(bp, port, ext_phy_addr, 2563 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 2564 shmem_base); 2565} 2566 2567static void bnx2x_bcm8727_external_rom_boot(struct bnx2x *bp, u8 port, 2568 u8 ext_phy_addr, 2569 u32 shmem_base) 2570{ 2571 bnx2x_bcm8073_bcm8727_external_rom_boot(bp, port, ext_phy_addr, 2572 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 2573 shmem_base); 2574 2575} 2576 2577static void bnx2x_bcm8726_external_rom_boot(struct link_params *params) 2578{ 2579 struct bnx2x *bp = params->bp; 2580 u8 port = params->port; 2581 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 2582 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 2583 2584 /* Need to wait 100ms after reset */ 2585 msleep(100); 2586 2587 /* Micro controller re-boot */ 2588 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 2589 MDIO_PMA_DEVAD, 2590 MDIO_PMA_REG_GEN_CTRL, 2591 0x018B); 2592 2593 /* Set soft reset */ 2594 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 2595 MDIO_PMA_DEVAD, 2596 MDIO_PMA_REG_GEN_CTRL, 2597 MDIO_PMA_REG_GEN_CTRL_ROM_MICRO_RESET); 2598 2599 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 2600 MDIO_PMA_DEVAD, 2601 MDIO_PMA_REG_MISC_CTRL1, 0x0001); 2602 2603 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 2604 MDIO_PMA_DEVAD, 2605 MDIO_PMA_REG_GEN_CTRL, 2606 MDIO_PMA_REG_GEN_CTRL_ROM_RESET_INTERNAL_MP); 2607 2608 /* wait for 150ms for microcode load */ 2609 msleep(150); 2610 2611 /* Disable serial boot control, tristates pins SS_N, SCK, MOSI, MISO */ 2612 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 2613 MDIO_PMA_DEVAD, 2614 MDIO_PMA_REG_MISC_CTRL1, 0x0000); 2615 2616 msleep(200); 2617 bnx2x_save_bcm_spirom_ver(bp, port, 2618 ext_phy_type, 2619 ext_phy_addr, 2620 params->shmem_base); 2621} 2622 2623static void bnx2x_sfp_set_transmitter(struct bnx2x *bp, u8 port, 2624 u32 ext_phy_type, u8 ext_phy_addr, 2625 u8 tx_en) 2626{ 2627 u16 val; 2628 2629 DP(NETIF_MSG_LINK, "Setting transmitter tx_en=%x for port %x\n", 2630 tx_en, port); 2631 /* Disable/Enable transmitter ( TX laser of the SFP+ module.)*/ 2632 bnx2x_cl45_read(bp, port, 2633 ext_phy_type, 2634 ext_phy_addr, 2635 MDIO_PMA_DEVAD, 2636 MDIO_PMA_REG_PHY_IDENTIFIER, 2637 &val); 2638 2639 if (tx_en) 2640 val &= ~(1<<15); 2641 else 2642 val |= (1<<15); 2643 2644 bnx2x_cl45_write(bp, port, 2645 ext_phy_type, 2646 ext_phy_addr, 2647 MDIO_PMA_DEVAD, 2648 MDIO_PMA_REG_PHY_IDENTIFIER, 2649 val); 2650} 2651 2652static u8 bnx2x_8726_read_sfp_module_eeprom(struct link_params *params, 2653 u16 addr, u8 byte_cnt, u8 *o_buf) 2654{ 2655 struct bnx2x *bp = params->bp; 2656 u16 val = 0; 2657 u16 i; 2658 u8 port = params->port; 2659 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 2660 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 2661 2662 if (byte_cnt > 16) { 2663 DP(NETIF_MSG_LINK, "Reading from eeprom is" 2664 " is limited to 0xf\n"); 2665 return -EINVAL; 2666 } 2667 /* Set the read command byte count */ 2668 bnx2x_cl45_write(bp, port, 2669 ext_phy_type, 2670 ext_phy_addr, 2671 MDIO_PMA_DEVAD, 2672 MDIO_PMA_REG_SFP_TWO_WIRE_BYTE_CNT, 2673 (byte_cnt | 0xa000)); 2674 2675 /* Set the read command address */ 2676 bnx2x_cl45_write(bp, port, 2677 ext_phy_type, 2678 ext_phy_addr, 2679 MDIO_PMA_DEVAD, 2680 MDIO_PMA_REG_SFP_TWO_WIRE_MEM_ADDR, 2681 addr); 2682 2683 /* Activate read command */ 2684 bnx2x_cl45_write(bp, port, 2685 ext_phy_type, 2686 ext_phy_addr, 2687 MDIO_PMA_DEVAD, 2688 MDIO_PMA_REG_SFP_TWO_WIRE_CTRL, 2689 0x2c0f); 2690 2691 /* Wait up to 500us for command complete status */ 2692 for (i = 0; i < 100; i++) { 2693 bnx2x_cl45_read(bp, port, 2694 ext_phy_type, 2695 ext_phy_addr, 2696 MDIO_PMA_DEVAD, 2697 MDIO_PMA_REG_SFP_TWO_WIRE_CTRL, &val); 2698 if ((val & MDIO_PMA_REG_SFP_TWO_WIRE_CTRL_STATUS_MASK) == 2699 MDIO_PMA_REG_SFP_TWO_WIRE_STATUS_COMPLETE) 2700 break; 2701 udelay(5); 2702 } 2703 2704 if ((val & MDIO_PMA_REG_SFP_TWO_WIRE_CTRL_STATUS_MASK) != 2705 MDIO_PMA_REG_SFP_TWO_WIRE_STATUS_COMPLETE) { 2706 DP(NETIF_MSG_LINK, 2707 "Got bad status 0x%x when reading from SFP+ EEPROM\n", 2708 (val & MDIO_PMA_REG_SFP_TWO_WIRE_CTRL_STATUS_MASK)); 2709 return -EINVAL; 2710 } 2711 2712 /* Read the buffer */ 2713 for (i = 0; i < byte_cnt; i++) { 2714 bnx2x_cl45_read(bp, port, 2715 ext_phy_type, 2716 ext_phy_addr, 2717 MDIO_PMA_DEVAD, 2718 MDIO_PMA_REG_8726_TWO_WIRE_DATA_BUF + i, &val); 2719 o_buf[i] = (u8)(val & MDIO_PMA_REG_8726_TWO_WIRE_DATA_MASK); 2720 } 2721 2722 for (i = 0; i < 100; i++) { 2723 bnx2x_cl45_read(bp, port, 2724 ext_phy_type, 2725 ext_phy_addr, 2726 MDIO_PMA_DEVAD, 2727 MDIO_PMA_REG_SFP_TWO_WIRE_CTRL, &val); 2728 if ((val & MDIO_PMA_REG_SFP_TWO_WIRE_CTRL_STATUS_MASK) == 2729 MDIO_PMA_REG_SFP_TWO_WIRE_STATUS_IDLE) 2730 return 0;; 2731 msleep(1); 2732 } 2733 return -EINVAL; 2734} 2735 2736static u8 bnx2x_8727_read_sfp_module_eeprom(struct link_params *params, 2737 u16 addr, u8 byte_cnt, u8 *o_buf) 2738{ 2739 struct bnx2x *bp = params->bp; 2740 u16 val, i; 2741 u8 port = params->port; 2742 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 2743 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 2744 2745 if (byte_cnt > 16) { 2746 DP(NETIF_MSG_LINK, "Reading from eeprom is" 2747 " is limited to 0xf\n"); 2748 return -EINVAL; 2749 } 2750 2751 /* Need to read from 1.8000 to clear it */ 2752 bnx2x_cl45_read(bp, port, 2753 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 2754 ext_phy_addr, 2755 MDIO_PMA_DEVAD, 2756 MDIO_PMA_REG_SFP_TWO_WIRE_CTRL, 2757 &val); 2758 2759 /* Set the read command byte count */ 2760 bnx2x_cl45_write(bp, port, 2761 ext_phy_type, 2762 ext_phy_addr, 2763 MDIO_PMA_DEVAD, 2764 MDIO_PMA_REG_SFP_TWO_WIRE_BYTE_CNT, 2765 ((byte_cnt < 2) ? 2 : byte_cnt)); 2766 2767 /* Set the read command address */ 2768 bnx2x_cl45_write(bp, port, 2769 ext_phy_type, 2770 ext_phy_addr, 2771 MDIO_PMA_DEVAD, 2772 MDIO_PMA_REG_SFP_TWO_WIRE_MEM_ADDR, 2773 addr); 2774 /* Set the destination address */ 2775 bnx2x_cl45_write(bp, port, 2776 ext_phy_type, 2777 ext_phy_addr, 2778 MDIO_PMA_DEVAD, 2779 0x8004, 2780 MDIO_PMA_REG_8727_TWO_WIRE_DATA_BUF); 2781 2782 /* Activate read command */ 2783 bnx2x_cl45_write(bp, port, 2784 ext_phy_type, 2785 ext_phy_addr, 2786 MDIO_PMA_DEVAD, 2787 MDIO_PMA_REG_SFP_TWO_WIRE_CTRL, 2788 0x8002); 2789 /* Wait appropriate time for two-wire command to finish before 2790 polling the status register */ 2791 msleep(1); 2792 2793 /* Wait up to 500us for command complete status */ 2794 for (i = 0; i < 100; i++) { 2795 bnx2x_cl45_read(bp, port, 2796 ext_phy_type, 2797 ext_phy_addr, 2798 MDIO_PMA_DEVAD, 2799 MDIO_PMA_REG_SFP_TWO_WIRE_CTRL, &val); 2800 if ((val & MDIO_PMA_REG_SFP_TWO_WIRE_CTRL_STATUS_MASK) == 2801 MDIO_PMA_REG_SFP_TWO_WIRE_STATUS_COMPLETE) 2802 break; 2803 udelay(5); 2804 } 2805 2806 if ((val & MDIO_PMA_REG_SFP_TWO_WIRE_CTRL_STATUS_MASK) != 2807 MDIO_PMA_REG_SFP_TWO_WIRE_STATUS_COMPLETE) { 2808 DP(NETIF_MSG_LINK, 2809 "Got bad status 0x%x when reading from SFP+ EEPROM\n", 2810 (val & MDIO_PMA_REG_SFP_TWO_WIRE_CTRL_STATUS_MASK)); 2811 return -EINVAL; 2812 } 2813 2814 /* Read the buffer */ 2815 for (i = 0; i < byte_cnt; i++) { 2816 bnx2x_cl45_read(bp, port, 2817 ext_phy_type, 2818 ext_phy_addr, 2819 MDIO_PMA_DEVAD, 2820 MDIO_PMA_REG_8727_TWO_WIRE_DATA_BUF + i, &val); 2821 o_buf[i] = (u8)(val & MDIO_PMA_REG_8727_TWO_WIRE_DATA_MASK); 2822 } 2823 2824 for (i = 0; i < 100; i++) { 2825 bnx2x_cl45_read(bp, port, 2826 ext_phy_type, 2827 ext_phy_addr, 2828 MDIO_PMA_DEVAD, 2829 MDIO_PMA_REG_SFP_TWO_WIRE_CTRL, &val); 2830 if ((val & MDIO_PMA_REG_SFP_TWO_WIRE_CTRL_STATUS_MASK) == 2831 MDIO_PMA_REG_SFP_TWO_WIRE_STATUS_IDLE) 2832 return 0;; 2833 msleep(1); 2834 } 2835 2836 return -EINVAL; 2837} 2838 2839u8 bnx2x_read_sfp_module_eeprom(struct link_params *params, u16 addr, 2840 u8 byte_cnt, u8 *o_buf) 2841{ 2842 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 2843 2844 if (ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726) 2845 return bnx2x_8726_read_sfp_module_eeprom(params, addr, 2846 byte_cnt, o_buf); 2847 else if (ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727) 2848 return bnx2x_8727_read_sfp_module_eeprom(params, addr, 2849 byte_cnt, o_buf); 2850 return -EINVAL; 2851} 2852 2853static u8 bnx2x_get_edc_mode(struct link_params *params, 2854 u16 *edc_mode) 2855{ 2856 struct bnx2x *bp = params->bp; 2857 u8 val, check_limiting_mode = 0; 2858 *edc_mode = EDC_MODE_LIMITING; 2859 2860 /* First check for copper cable */ 2861 if (bnx2x_read_sfp_module_eeprom(params, 2862 SFP_EEPROM_CON_TYPE_ADDR, 2863 1, 2864 &val) != 0) { 2865 DP(NETIF_MSG_LINK, "Failed to read from SFP+ module EEPROM\n"); 2866 return -EINVAL; 2867 } 2868 2869 switch (val) { 2870 case SFP_EEPROM_CON_TYPE_VAL_COPPER: 2871 { 2872 u8 copper_module_type; 2873 2874 /* Check if its active cable( includes SFP+ module) 2875 of passive cable*/ 2876 if (bnx2x_read_sfp_module_eeprom(params, 2877 SFP_EEPROM_FC_TX_TECH_ADDR, 2878 1, 2879 &copper_module_type) != 2880 0) { 2881 DP(NETIF_MSG_LINK, 2882 "Failed to read copper-cable-type" 2883 " from SFP+ EEPROM\n"); 2884 return -EINVAL; 2885 } 2886 2887 if (copper_module_type & 2888 SFP_EEPROM_FC_TX_TECH_BITMASK_COPPER_ACTIVE) { 2889 DP(NETIF_MSG_LINK, "Active Copper cable detected\n"); 2890 check_limiting_mode = 1; 2891 } else if (copper_module_type & 2892 SFP_EEPROM_FC_TX_TECH_BITMASK_COPPER_PASSIVE) { 2893 DP(NETIF_MSG_LINK, "Passive Copper" 2894 " cable detected\n"); 2895 *edc_mode = 2896 EDC_MODE_PASSIVE_DAC; 2897 } else { 2898 DP(NETIF_MSG_LINK, "Unknown copper-cable-" 2899 "type 0x%x !!!\n", copper_module_type); 2900 return -EINVAL; 2901 } 2902 break; 2903 } 2904 case SFP_EEPROM_CON_TYPE_VAL_LC: 2905 DP(NETIF_MSG_LINK, "Optic module detected\n"); 2906 check_limiting_mode = 1; 2907 break; 2908 default: 2909 DP(NETIF_MSG_LINK, "Unable to determine module type 0x%x !!!\n", 2910 val); 2911 return -EINVAL; 2912 } 2913 2914 if (check_limiting_mode) { 2915 u8 options[SFP_EEPROM_OPTIONS_SIZE]; 2916 if (bnx2x_read_sfp_module_eeprom(params, 2917 SFP_EEPROM_OPTIONS_ADDR, 2918 SFP_EEPROM_OPTIONS_SIZE, 2919 options) != 0) { 2920 DP(NETIF_MSG_LINK, "Failed to read Option" 2921 " field from module EEPROM\n"); 2922 return -EINVAL; 2923 } 2924 if ((options[0] & SFP_EEPROM_OPTIONS_LINEAR_RX_OUT_MASK)) 2925 *edc_mode = EDC_MODE_LINEAR; 2926 else 2927 *edc_mode = EDC_MODE_LIMITING; 2928 } 2929 DP(NETIF_MSG_LINK, "EDC mode is set to 0x%x\n", *edc_mode); 2930 return 0; 2931} 2932 2933/* This function read the relevant field from the module ( SFP+ ), 2934 and verify it is compliant with this board */ 2935static u8 bnx2x_verify_sfp_module(struct link_params *params) 2936{ 2937 struct bnx2x *bp = params->bp; 2938 u32 val; 2939 u32 fw_resp; 2940 char vendor_name[SFP_EEPROM_VENDOR_NAME_SIZE+1]; 2941 char vendor_pn[SFP_EEPROM_PART_NO_SIZE+1]; 2942 2943 val = REG_RD(bp, params->shmem_base + 2944 offsetof(struct shmem_region, dev_info. 2945 port_feature_config[params->port].config)); 2946 if ((val & PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_MASK) == 2947 PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_NO_ENFORCEMENT) { 2948 DP(NETIF_MSG_LINK, "NOT enforcing module verification\n"); 2949 return 0; 2950 } 2951 2952 /* Ask the FW to validate the module */ 2953 if (!(params->feature_config_flags & 2954 FEATURE_CONFIG_BC_SUPPORTS_OPT_MDL_VRFY)) { 2955 DP(NETIF_MSG_LINK, "FW does not support OPT MDL " 2956 "verification\n"); 2957 return -EINVAL; 2958 } 2959 2960 fw_resp = bnx2x_fw_command(bp, DRV_MSG_CODE_VRFY_OPT_MDL); 2961 if (fw_resp == FW_MSG_CODE_VRFY_OPT_MDL_SUCCESS) { 2962 DP(NETIF_MSG_LINK, "Approved module\n"); 2963 return 0; 2964 } 2965 2966 /* format the warning message */ 2967 if (bnx2x_read_sfp_module_eeprom(params, 2968 SFP_EEPROM_VENDOR_NAME_ADDR, 2969 SFP_EEPROM_VENDOR_NAME_SIZE, 2970 (u8 *)vendor_name)) 2971 vendor_name[0] = '\0'; 2972 else 2973 vendor_name[SFP_EEPROM_VENDOR_NAME_SIZE] = '\0'; 2974 if (bnx2x_read_sfp_module_eeprom(params, 2975 SFP_EEPROM_PART_NO_ADDR, 2976 SFP_EEPROM_PART_NO_SIZE, 2977 (u8 *)vendor_pn)) 2978 vendor_pn[0] = '\0'; 2979 else 2980 vendor_pn[SFP_EEPROM_PART_NO_SIZE] = '\0'; 2981 2982 netdev_info(bp->dev, "Warning: Unqualified SFP+ module detected, Port %d from %s part number %s\n", 2983 params->port, vendor_name, vendor_pn); 2984 return -EINVAL; 2985} 2986 2987static u8 bnx2x_bcm8726_set_limiting_mode(struct link_params *params, 2988 u16 edc_mode) 2989{ 2990 struct bnx2x *bp = params->bp; 2991 u8 port = params->port; 2992 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 2993 u16 cur_limiting_mode; 2994 2995 bnx2x_cl45_read(bp, port, 2996 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726, 2997 ext_phy_addr, 2998 MDIO_PMA_DEVAD, 2999 MDIO_PMA_REG_ROM_VER2, 3000 &cur_limiting_mode); 3001 DP(NETIF_MSG_LINK, "Current Limiting mode is 0x%x\n", 3002 cur_limiting_mode); 3003 3004 if (edc_mode == EDC_MODE_LIMITING) { 3005 DP(NETIF_MSG_LINK, 3006 "Setting LIMITING MODE\n"); 3007 bnx2x_cl45_write(bp, port, 3008 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726, 3009 ext_phy_addr, 3010 MDIO_PMA_DEVAD, 3011 MDIO_PMA_REG_ROM_VER2, 3012 EDC_MODE_LIMITING); 3013 } else { /* LRM mode ( default )*/ 3014 3015 DP(NETIF_MSG_LINK, "Setting LRM MODE\n"); 3016 3017 /* Changing to LRM mode takes quite few seconds. 3018 So do it only if current mode is limiting 3019 ( default is LRM )*/ 3020 if (cur_limiting_mode != EDC_MODE_LIMITING) 3021 return 0; 3022 3023 bnx2x_cl45_write(bp, port, 3024 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726, 3025 ext_phy_addr, 3026 MDIO_PMA_DEVAD, 3027 MDIO_PMA_REG_LRM_MODE, 3028 0); 3029 bnx2x_cl45_write(bp, port, 3030 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726, 3031 ext_phy_addr, 3032 MDIO_PMA_DEVAD, 3033 MDIO_PMA_REG_ROM_VER2, 3034 0x128); 3035 bnx2x_cl45_write(bp, port, 3036 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726, 3037 ext_phy_addr, 3038 MDIO_PMA_DEVAD, 3039 MDIO_PMA_REG_MISC_CTRL0, 3040 0x4008); 3041 bnx2x_cl45_write(bp, port, 3042 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726, 3043 ext_phy_addr, 3044 MDIO_PMA_DEVAD, 3045 MDIO_PMA_REG_LRM_MODE, 3046 0xaaaa); 3047 } 3048 return 0; 3049} 3050 3051static u8 bnx2x_bcm8727_set_limiting_mode(struct link_params *params, 3052 u16 edc_mode) 3053{ 3054 struct bnx2x *bp = params->bp; 3055 u8 port = params->port; 3056 u16 phy_identifier; 3057 u16 rom_ver2_val; 3058 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 3059 3060 bnx2x_cl45_read(bp, port, 3061 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 3062 ext_phy_addr, 3063 MDIO_PMA_DEVAD, 3064 MDIO_PMA_REG_PHY_IDENTIFIER, 3065 &phy_identifier); 3066 3067 bnx2x_cl45_write(bp, port, 3068 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 3069 ext_phy_addr, 3070 MDIO_PMA_DEVAD, 3071 MDIO_PMA_REG_PHY_IDENTIFIER, 3072 (phy_identifier & ~(1<<9))); 3073 3074 bnx2x_cl45_read(bp, port, 3075 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 3076 ext_phy_addr, 3077 MDIO_PMA_DEVAD, 3078 MDIO_PMA_REG_ROM_VER2, 3079 &rom_ver2_val); 3080 /* Keep the MSB 8-bits, and set the LSB 8-bits with the edc_mode */ 3081 bnx2x_cl45_write(bp, port, 3082 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 3083 ext_phy_addr, 3084 MDIO_PMA_DEVAD, 3085 MDIO_PMA_REG_ROM_VER2, 3086 (rom_ver2_val & 0xff00) | (edc_mode & 0x00ff)); 3087 3088 bnx2x_cl45_write(bp, port, 3089 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 3090 ext_phy_addr, 3091 MDIO_PMA_DEVAD, 3092 MDIO_PMA_REG_PHY_IDENTIFIER, 3093 (phy_identifier | (1<<9))); 3094 3095 return 0; 3096} 3097 3098 3099static u8 bnx2x_wait_for_sfp_module_initialized(struct link_params *params) 3100{ 3101 u8 val; 3102 struct bnx2x *bp = params->bp; 3103 u16 timeout; 3104 /* Initialization time after hot-plug may take up to 300ms for some 3105 phys type ( e.g. JDSU ) */ 3106 for (timeout = 0; timeout < 60; timeout++) { 3107 if (bnx2x_read_sfp_module_eeprom(params, 1, 1, &val) 3108 == 0) { 3109 DP(NETIF_MSG_LINK, "SFP+ module initialization " 3110 "took %d ms\n", timeout * 5); 3111 return 0; 3112 } 3113 msleep(5); 3114 } 3115 return -EINVAL; 3116} 3117 3118static void bnx2x_8727_power_module(struct bnx2x *bp, 3119 struct link_params *params, 3120 u8 ext_phy_addr, u8 is_power_up) { 3121 /* Make sure GPIOs are not using for LED mode */ 3122 u16 val; 3123 u8 port = params->port; 3124 /* 3125 * In the GPIO register, bit 4 is use to detemine if the GPIOs are 3126 * operating as INPUT or as OUTPUT. Bit 1 is for input, and 0 for 3127 * output 3128 * Bits 0-1 determine the gpios value for OUTPUT in case bit 4 val is 0 3129 * Bits 8-9 determine the gpios value for INPUT in case bit 4 val is 1 3130 * where the 1st bit is the over-current(only input), and 2nd bit is 3131 * for power( only output ) 3132 */ 3133 3134 /* 3135 * In case of NOC feature is disabled and power is up, set GPIO control 3136 * as input to enable listening of over-current indication 3137 */ 3138 3139 if (!(params->feature_config_flags & 3140 FEATURE_CONFIG_BCM8727_NOC) && is_power_up) 3141 val = (1<<4); 3142 else 3143 /* 3144 * Set GPIO control to OUTPUT, and set the power bit 3145 * to according to the is_power_up 3146 */ 3147 val = ((!(is_power_up)) << 1); 3148 3149 bnx2x_cl45_write(bp, port, 3150 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 3151 ext_phy_addr, 3152 MDIO_PMA_DEVAD, 3153 MDIO_PMA_REG_8727_GPIO_CTRL, 3154 val); 3155} 3156 3157static u8 bnx2x_sfp_module_detection(struct link_params *params) 3158{ 3159 struct bnx2x *bp = params->bp; 3160 u16 edc_mode; 3161 u8 rc = 0; 3162 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 3163 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 3164 u32 val = REG_RD(bp, params->shmem_base + 3165 offsetof(struct shmem_region, dev_info. 3166 port_feature_config[params->port].config)); 3167 3168 DP(NETIF_MSG_LINK, "SFP+ module plugged in/out detected on port %d\n", 3169 params->port); 3170 3171 if (bnx2x_get_edc_mode(params, &edc_mode) != 0) { 3172 DP(NETIF_MSG_LINK, "Failed to get valid module type\n"); 3173 return -EINVAL; 3174 } else if (bnx2x_verify_sfp_module(params) != 3175 0) { 3176 /* check SFP+ module compatibility */ 3177 DP(NETIF_MSG_LINK, "Module verification failed!!\n"); 3178 rc = -EINVAL; 3179 /* Turn on fault module-detected led */ 3180 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_0, 3181 MISC_REGISTERS_GPIO_HIGH, 3182 params->port); 3183 if ((ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727) && 3184 ((val & PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_MASK) == 3185 PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_POWER_DOWN)) { 3186 /* Shutdown SFP+ module */ 3187 DP(NETIF_MSG_LINK, "Shutdown SFP+ module!!\n"); 3188 bnx2x_8727_power_module(bp, params, 3189 ext_phy_addr, 0); 3190 return rc; 3191 } 3192 } else { 3193 /* Turn off fault module-detected led */ 3194 DP(NETIF_MSG_LINK, "Turn off fault module-detected led\n"); 3195 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_0, 3196 MISC_REGISTERS_GPIO_LOW, 3197 params->port); 3198 } 3199 3200 /* power up the SFP module */ 3201 if (ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727) 3202 bnx2x_8727_power_module(bp, params, ext_phy_addr, 1); 3203 3204 /* Check and set limiting mode / LRM mode on 8726. 3205 On 8727 it is done automatically */ 3206 if (ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726) 3207 bnx2x_bcm8726_set_limiting_mode(params, edc_mode); 3208 else 3209 bnx2x_bcm8727_set_limiting_mode(params, edc_mode); 3210 /* 3211 * Enable transmit for this module if the module is approved, or 3212 * if unapproved modules should also enable the Tx laser 3213 */ 3214 if (rc == 0 || 3215 (val & PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_MASK) != 3216 PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_DISABLE_TX_LASER) 3217 bnx2x_sfp_set_transmitter(bp, params->port, 3218 ext_phy_type, ext_phy_addr, 1); 3219 else 3220 bnx2x_sfp_set_transmitter(bp, params->port, 3221 ext_phy_type, ext_phy_addr, 0); 3222 3223 return rc; 3224} 3225 3226void bnx2x_handle_module_detect_int(struct link_params *params) 3227{ 3228 struct bnx2x *bp = params->bp; 3229 u32 gpio_val; 3230 u8 port = params->port; 3231 3232 /* Set valid module led off */ 3233 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_0, 3234 MISC_REGISTERS_GPIO_HIGH, 3235 params->port); 3236 3237 /* Get current gpio val refelecting module plugged in / out*/ 3238 gpio_val = bnx2x_get_gpio(bp, MISC_REGISTERS_GPIO_3, port); 3239 3240 /* Call the handling function in case module is detected */ 3241 if (gpio_val == 0) { 3242 3243 bnx2x_set_gpio_int(bp, MISC_REGISTERS_GPIO_3, 3244 MISC_REGISTERS_GPIO_INT_OUTPUT_CLR, 3245 port); 3246 3247 if (bnx2x_wait_for_sfp_module_initialized(params) == 3248 0) 3249 bnx2x_sfp_module_detection(params); 3250 else 3251 DP(NETIF_MSG_LINK, "SFP+ module is not initialized\n"); 3252 } else { 3253 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 3254 3255 u32 ext_phy_type = 3256 XGXS_EXT_PHY_TYPE(params->ext_phy_config); 3257 u32 val = REG_RD(bp, params->shmem_base + 3258 offsetof(struct shmem_region, dev_info. 3259 port_feature_config[params->port]. 3260 config)); 3261 3262 bnx2x_set_gpio_int(bp, MISC_REGISTERS_GPIO_3, 3263 MISC_REGISTERS_GPIO_INT_OUTPUT_SET, 3264 port); 3265 /* Module was plugged out. */ 3266 /* Disable transmit for this module */ 3267 if ((val & PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_MASK) == 3268 PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_DISABLE_TX_LASER) 3269 bnx2x_sfp_set_transmitter(bp, params->port, 3270 ext_phy_type, ext_phy_addr, 0); 3271 } 3272} 3273 3274static void bnx2x_bcm807x_force_10G(struct link_params *params) 3275{ 3276 struct bnx2x *bp = params->bp; 3277 u8 port = params->port; 3278 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 3279 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 3280 3281 /* Force KR or KX */ 3282 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3283 MDIO_PMA_DEVAD, 3284 MDIO_PMA_REG_CTRL, 3285 0x2040); 3286 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3287 MDIO_PMA_DEVAD, 3288 MDIO_PMA_REG_10G_CTRL2, 3289 0x000b); 3290 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3291 MDIO_PMA_DEVAD, 3292 MDIO_PMA_REG_BCM_CTRL, 3293 0x0000); 3294 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3295 MDIO_AN_DEVAD, 3296 MDIO_AN_REG_CTRL, 3297 0x0000); 3298} 3299 3300static void bnx2x_bcm8073_set_xaui_low_power_mode(struct link_params *params) 3301{ 3302 struct bnx2x *bp = params->bp; 3303 u8 port = params->port; 3304 u16 val; 3305 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 3306 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 3307 3308 bnx2x_cl45_read(bp, params->port, 3309 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 3310 ext_phy_addr, 3311 MDIO_PMA_DEVAD, 3312 MDIO_PMA_REG_8073_CHIP_REV, &val); 3313 3314 if (val == 0) { 3315 /* Mustn't set low power mode in 8073 A0 */ 3316 return; 3317 } 3318 3319 /* Disable PLL sequencer (use read-modify-write to clear bit 13) */ 3320 bnx2x_cl45_read(bp, port, ext_phy_type, ext_phy_addr, 3321 MDIO_XS_DEVAD, 3322 MDIO_XS_PLL_SEQUENCER, &val); 3323 val &= ~(1<<13); 3324 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3325 MDIO_XS_DEVAD, MDIO_XS_PLL_SEQUENCER, val); 3326 3327 /* PLL controls */ 3328 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3329 MDIO_XS_DEVAD, 0x805E, 0x1077); 3330 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3331 MDIO_XS_DEVAD, 0x805D, 0x0000); 3332 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3333 MDIO_XS_DEVAD, 0x805C, 0x030B); 3334 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3335 MDIO_XS_DEVAD, 0x805B, 0x1240); 3336 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3337 MDIO_XS_DEVAD, 0x805A, 0x2490); 3338 3339 /* Tx Controls */ 3340 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3341 MDIO_XS_DEVAD, 0x80A7, 0x0C74); 3342 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3343 MDIO_XS_DEVAD, 0x80A6, 0x9041); 3344 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3345 MDIO_XS_DEVAD, 0x80A5, 0x4640); 3346 3347 /* Rx Controls */ 3348 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3349 MDIO_XS_DEVAD, 0x80FE, 0x01C4); 3350 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3351 MDIO_XS_DEVAD, 0x80FD, 0x9249); 3352 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3353 MDIO_XS_DEVAD, 0x80FC, 0x2015); 3354 3355 /* Enable PLL sequencer (use read-modify-write to set bit 13) */ 3356 bnx2x_cl45_read(bp, port, ext_phy_type, ext_phy_addr, 3357 MDIO_XS_DEVAD, 3358 MDIO_XS_PLL_SEQUENCER, &val); 3359 val |= (1<<13); 3360 bnx2x_cl45_write(bp, port, ext_phy_type, ext_phy_addr, 3361 MDIO_XS_DEVAD, MDIO_XS_PLL_SEQUENCER, val); 3362} 3363 3364static void bnx2x_8073_set_pause_cl37(struct link_params *params, 3365 struct link_vars *vars) 3366{ 3367 struct bnx2x *bp = params->bp; 3368 u16 cl37_val; 3369 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 3370 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 3371 3372 bnx2x_cl45_read(bp, params->port, 3373 ext_phy_type, 3374 ext_phy_addr, 3375 MDIO_AN_DEVAD, 3376 MDIO_AN_REG_CL37_FC_LD, &cl37_val); 3377 3378 cl37_val &= ~MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_BOTH; 3379 /* Please refer to Table 28B-3 of 802.3ab-1999 spec. */ 3380 3381 if ((vars->ieee_fc & 3382 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_SYMMETRIC) == 3383 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_SYMMETRIC) { 3384 cl37_val |= MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_SYMMETRIC; 3385 } 3386 if ((vars->ieee_fc & 3387 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_ASYMMETRIC) == 3388 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_ASYMMETRIC) { 3389 cl37_val |= MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_ASYMMETRIC; 3390 } 3391 if ((vars->ieee_fc & 3392 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_BOTH) == 3393 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_BOTH) { 3394 cl37_val |= MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_BOTH; 3395 } 3396 DP(NETIF_MSG_LINK, 3397 "Ext phy AN advertize cl37 0x%x\n", cl37_val); 3398 3399 bnx2x_cl45_write(bp, params->port, 3400 ext_phy_type, 3401 ext_phy_addr, 3402 MDIO_AN_DEVAD, 3403 MDIO_AN_REG_CL37_FC_LD, cl37_val); 3404 msleep(500); 3405} 3406 3407static void bnx2x_ext_phy_set_pause(struct link_params *params, 3408 struct link_vars *vars) 3409{ 3410 struct bnx2x *bp = params->bp; 3411 u16 val; 3412 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 3413 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 3414 3415 /* read modify write pause advertizing */ 3416 bnx2x_cl45_read(bp, params->port, 3417 ext_phy_type, 3418 ext_phy_addr, 3419 MDIO_AN_DEVAD, 3420 MDIO_AN_REG_ADV_PAUSE, &val); 3421 3422 val &= ~MDIO_AN_REG_ADV_PAUSE_BOTH; 3423 3424 /* Please refer to Table 28B-3 of 802.3ab-1999 spec. */ 3425 3426 if ((vars->ieee_fc & 3427 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_ASYMMETRIC) == 3428 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_ASYMMETRIC) { 3429 val |= MDIO_AN_REG_ADV_PAUSE_ASYMMETRIC; 3430 } 3431 if ((vars->ieee_fc & 3432 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_BOTH) == 3433 MDIO_COMBO_IEEE0_AUTO_NEG_ADV_PAUSE_BOTH) { 3434 val |= 3435 MDIO_AN_REG_ADV_PAUSE_PAUSE; 3436 } 3437 DP(NETIF_MSG_LINK, 3438 "Ext phy AN advertize 0x%x\n", val); 3439 bnx2x_cl45_write(bp, params->port, 3440 ext_phy_type, 3441 ext_phy_addr, 3442 MDIO_AN_DEVAD, 3443 MDIO_AN_REG_ADV_PAUSE, val); 3444} 3445static void bnx2x_set_preemphasis(struct link_params *params) 3446{ 3447 u16 bank, i = 0; 3448 struct bnx2x *bp = params->bp; 3449 3450 for (bank = MDIO_REG_BANK_RX0, i = 0; bank <= MDIO_REG_BANK_RX3; 3451 bank += (MDIO_REG_BANK_RX1-MDIO_REG_BANK_RX0), i++) { 3452 CL45_WR_OVER_CL22(bp, params->port, 3453 params->phy_addr, 3454 bank, 3455 MDIO_RX0_RX_EQ_BOOST, 3456 params->xgxs_config_rx[i]); 3457 } 3458 3459 for (bank = MDIO_REG_BANK_TX0, i = 0; bank <= MDIO_REG_BANK_TX3; 3460 bank += (MDIO_REG_BANK_TX1 - MDIO_REG_BANK_TX0), i++) { 3461 CL45_WR_OVER_CL22(bp, params->port, 3462 params->phy_addr, 3463 bank, 3464 MDIO_TX0_TX_DRIVER, 3465 params->xgxs_config_tx[i]); 3466 } 3467} 3468 3469 3470static void bnx2x_8481_set_led4(struct link_params *params, 3471 u32 ext_phy_type, u8 ext_phy_addr) 3472{ 3473 struct bnx2x *bp = params->bp; 3474 3475 /* PHYC_CTL_LED_CTL */ 3476 bnx2x_cl45_write(bp, params->port, 3477 ext_phy_type, 3478 ext_phy_addr, 3479 MDIO_PMA_DEVAD, 3480 MDIO_PMA_REG_8481_LINK_SIGNAL, 0xa482); 3481 3482 /* Unmask LED4 for 10G link */ 3483 bnx2x_cl45_write(bp, params->port, 3484 ext_phy_type, 3485 ext_phy_addr, 3486 MDIO_PMA_DEVAD, 3487 MDIO_PMA_REG_8481_SIGNAL_MASK, (1<<6)); 3488 /* 'Interrupt Mask' */ 3489 bnx2x_cl45_write(bp, params->port, 3490 ext_phy_type, 3491 ext_phy_addr, 3492 MDIO_AN_DEVAD, 3493 0xFFFB, 0xFFFD); 3494} 3495static void bnx2x_8481_set_legacy_led_mode(struct link_params *params, 3496 u32 ext_phy_type, u8 ext_phy_addr) 3497{ 3498 struct bnx2x *bp = params->bp; 3499 3500 /* LED1 (10G Link): Disable LED1 when 10/100/1000 link */ 3501 /* LED2 (1G/100/10 Link): Enable LED2 when 10/100/1000 link) */ 3502 bnx2x_cl45_write(bp, params->port, 3503 ext_phy_type, 3504 ext_phy_addr, 3505 MDIO_AN_DEVAD, 3506 MDIO_AN_REG_8481_LEGACY_SHADOW, 3507 (1<<15) | (0xd << 10) | (0xc<<4) | 0xe); 3508} 3509 3510static void bnx2x_8481_set_10G_led_mode(struct link_params *params, 3511 u32 ext_phy_type, u8 ext_phy_addr) 3512{ 3513 struct bnx2x *bp = params->bp; 3514 u16 val1; 3515 3516 /* LED1 (10G Link) */ 3517 /* Enable continuse based on source 7(10G-link) */ 3518 bnx2x_cl45_read(bp, params->port, 3519 ext_phy_type, 3520 ext_phy_addr, 3521 MDIO_PMA_DEVAD, 3522 MDIO_PMA_REG_8481_LINK_SIGNAL, 3523 &val1); 3524 /* Set bit 2 to 0, and bits [1:0] to 10 */ 3525 val1 &= ~((1<<0) | (1<<2) | (1<<7)); /* Clear bits 0,2,7*/ 3526 val1 |= ((1<<1) | (1<<6)); /* Set bit 1, 6 */ 3527 3528 bnx2x_cl45_write(bp, params->port, 3529 ext_phy_type, 3530 ext_phy_addr, 3531 MDIO_PMA_DEVAD, 3532 MDIO_PMA_REG_8481_LINK_SIGNAL, 3533 val1); 3534 3535 /* Unmask LED1 for 10G link */ 3536 bnx2x_cl45_read(bp, params->port, 3537 ext_phy_type, 3538 ext_phy_addr, 3539 MDIO_PMA_DEVAD, 3540 MDIO_PMA_REG_8481_LED1_MASK, 3541 &val1); 3542 /* Set bit 2 to 0, and bits [1:0] to 10 */ 3543 val1 |= (1<<7); 3544 bnx2x_cl45_write(bp, params->port, 3545 ext_phy_type, 3546 ext_phy_addr, 3547 MDIO_PMA_DEVAD, 3548 MDIO_PMA_REG_8481_LED1_MASK, 3549 val1); 3550 3551 /* LED2 (1G/100/10G Link) */ 3552 /* Mask LED2 for 10G link */ 3553 bnx2x_cl45_write(bp, params->port, 3554 ext_phy_type, 3555 ext_phy_addr, 3556 MDIO_PMA_DEVAD, 3557 MDIO_PMA_REG_8481_LED2_MASK, 3558 0); 3559 3560 /* Unmask LED3 for 10G link */ 3561 bnx2x_cl45_write(bp, params->port, 3562 ext_phy_type, 3563 ext_phy_addr, 3564 MDIO_PMA_DEVAD, 3565 MDIO_PMA_REG_8481_LED3_MASK, 3566 0x6); 3567 bnx2x_cl45_write(bp, params->port, 3568 ext_phy_type, 3569 ext_phy_addr, 3570 MDIO_PMA_DEVAD, 3571 MDIO_PMA_REG_8481_LED3_BLINK, 3572 0); 3573} 3574 3575 3576static void bnx2x_init_internal_phy(struct link_params *params, 3577 struct link_vars *vars, 3578 u8 enable_cl73) 3579{ 3580 struct bnx2x *bp = params->bp; 3581 3582 if (!(vars->phy_flags & PHY_SGMII_FLAG)) { 3583 if ((XGXS_EXT_PHY_TYPE(params->ext_phy_config) == 3584 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT) && 3585 (params->feature_config_flags & 3586 FEATURE_CONFIG_OVERRIDE_PREEMPHASIS_ENABLED)) 3587 bnx2x_set_preemphasis(params); 3588 3589 /* forced speed requested? */ 3590 if (vars->line_speed != SPEED_AUTO_NEG || 3591 ((XGXS_EXT_PHY_TYPE(params->ext_phy_config) == 3592 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT) && 3593 params->loopback_mode == LOOPBACK_EXT)) { 3594 DP(NETIF_MSG_LINK, "not SGMII, no AN\n"); 3595 3596 /* disable autoneg */ 3597 bnx2x_set_autoneg(params, vars, 0); 3598 3599 /* program speed and duplex */ 3600 bnx2x_program_serdes(params, vars); 3601 3602 } else { /* AN_mode */ 3603 DP(NETIF_MSG_LINK, "not SGMII, AN\n"); 3604 3605 /* AN enabled */ 3606 bnx2x_set_brcm_cl37_advertisment(params); 3607 3608 /* program duplex & pause advertisement (for aneg) */ 3609 bnx2x_set_ieee_aneg_advertisment(params, 3610 vars->ieee_fc); 3611 3612 /* enable autoneg */ 3613 bnx2x_set_autoneg(params, vars, enable_cl73); 3614 3615 /* enable and restart AN */ 3616 bnx2x_restart_autoneg(params, enable_cl73); 3617 } 3618 3619 } else { /* SGMII mode */ 3620 DP(NETIF_MSG_LINK, "SGMII\n"); 3621 3622 bnx2x_initialize_sgmii_process(params, vars); 3623 } 3624} 3625 3626static u8 bnx2x_ext_phy_init(struct link_params *params, struct link_vars *vars) 3627{ 3628 struct bnx2x *bp = params->bp; 3629 u32 ext_phy_type; 3630 u8 ext_phy_addr; 3631 u16 cnt; 3632 u16 ctrl = 0; 3633 u16 val = 0; 3634 u8 rc = 0; 3635 3636 if (vars->phy_flags & PHY_XGXS_FLAG) { 3637 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 3638 3639 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 3640 /* Make sure that the soft reset is off (expect for the 8072: 3641 * due to the lock, it will be done inside the specific 3642 * handling) 3643 */ 3644 if ((ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT) && 3645 (ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_FAILURE) && 3646 (ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_NOT_CONN) && 3647 (ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072) && 3648 (ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073)) { 3649 /* Wait for soft reset to get cleared upto 1 sec */ 3650 for (cnt = 0; cnt < 1000; cnt++) { 3651 bnx2x_cl45_read(bp, params->port, 3652 ext_phy_type, 3653 ext_phy_addr, 3654 MDIO_PMA_DEVAD, 3655 MDIO_PMA_REG_CTRL, &ctrl); 3656 if (!(ctrl & (1<<15))) 3657 break; 3658 msleep(1); 3659 } 3660 DP(NETIF_MSG_LINK, "control reg 0x%x (after %d ms)\n", 3661 ctrl, cnt); 3662 } 3663 3664 switch (ext_phy_type) { 3665 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT: 3666 break; 3667 3668 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705: 3669 DP(NETIF_MSG_LINK, "XGXS 8705\n"); 3670 3671 bnx2x_cl45_write(bp, params->port, 3672 ext_phy_type, 3673 ext_phy_addr, 3674 MDIO_PMA_DEVAD, 3675 MDIO_PMA_REG_MISC_CTRL, 3676 0x8288); 3677 bnx2x_cl45_write(bp, params->port, 3678 ext_phy_type, 3679 ext_phy_addr, 3680 MDIO_PMA_DEVAD, 3681 MDIO_PMA_REG_PHY_IDENTIFIER, 3682 0x7fbf); 3683 bnx2x_cl45_write(bp, params->port, 3684 ext_phy_type, 3685 ext_phy_addr, 3686 MDIO_PMA_DEVAD, 3687 MDIO_PMA_REG_CMU_PLL_BYPASS, 3688 0x0100); 3689 bnx2x_cl45_write(bp, params->port, 3690 ext_phy_type, 3691 ext_phy_addr, 3692 MDIO_WIS_DEVAD, 3693 MDIO_WIS_REG_LASI_CNTL, 0x1); 3694 3695 /* BCM8705 doesn't have microcode, hence the 0 */ 3696 bnx2x_save_spirom_version(bp, params->port, 3697 params->shmem_base, 0); 3698 break; 3699 3700 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706: 3701 /* Wait until fw is loaded */ 3702 for (cnt = 0; cnt < 100; cnt++) { 3703 bnx2x_cl45_read(bp, params->port, ext_phy_type, 3704 ext_phy_addr, MDIO_PMA_DEVAD, 3705 MDIO_PMA_REG_ROM_VER1, &val); 3706 if (val) 3707 break; 3708 msleep(10); 3709 } 3710 DP(NETIF_MSG_LINK, "XGXS 8706 is initialized " 3711 "after %d ms\n", cnt); 3712 if ((params->feature_config_flags & 3713 FEATURE_CONFIG_OVERRIDE_PREEMPHASIS_ENABLED)) { 3714 u8 i; 3715 u16 reg; 3716 for (i = 0; i < 4; i++) { 3717 reg = MDIO_XS_8706_REG_BANK_RX0 + 3718 i*(MDIO_XS_8706_REG_BANK_RX1 - 3719 MDIO_XS_8706_REG_BANK_RX0); 3720 bnx2x_cl45_read(bp, params->port, 3721 ext_phy_type, 3722 ext_phy_addr, 3723 MDIO_XS_DEVAD, 3724 reg, &val); 3725 /* Clear first 3 bits of the control */ 3726 val &= ~0x7; 3727 /* Set control bits according to 3728 configuation */ 3729 val |= (params->xgxs_config_rx[i] & 3730 0x7); 3731 DP(NETIF_MSG_LINK, "Setting RX" 3732 "Equalizer to BCM8706 reg 0x%x" 3733 " <-- val 0x%x\n", reg, val); 3734 bnx2x_cl45_write(bp, params->port, 3735 ext_phy_type, 3736 ext_phy_addr, 3737 MDIO_XS_DEVAD, 3738 reg, val); 3739 } 3740 } 3741 /* Force speed */ 3742 if (params->req_line_speed == SPEED_10000) { 3743 DP(NETIF_MSG_LINK, "XGXS 8706 force 10Gbps\n"); 3744 3745 bnx2x_cl45_write(bp, params->port, 3746 ext_phy_type, 3747 ext_phy_addr, 3748 MDIO_PMA_DEVAD, 3749 MDIO_PMA_REG_DIGITAL_CTRL, 3750 0x400); 3751 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3752 ext_phy_addr, MDIO_PMA_DEVAD, 3753 MDIO_PMA_REG_LASI_CTRL, 1); 3754 } else { 3755 /* Force 1Gbps using autoneg with 1G 3756 advertisment */ 3757 3758 /* Allow CL37 through CL73 */ 3759 DP(NETIF_MSG_LINK, "XGXS 8706 AutoNeg\n"); 3760 bnx2x_cl45_write(bp, params->port, 3761 ext_phy_type, 3762 ext_phy_addr, 3763 MDIO_AN_DEVAD, 3764 MDIO_AN_REG_CL37_CL73, 3765 0x040c); 3766 3767 /* Enable Full-Duplex advertisment on CL37 */ 3768 bnx2x_cl45_write(bp, params->port, 3769 ext_phy_type, 3770 ext_phy_addr, 3771 MDIO_AN_DEVAD, 3772 MDIO_AN_REG_CL37_FC_LP, 3773 0x0020); 3774 /* Enable CL37 AN */ 3775 bnx2x_cl45_write(bp, params->port, 3776 ext_phy_type, 3777 ext_phy_addr, 3778 MDIO_AN_DEVAD, 3779 MDIO_AN_REG_CL37_AN, 3780 0x1000); 3781 /* 1G support */ 3782 bnx2x_cl45_write(bp, params->port, 3783 ext_phy_type, 3784 ext_phy_addr, 3785 MDIO_AN_DEVAD, 3786 MDIO_AN_REG_ADV, (1<<5)); 3787 3788 /* Enable clause 73 AN */ 3789 bnx2x_cl45_write(bp, params->port, 3790 ext_phy_type, 3791 ext_phy_addr, 3792 MDIO_AN_DEVAD, 3793 MDIO_AN_REG_CTRL, 3794 0x1200); 3795 bnx2x_cl45_write(bp, params->port, 3796 ext_phy_type, 3797 ext_phy_addr, 3798 MDIO_PMA_DEVAD, 3799 MDIO_PMA_REG_RX_ALARM_CTRL, 3800 0x0400); 3801 bnx2x_cl45_write(bp, params->port, 3802 ext_phy_type, 3803 ext_phy_addr, 3804 MDIO_PMA_DEVAD, 3805 MDIO_PMA_REG_LASI_CTRL, 0x0004); 3806 3807 } 3808 bnx2x_save_bcm_spirom_ver(bp, params->port, 3809 ext_phy_type, 3810 ext_phy_addr, 3811 params->shmem_base); 3812 break; 3813 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726: 3814 DP(NETIF_MSG_LINK, "Initializing BCM8726\n"); 3815 bnx2x_bcm8726_external_rom_boot(params); 3816 3817 /* Need to call module detected on initialization since 3818 the module detection triggered by actual module 3819 insertion might occur before driver is loaded, and when 3820 driver is loaded, it reset all registers, including the 3821 transmitter */ 3822 bnx2x_sfp_module_detection(params); 3823 3824 /* Set Flow control */ 3825 bnx2x_ext_phy_set_pause(params, vars); 3826 if (params->req_line_speed == SPEED_1000) { 3827 DP(NETIF_MSG_LINK, "Setting 1G force\n"); 3828 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3829 ext_phy_addr, MDIO_PMA_DEVAD, 3830 MDIO_PMA_REG_CTRL, 0x40); 3831 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3832 ext_phy_addr, MDIO_PMA_DEVAD, 3833 MDIO_PMA_REG_10G_CTRL2, 0xD); 3834 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3835 ext_phy_addr, MDIO_PMA_DEVAD, 3836 MDIO_PMA_REG_LASI_CTRL, 0x5); 3837 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3838 ext_phy_addr, MDIO_PMA_DEVAD, 3839 MDIO_PMA_REG_RX_ALARM_CTRL, 3840 0x400); 3841 } else if ((params->req_line_speed == 3842 SPEED_AUTO_NEG) && 3843 ((params->speed_cap_mask & 3844 PORT_HW_CFG_SPEED_CAPABILITY_D0_1G))) { 3845 DP(NETIF_MSG_LINK, "Setting 1G clause37\n"); 3846 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3847 ext_phy_addr, MDIO_AN_DEVAD, 3848 MDIO_AN_REG_ADV, 0x20); 3849 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3850 ext_phy_addr, MDIO_AN_DEVAD, 3851 MDIO_AN_REG_CL37_CL73, 0x040c); 3852 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3853 ext_phy_addr, MDIO_AN_DEVAD, 3854 MDIO_AN_REG_CL37_FC_LD, 0x0020); 3855 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3856 ext_phy_addr, MDIO_AN_DEVAD, 3857 MDIO_AN_REG_CL37_AN, 0x1000); 3858 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3859 ext_phy_addr, MDIO_AN_DEVAD, 3860 MDIO_AN_REG_CTRL, 0x1200); 3861 3862 /* Enable RX-ALARM control to receive 3863 interrupt for 1G speed change */ 3864 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3865 ext_phy_addr, MDIO_PMA_DEVAD, 3866 MDIO_PMA_REG_LASI_CTRL, 0x4); 3867 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3868 ext_phy_addr, MDIO_PMA_DEVAD, 3869 MDIO_PMA_REG_RX_ALARM_CTRL, 3870 0x400); 3871 3872 } else { /* Default 10G. Set only LASI control */ 3873 bnx2x_cl45_write(bp, params->port, ext_phy_type, 3874 ext_phy_addr, MDIO_PMA_DEVAD, 3875 MDIO_PMA_REG_LASI_CTRL, 1); 3876 } 3877 3878 /* Set TX PreEmphasis if needed */ 3879 if ((params->feature_config_flags & 3880 FEATURE_CONFIG_OVERRIDE_PREEMPHASIS_ENABLED)) { 3881 DP(NETIF_MSG_LINK, "Setting TX_CTRL1 0x%x," 3882 "TX_CTRL2 0x%x\n", 3883 params->xgxs_config_tx[0], 3884 params->xgxs_config_tx[1]); 3885 bnx2x_cl45_write(bp, params->port, 3886 ext_phy_type, 3887 ext_phy_addr, 3888 MDIO_PMA_DEVAD, 3889 MDIO_PMA_REG_8726_TX_CTRL1, 3890 params->xgxs_config_tx[0]); 3891 3892 bnx2x_cl45_write(bp, params->port, 3893 ext_phy_type, 3894 ext_phy_addr, 3895 MDIO_PMA_DEVAD, 3896 MDIO_PMA_REG_8726_TX_CTRL2, 3897 params->xgxs_config_tx[1]); 3898 } 3899 break; 3900 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072: 3901 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073: 3902 { 3903 u16 tmp1; 3904 u16 rx_alarm_ctrl_val; 3905 u16 lasi_ctrl_val; 3906 if (ext_phy_type == 3907 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072) { 3908 rx_alarm_ctrl_val = 0x400; 3909 lasi_ctrl_val = 0x0004; 3910 } else { 3911 rx_alarm_ctrl_val = (1<<2); 3912 lasi_ctrl_val = 0x0004; 3913 } 3914 3915 /* enable LASI */ 3916 bnx2x_cl45_write(bp, params->port, 3917 ext_phy_type, 3918 ext_phy_addr, 3919 MDIO_PMA_DEVAD, 3920 MDIO_PMA_REG_RX_ALARM_CTRL, 3921 rx_alarm_ctrl_val); 3922 3923 bnx2x_cl45_write(bp, params->port, 3924 ext_phy_type, 3925 ext_phy_addr, 3926 MDIO_PMA_DEVAD, 3927 MDIO_PMA_REG_LASI_CTRL, 3928 lasi_ctrl_val); 3929 3930 bnx2x_8073_set_pause_cl37(params, vars); 3931 3932 if (ext_phy_type == 3933 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072) 3934 bnx2x_bcm8072_external_rom_boot(params); 3935 else 3936 /* In case of 8073 with long xaui lines, 3937 don't set the 8073 xaui low power*/ 3938 bnx2x_bcm8073_set_xaui_low_power_mode(params); 3939 3940 bnx2x_cl45_read(bp, params->port, 3941 ext_phy_type, 3942 ext_phy_addr, 3943 MDIO_PMA_DEVAD, 3944 MDIO_PMA_REG_M8051_MSGOUT_REG, 3945 &tmp1); 3946 3947 bnx2x_cl45_read(bp, params->port, 3948 ext_phy_type, 3949 ext_phy_addr, 3950 MDIO_PMA_DEVAD, 3951 MDIO_PMA_REG_RX_ALARM, &tmp1); 3952 3953 DP(NETIF_MSG_LINK, "Before rom RX_ALARM(port1):" 3954 "0x%x\n", tmp1); 3955 3956 /* If this is forced speed, set to KR or KX 3957 * (all other are not supported) 3958 */ 3959 if (params->loopback_mode == LOOPBACK_EXT) { 3960 bnx2x_bcm807x_force_10G(params); 3961 DP(NETIF_MSG_LINK, 3962 "Forced speed 10G on 807X\n"); 3963 break; 3964 } else { 3965 bnx2x_cl45_write(bp, params->port, 3966 ext_phy_type, ext_phy_addr, 3967 MDIO_PMA_DEVAD, 3968 MDIO_PMA_REG_BCM_CTRL, 3969 0x0002); 3970 } 3971 if (params->req_line_speed != SPEED_AUTO_NEG) { 3972 if (params->req_line_speed == SPEED_10000) { 3973 val = (1<<7); 3974 } else if (params->req_line_speed == 3975 SPEED_2500) { 3976 val = (1<<5); 3977 /* Note that 2.5G works only 3978 when used with 1G advertisment */ 3979 } else 3980 val = (1<<5); 3981 } else { 3982 3983 val = 0; 3984 if (params->speed_cap_mask & 3985 PORT_HW_CFG_SPEED_CAPABILITY_D0_10G) 3986 val |= (1<<7); 3987 3988 /* Note that 2.5G works only when 3989 used with 1G advertisment */ 3990 if (params->speed_cap_mask & 3991 (PORT_HW_CFG_SPEED_CAPABILITY_D0_1G | 3992 PORT_HW_CFG_SPEED_CAPABILITY_D0_2_5G)) 3993 val |= (1<<5); 3994 DP(NETIF_MSG_LINK, 3995 "807x autoneg val = 0x%x\n", val); 3996 } 3997 3998 bnx2x_cl45_write(bp, params->port, 3999 ext_phy_type, 4000 ext_phy_addr, 4001 MDIO_AN_DEVAD, 4002 MDIO_AN_REG_ADV, val); 4003 if (ext_phy_type == 4004 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073) { 4005 bnx2x_cl45_read(bp, params->port, 4006 ext_phy_type, 4007 ext_phy_addr, 4008 MDIO_AN_DEVAD, 4009 MDIO_AN_REG_8073_2_5G, &tmp1); 4010 4011 if (((params->speed_cap_mask & 4012 PORT_HW_CFG_SPEED_CAPABILITY_D0_2_5G) && 4013 (params->req_line_speed == 4014 SPEED_AUTO_NEG)) || 4015 (params->req_line_speed == 4016 SPEED_2500)) { 4017 u16 phy_ver; 4018 /* Allow 2.5G for A1 and above */ 4019 bnx2x_cl45_read(bp, params->port, 4020 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 4021 ext_phy_addr, 4022 MDIO_PMA_DEVAD, 4023 MDIO_PMA_REG_8073_CHIP_REV, &phy_ver); 4024 DP(NETIF_MSG_LINK, "Add 2.5G\n"); 4025 if (phy_ver > 0) 4026 tmp1 |= 1; 4027 else 4028 tmp1 &= 0xfffe; 4029 } else { 4030 DP(NETIF_MSG_LINK, "Disable 2.5G\n"); 4031 tmp1 &= 0xfffe; 4032 } 4033 4034 bnx2x_cl45_write(bp, params->port, 4035 ext_phy_type, 4036 ext_phy_addr, 4037 MDIO_AN_DEVAD, 4038 MDIO_AN_REG_8073_2_5G, tmp1); 4039 } 4040 4041 /* Add support for CL37 (passive mode) II */ 4042 4043 bnx2x_cl45_read(bp, params->port, 4044 ext_phy_type, 4045 ext_phy_addr, 4046 MDIO_AN_DEVAD, 4047 MDIO_AN_REG_CL37_FC_LD, 4048 &tmp1); 4049 4050 bnx2x_cl45_write(bp, params->port, 4051 ext_phy_type, 4052 ext_phy_addr, 4053 MDIO_AN_DEVAD, 4054 MDIO_AN_REG_CL37_FC_LD, (tmp1 | 4055 ((params->req_duplex == DUPLEX_FULL) ? 4056 0x20 : 0x40))); 4057 4058 /* Add support for CL37 (passive mode) III */ 4059 bnx2x_cl45_write(bp, params->port, 4060 ext_phy_type, 4061 ext_phy_addr, 4062 MDIO_AN_DEVAD, 4063 MDIO_AN_REG_CL37_AN, 0x1000); 4064 4065 if (ext_phy_type == 4066 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073) { 4067 /* The SNR will improve about 2db by changing 4068 BW and FEE main tap. Rest commands are executed 4069 after link is up*/ 4070 /*Change FFE main cursor to 5 in EDC register*/ 4071 if (bnx2x_8073_is_snr_needed(params)) 4072 bnx2x_cl45_write(bp, params->port, 4073 ext_phy_type, 4074 ext_phy_addr, 4075 MDIO_PMA_DEVAD, 4076 MDIO_PMA_REG_EDC_FFE_MAIN, 4077 0xFB0C); 4078 4079 /* Enable FEC (Forware Error Correction) 4080 Request in the AN */ 4081 bnx2x_cl45_read(bp, params->port, 4082 ext_phy_type, 4083 ext_phy_addr, 4084 MDIO_AN_DEVAD, 4085 MDIO_AN_REG_ADV2, &tmp1); 4086 4087 tmp1 |= (1<<15); 4088 4089 bnx2x_cl45_write(bp, params->port, 4090 ext_phy_type, 4091 ext_phy_addr, 4092 MDIO_AN_DEVAD, 4093 MDIO_AN_REG_ADV2, tmp1); 4094 4095 } 4096 4097 bnx2x_ext_phy_set_pause(params, vars); 4098 4099 /* Restart autoneg */ 4100 msleep(500); 4101 bnx2x_cl45_write(bp, params->port, 4102 ext_phy_type, 4103 ext_phy_addr, 4104 MDIO_AN_DEVAD, 4105 MDIO_AN_REG_CTRL, 0x1200); 4106 DP(NETIF_MSG_LINK, "807x Autoneg Restart: " 4107 "Advertise 1G=%x, 10G=%x\n", 4108 ((val & (1<<5)) > 0), 4109 ((val & (1<<7)) > 0)); 4110 break; 4111 } 4112 4113 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727: 4114 { 4115 u16 tmp1; 4116 u16 rx_alarm_ctrl_val; 4117 u16 lasi_ctrl_val; 4118 4119 /* Enable PMD link, MOD_ABS_FLT, and 1G link alarm */ 4120 4121 u16 mod_abs; 4122 rx_alarm_ctrl_val = (1<<2) | (1<<5) ; 4123 lasi_ctrl_val = 0x0004; 4124 4125 DP(NETIF_MSG_LINK, "Initializing BCM8727\n"); 4126 /* enable LASI */ 4127 bnx2x_cl45_write(bp, params->port, 4128 ext_phy_type, 4129 ext_phy_addr, 4130 MDIO_PMA_DEVAD, 4131 MDIO_PMA_REG_RX_ALARM_CTRL, 4132 rx_alarm_ctrl_val); 4133 4134 bnx2x_cl45_write(bp, params->port, 4135 ext_phy_type, 4136 ext_phy_addr, 4137 MDIO_PMA_DEVAD, 4138 MDIO_PMA_REG_LASI_CTRL, 4139 lasi_ctrl_val); 4140 4141 /* Initially configure MOD_ABS to interrupt when 4142 module is presence( bit 8) */ 4143 bnx2x_cl45_read(bp, params->port, 4144 ext_phy_type, 4145 ext_phy_addr, 4146 MDIO_PMA_DEVAD, 4147 MDIO_PMA_REG_PHY_IDENTIFIER, &mod_abs); 4148 /* Set EDC off by setting OPTXLOS signal input to low 4149 (bit 9). 4150 When the EDC is off it locks onto a reference clock and 4151 avoids becoming 'lost'.*/ 4152 mod_abs &= ~((1<<8) | (1<<9)); 4153 bnx2x_cl45_write(bp, params->port, 4154 ext_phy_type, 4155 ext_phy_addr, 4156 MDIO_PMA_DEVAD, 4157 MDIO_PMA_REG_PHY_IDENTIFIER, mod_abs); 4158 4159 /* Make MOD_ABS give interrupt on change */ 4160 bnx2x_cl45_read(bp, params->port, 4161 ext_phy_type, 4162 ext_phy_addr, 4163 MDIO_PMA_DEVAD, 4164 MDIO_PMA_REG_8727_PCS_OPT_CTRL, 4165 &val); 4166 val |= (1<<12); 4167 bnx2x_cl45_write(bp, params->port, 4168 ext_phy_type, 4169 ext_phy_addr, 4170 MDIO_PMA_DEVAD, 4171 MDIO_PMA_REG_8727_PCS_OPT_CTRL, 4172 val); 4173 4174 /* Set 8727 GPIOs to input to allow reading from the 4175 8727 GPIO0 status which reflect SFP+ module 4176 over-current */ 4177 4178 bnx2x_cl45_read(bp, params->port, 4179 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 4180 ext_phy_addr, 4181 MDIO_PMA_DEVAD, 4182 MDIO_PMA_REG_8727_PCS_OPT_CTRL, 4183 &val); 4184 val &= 0xff8f; /* Reset bits 4-6 */ 4185 bnx2x_cl45_write(bp, params->port, 4186 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 4187 ext_phy_addr, 4188 MDIO_PMA_DEVAD, 4189 MDIO_PMA_REG_8727_PCS_OPT_CTRL, 4190 val); 4191 4192 bnx2x_8727_power_module(bp, params, ext_phy_addr, 1); 4193 bnx2x_bcm8073_set_xaui_low_power_mode(params); 4194 4195 bnx2x_cl45_read(bp, params->port, 4196 ext_phy_type, 4197 ext_phy_addr, 4198 MDIO_PMA_DEVAD, 4199 MDIO_PMA_REG_M8051_MSGOUT_REG, 4200 &tmp1); 4201 4202 bnx2x_cl45_read(bp, params->port, 4203 ext_phy_type, 4204 ext_phy_addr, 4205 MDIO_PMA_DEVAD, 4206 MDIO_PMA_REG_RX_ALARM, &tmp1); 4207 4208 /* Set option 1G speed */ 4209 if (params->req_line_speed == SPEED_1000) { 4210 4211 DP(NETIF_MSG_LINK, "Setting 1G force\n"); 4212 bnx2x_cl45_write(bp, params->port, 4213 ext_phy_type, 4214 ext_phy_addr, 4215 MDIO_PMA_DEVAD, 4216 MDIO_PMA_REG_CTRL, 0x40); 4217 bnx2x_cl45_write(bp, params->port, 4218 ext_phy_type, 4219 ext_phy_addr, 4220 MDIO_PMA_DEVAD, 4221 MDIO_PMA_REG_10G_CTRL2, 0xD); 4222 bnx2x_cl45_read(bp, params->port, 4223 ext_phy_type, 4224 ext_phy_addr, 4225 MDIO_PMA_DEVAD, 4226 MDIO_PMA_REG_10G_CTRL2, &tmp1); 4227 DP(NETIF_MSG_LINK, "1.7 = 0x%x\n", tmp1); 4228 4229 } else if ((params->req_line_speed == 4230 SPEED_AUTO_NEG) && 4231 ((params->speed_cap_mask & 4232 PORT_HW_CFG_SPEED_CAPABILITY_D0_1G))) { 4233 4234 DP(NETIF_MSG_LINK, "Setting 1G clause37\n"); 4235 bnx2x_cl45_write(bp, params->port, ext_phy_type, 4236 ext_phy_addr, MDIO_AN_DEVAD, 4237 MDIO_PMA_REG_8727_MISC_CTRL, 0); 4238 bnx2x_cl45_write(bp, params->port, ext_phy_type, 4239 ext_phy_addr, MDIO_AN_DEVAD, 4240 MDIO_AN_REG_CL37_AN, 0x1300); 4241 } else { 4242 /* Since the 8727 has only single reset pin, 4243 need to set the 10G registers although it is 4244 default */ 4245 bnx2x_cl45_write(bp, params->port, ext_phy_type, 4246 ext_phy_addr, MDIO_AN_DEVAD, 4247 MDIO_AN_REG_CTRL, 0x0020); 4248 bnx2x_cl45_write(bp, params->port, ext_phy_type, 4249 ext_phy_addr, MDIO_AN_DEVAD, 4250 0x7, 0x0100); 4251 bnx2x_cl45_write(bp, params->port, ext_phy_type, 4252 ext_phy_addr, MDIO_PMA_DEVAD, 4253 MDIO_PMA_REG_CTRL, 0x2040); 4254 bnx2x_cl45_write(bp, params->port, ext_phy_type, 4255 ext_phy_addr, MDIO_PMA_DEVAD, 4256 MDIO_PMA_REG_10G_CTRL2, 0x0008); 4257 } 4258 4259 /* Set 2-wire transfer rate of SFP+ module EEPROM 4260 * to 100Khz since some DACs(direct attached cables) do 4261 * not work at 400Khz. 4262 */ 4263 bnx2x_cl45_write(bp, params->port, 4264 ext_phy_type, 4265 ext_phy_addr, 4266 MDIO_PMA_DEVAD, 4267 MDIO_PMA_REG_8727_TWO_WIRE_SLAVE_ADDR, 4268 0xa001); 4269 4270 /* Set TX PreEmphasis if needed */ 4271 if ((params->feature_config_flags & 4272 FEATURE_CONFIG_OVERRIDE_PREEMPHASIS_ENABLED)) { 4273 DP(NETIF_MSG_LINK, "Setting TX_CTRL1 0x%x," 4274 "TX_CTRL2 0x%x\n", 4275 params->xgxs_config_tx[0], 4276 params->xgxs_config_tx[1]); 4277 bnx2x_cl45_write(bp, params->port, 4278 ext_phy_type, 4279 ext_phy_addr, 4280 MDIO_PMA_DEVAD, 4281 MDIO_PMA_REG_8727_TX_CTRL1, 4282 params->xgxs_config_tx[0]); 4283 4284 bnx2x_cl45_write(bp, params->port, 4285 ext_phy_type, 4286 ext_phy_addr, 4287 MDIO_PMA_DEVAD, 4288 MDIO_PMA_REG_8727_TX_CTRL2, 4289 params->xgxs_config_tx[1]); 4290 } 4291 4292 break; 4293 } 4294 4295 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_SFX7101: 4296 { 4297 u16 fw_ver1, fw_ver2; 4298 DP(NETIF_MSG_LINK, 4299 "Setting the SFX7101 LASI indication\n"); 4300 4301 bnx2x_cl45_write(bp, params->port, 4302 ext_phy_type, 4303 ext_phy_addr, 4304 MDIO_PMA_DEVAD, 4305 MDIO_PMA_REG_LASI_CTRL, 0x1); 4306 DP(NETIF_MSG_LINK, 4307 "Setting the SFX7101 LED to blink on traffic\n"); 4308 bnx2x_cl45_write(bp, params->port, 4309 ext_phy_type, 4310 ext_phy_addr, 4311 MDIO_PMA_DEVAD, 4312 MDIO_PMA_REG_7107_LED_CNTL, (1<<3)); 4313 4314 bnx2x_ext_phy_set_pause(params, vars); 4315 /* Restart autoneg */ 4316 bnx2x_cl45_read(bp, params->port, 4317 ext_phy_type, 4318 ext_phy_addr, 4319 MDIO_AN_DEVAD, 4320 MDIO_AN_REG_CTRL, &val); 4321 val |= 0x200; 4322 bnx2x_cl45_write(bp, params->port, 4323 ext_phy_type, 4324 ext_phy_addr, 4325 MDIO_AN_DEVAD, 4326 MDIO_AN_REG_CTRL, val); 4327 4328 /* Save spirom version */ 4329 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4330 ext_phy_addr, MDIO_PMA_DEVAD, 4331 MDIO_PMA_REG_7101_VER1, &fw_ver1); 4332 4333 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4334 ext_phy_addr, MDIO_PMA_DEVAD, 4335 MDIO_PMA_REG_7101_VER2, &fw_ver2); 4336 4337 bnx2x_save_spirom_version(params->bp, params->port, 4338 params->shmem_base, 4339 (u32)(fw_ver1<<16 | fw_ver2)); 4340 break; 4341 } 4342 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481: 4343 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM84823: 4344 /* This phy uses the NIG latch mechanism since link 4345 indication arrives through its LED4 and not via 4346 its LASI signal, so we get steady signal 4347 instead of clear on read */ 4348 bnx2x_bits_en(bp, NIG_REG_LATCH_BC_0 + params->port*4, 4349 1 << NIG_LATCH_BC_ENABLE_MI_INT); 4350 4351 bnx2x_cl45_write(bp, params->port, 4352 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 4353 ext_phy_addr, 4354 MDIO_PMA_DEVAD, 4355 MDIO_PMA_REG_CTRL, 0x0000); 4356 4357 bnx2x_8481_set_led4(params, ext_phy_type, ext_phy_addr); 4358 if (params->req_line_speed == SPEED_AUTO_NEG) { 4359 4360 u16 autoneg_val, an_1000_val, an_10_100_val; 4361 /* set 1000 speed advertisement */ 4362 bnx2x_cl45_read(bp, params->port, 4363 ext_phy_type, 4364 ext_phy_addr, 4365 MDIO_AN_DEVAD, 4366 MDIO_AN_REG_8481_1000T_CTRL, 4367 &an_1000_val); 4368 4369 if (params->speed_cap_mask & 4370 PORT_HW_CFG_SPEED_CAPABILITY_D0_1G) { 4371 an_1000_val |= (1<<8); 4372 if (params->req_duplex == DUPLEX_FULL) 4373 an_1000_val |= (1<<9); 4374 DP(NETIF_MSG_LINK, "Advertising 1G\n"); 4375 } else 4376 an_1000_val &= ~((1<<8) | (1<<9)); 4377 4378 bnx2x_cl45_write(bp, params->port, 4379 ext_phy_type, 4380 ext_phy_addr, 4381 MDIO_AN_DEVAD, 4382 MDIO_AN_REG_8481_1000T_CTRL, 4383 an_1000_val); 4384 4385 /* set 100 speed advertisement */ 4386 bnx2x_cl45_read(bp, params->port, 4387 ext_phy_type, 4388 ext_phy_addr, 4389 MDIO_AN_DEVAD, 4390 MDIO_AN_REG_8481_LEGACY_AN_ADV, 4391 &an_10_100_val); 4392 4393 if (params->speed_cap_mask & 4394 (PORT_HW_CFG_SPEED_CAPABILITY_D0_100M_FULL | 4395 PORT_HW_CFG_SPEED_CAPABILITY_D0_100M_HALF)) { 4396 an_10_100_val |= (1<<7); 4397 if (params->req_duplex == DUPLEX_FULL) 4398 an_10_100_val |= (1<<8); 4399 DP(NETIF_MSG_LINK, 4400 "Advertising 100M\n"); 4401 } else 4402 an_10_100_val &= ~((1<<7) | (1<<8)); 4403 4404 /* set 10 speed advertisement */ 4405 if (params->speed_cap_mask & 4406 (PORT_HW_CFG_SPEED_CAPABILITY_D0_10M_FULL | 4407 PORT_HW_CFG_SPEED_CAPABILITY_D0_10M_HALF)) { 4408 an_10_100_val |= (1<<5); 4409 if (params->req_duplex == DUPLEX_FULL) 4410 an_10_100_val |= (1<<6); 4411 DP(NETIF_MSG_LINK, "Advertising 10M\n"); 4412 } 4413 else 4414 an_10_100_val &= ~((1<<5) | (1<<6)); 4415 4416 bnx2x_cl45_write(bp, params->port, 4417 ext_phy_type, 4418 ext_phy_addr, 4419 MDIO_AN_DEVAD, 4420 MDIO_AN_REG_8481_LEGACY_AN_ADV, 4421 an_10_100_val); 4422 4423 bnx2x_cl45_read(bp, params->port, 4424 ext_phy_type, 4425 ext_phy_addr, 4426 MDIO_AN_DEVAD, 4427 MDIO_AN_REG_8481_LEGACY_MII_CTRL, 4428 &autoneg_val); 4429 4430 /* Disable forced speed */ 4431 autoneg_val &= ~(1<<6|1<<13); 4432 4433 /* Enable autoneg and restart autoneg 4434 for legacy speeds */ 4435 autoneg_val |= (1<<9|1<<12); 4436 4437 if (params->req_duplex == DUPLEX_FULL) 4438 autoneg_val |= (1<<8); 4439 else 4440 autoneg_val &= ~(1<<8); 4441 4442 bnx2x_cl45_write(bp, params->port, 4443 ext_phy_type, 4444 ext_phy_addr, 4445 MDIO_AN_DEVAD, 4446 MDIO_AN_REG_8481_LEGACY_MII_CTRL, 4447 autoneg_val); 4448 4449 if (params->speed_cap_mask & 4450 PORT_HW_CFG_SPEED_CAPABILITY_D0_10G) { 4451 DP(NETIF_MSG_LINK, "Advertising 10G\n"); 4452 /* Restart autoneg for 10G*/ 4453 4454 bnx2x_cl45_write(bp, params->port, 4455 ext_phy_type, 4456 ext_phy_addr, 4457 MDIO_AN_DEVAD, 4458 MDIO_AN_REG_CTRL, 0x3200); 4459 } 4460 } else { 4461 /* Force speed */ 4462 u16 autoneg_ctrl, pma_ctrl; 4463 bnx2x_cl45_read(bp, params->port, 4464 ext_phy_type, 4465 ext_phy_addr, 4466 MDIO_AN_DEVAD, 4467 MDIO_AN_REG_8481_LEGACY_MII_CTRL, 4468 &autoneg_ctrl); 4469 4470 /* Disable autoneg */ 4471 autoneg_ctrl &= ~(1<<12); 4472 4473 /* Set 1000 force */ 4474 switch (params->req_line_speed) { 4475 case SPEED_10000: 4476 DP(NETIF_MSG_LINK, 4477 "Unable to set 10G force !\n"); 4478 break; 4479 case SPEED_1000: 4480 bnx2x_cl45_read(bp, params->port, 4481 ext_phy_type, 4482 ext_phy_addr, 4483 MDIO_PMA_DEVAD, 4484 MDIO_PMA_REG_CTRL, 4485 &pma_ctrl); 4486 autoneg_ctrl &= ~(1<<13); 4487 autoneg_ctrl |= (1<<6); 4488 pma_ctrl &= ~(1<<13); 4489 pma_ctrl |= (1<<6); 4490 DP(NETIF_MSG_LINK, 4491 "Setting 1000M force\n"); 4492 bnx2x_cl45_write(bp, params->port, 4493 ext_phy_type, 4494 ext_phy_addr, 4495 MDIO_PMA_DEVAD, 4496 MDIO_PMA_REG_CTRL, 4497 pma_ctrl); 4498 break; 4499 case SPEED_100: 4500 autoneg_ctrl |= (1<<13); 4501 autoneg_ctrl &= ~(1<<6); 4502 DP(NETIF_MSG_LINK, 4503 "Setting 100M force\n"); 4504 break; 4505 case SPEED_10: 4506 autoneg_ctrl &= ~(1<<13); 4507 autoneg_ctrl &= ~(1<<6); 4508 DP(NETIF_MSG_LINK, 4509 "Setting 10M force\n"); 4510 break; 4511 } 4512 4513 /* Duplex mode */ 4514 if (params->req_duplex == DUPLEX_FULL) { 4515 autoneg_ctrl |= (1<<8); 4516 DP(NETIF_MSG_LINK, 4517 "Setting full duplex\n"); 4518 } else 4519 autoneg_ctrl &= ~(1<<8); 4520 4521 /* Update autoneg ctrl and pma ctrl */ 4522 bnx2x_cl45_write(bp, params->port, 4523 ext_phy_type, 4524 ext_phy_addr, 4525 MDIO_AN_DEVAD, 4526 MDIO_AN_REG_8481_LEGACY_MII_CTRL, 4527 autoneg_ctrl); 4528 } 4529 4530 /* Save spirom version */ 4531 bnx2x_save_8481_spirom_version(bp, params->port, 4532 ext_phy_addr, 4533 params->shmem_base); 4534 break; 4535 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_FAILURE: 4536 DP(NETIF_MSG_LINK, 4537 "XGXS PHY Failure detected 0x%x\n", 4538 params->ext_phy_config); 4539 rc = -EINVAL; 4540 break; 4541 default: 4542 DP(NETIF_MSG_LINK, "BAD XGXS ext_phy_config 0x%x\n", 4543 params->ext_phy_config); 4544 rc = -EINVAL; 4545 break; 4546 } 4547 4548 } else { /* SerDes */ 4549 4550 ext_phy_type = SERDES_EXT_PHY_TYPE(params->ext_phy_config); 4551 switch (ext_phy_type) { 4552 case PORT_HW_CFG_SERDES_EXT_PHY_TYPE_DIRECT: 4553 DP(NETIF_MSG_LINK, "SerDes Direct\n"); 4554 break; 4555 4556 case PORT_HW_CFG_SERDES_EXT_PHY_TYPE_BCM5482: 4557 DP(NETIF_MSG_LINK, "SerDes 5482\n"); 4558 break; 4559 4560 default: 4561 DP(NETIF_MSG_LINK, "BAD SerDes ext_phy_config 0x%x\n", 4562 params->ext_phy_config); 4563 break; 4564 } 4565 } 4566 return rc; 4567} 4568 4569static void bnx2x_8727_handle_mod_abs(struct link_params *params) 4570{ 4571 struct bnx2x *bp = params->bp; 4572 u16 mod_abs, rx_alarm_status; 4573 u8 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 4574 u32 val = REG_RD(bp, params->shmem_base + 4575 offsetof(struct shmem_region, dev_info. 4576 port_feature_config[params->port]. 4577 config)); 4578 bnx2x_cl45_read(bp, params->port, 4579 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 4580 ext_phy_addr, 4581 MDIO_PMA_DEVAD, 4582 MDIO_PMA_REG_PHY_IDENTIFIER, &mod_abs); 4583 if (mod_abs & (1<<8)) { 4584 4585 /* Module is absent */ 4586 DP(NETIF_MSG_LINK, "MOD_ABS indication " 4587 "show module is absent\n"); 4588 4589 /* 1. Set mod_abs to detect next module 4590 presence event 4591 2. Set EDC off by setting OPTXLOS signal input to low 4592 (bit 9). 4593 When the EDC is off it locks onto a reference clock and 4594 avoids becoming 'lost'.*/ 4595 mod_abs &= ~((1<<8)|(1<<9)); 4596 bnx2x_cl45_write(bp, params->port, 4597 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 4598 ext_phy_addr, 4599 MDIO_PMA_DEVAD, 4600 MDIO_PMA_REG_PHY_IDENTIFIER, mod_abs); 4601 4602 /* Clear RX alarm since it stays up as long as 4603 the mod_abs wasn't changed */ 4604 bnx2x_cl45_read(bp, params->port, 4605 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 4606 ext_phy_addr, 4607 MDIO_PMA_DEVAD, 4608 MDIO_PMA_REG_RX_ALARM, &rx_alarm_status); 4609 4610 } else { 4611 /* Module is present */ 4612 DP(NETIF_MSG_LINK, "MOD_ABS indication " 4613 "show module is present\n"); 4614 /* First thing, disable transmitter, 4615 and if the module is ok, the 4616 module_detection will enable it*/ 4617 4618 /* 1. Set mod_abs to detect next module 4619 absent event ( bit 8) 4620 2. Restore the default polarity of the OPRXLOS signal and 4621 this signal will then correctly indicate the presence or 4622 absence of the Rx signal. (bit 9) */ 4623 mod_abs |= ((1<<8)|(1<<9)); 4624 bnx2x_cl45_write(bp, params->port, 4625 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 4626 ext_phy_addr, 4627 MDIO_PMA_DEVAD, 4628 MDIO_PMA_REG_PHY_IDENTIFIER, mod_abs); 4629 4630 /* Clear RX alarm since it stays up as long as 4631 the mod_abs wasn't changed. This is need to be done 4632 before calling the module detection, otherwise it will clear 4633 the link update alarm */ 4634 bnx2x_cl45_read(bp, params->port, 4635 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 4636 ext_phy_addr, 4637 MDIO_PMA_DEVAD, 4638 MDIO_PMA_REG_RX_ALARM, &rx_alarm_status); 4639 4640 4641 if ((val & PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_MASK) == 4642 PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_DISABLE_TX_LASER) 4643 bnx2x_sfp_set_transmitter(bp, params->port, 4644 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 4645 ext_phy_addr, 0); 4646 4647 if (bnx2x_wait_for_sfp_module_initialized(params) 4648 == 0) 4649 bnx2x_sfp_module_detection(params); 4650 else 4651 DP(NETIF_MSG_LINK, "SFP+ module is not initialized\n"); 4652 } 4653 4654 DP(NETIF_MSG_LINK, "8727 RX_ALARM_STATUS 0x%x\n", 4655 rx_alarm_status); 4656 /* No need to check link status in case of 4657 module plugged in/out */ 4658} 4659 4660 4661static u8 bnx2x_ext_phy_is_link_up(struct link_params *params, 4662 struct link_vars *vars, 4663 u8 is_mi_int) 4664{ 4665 struct bnx2x *bp = params->bp; 4666 u32 ext_phy_type; 4667 u8 ext_phy_addr; 4668 u16 val1 = 0, val2; 4669 u16 rx_sd, pcs_status; 4670 u8 ext_phy_link_up = 0; 4671 u8 port = params->port; 4672 4673 if (vars->phy_flags & PHY_XGXS_FLAG) { 4674 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 4675 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 4676 switch (ext_phy_type) { 4677 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT: 4678 DP(NETIF_MSG_LINK, "XGXS Direct\n"); 4679 ext_phy_link_up = 1; 4680 break; 4681 4682 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705: 4683 DP(NETIF_MSG_LINK, "XGXS 8705\n"); 4684 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4685 ext_phy_addr, 4686 MDIO_WIS_DEVAD, 4687 MDIO_WIS_REG_LASI_STATUS, &val1); 4688 DP(NETIF_MSG_LINK, "8705 LASI status 0x%x\n", val1); 4689 4690 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4691 ext_phy_addr, 4692 MDIO_WIS_DEVAD, 4693 MDIO_WIS_REG_LASI_STATUS, &val1); 4694 DP(NETIF_MSG_LINK, "8705 LASI status 0x%x\n", val1); 4695 4696 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4697 ext_phy_addr, 4698 MDIO_PMA_DEVAD, 4699 MDIO_PMA_REG_RX_SD, &rx_sd); 4700 4701 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4702 ext_phy_addr, 4703 1, 4704 0xc809, &val1); 4705 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4706 ext_phy_addr, 4707 1, 4708 0xc809, &val1); 4709 4710 DP(NETIF_MSG_LINK, "8705 1.c809 val=0x%x\n", val1); 4711 ext_phy_link_up = ((rx_sd & 0x1) && (val1 & (1<<9)) && 4712 ((val1 & (1<<8)) == 0)); 4713 if (ext_phy_link_up) 4714 vars->line_speed = SPEED_10000; 4715 break; 4716 4717 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706: 4718 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726: 4719 DP(NETIF_MSG_LINK, "XGXS 8706/8726\n"); 4720 /* Clear RX Alarm*/ 4721 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4722 ext_phy_addr, 4723 MDIO_PMA_DEVAD, MDIO_PMA_REG_RX_ALARM, 4724 &val2); 4725 /* clear LASI indication*/ 4726 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4727 ext_phy_addr, 4728 MDIO_PMA_DEVAD, MDIO_PMA_REG_LASI_STATUS, 4729 &val1); 4730 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4731 ext_phy_addr, 4732 MDIO_PMA_DEVAD, MDIO_PMA_REG_LASI_STATUS, 4733 &val2); 4734 DP(NETIF_MSG_LINK, "8706/8726 LASI status 0x%x-->" 4735 "0x%x\n", val1, val2); 4736 4737 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4738 ext_phy_addr, 4739 MDIO_PMA_DEVAD, MDIO_PMA_REG_RX_SD, 4740 &rx_sd); 4741 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4742 ext_phy_addr, 4743 MDIO_PCS_DEVAD, MDIO_PCS_REG_STATUS, 4744 &pcs_status); 4745 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4746 ext_phy_addr, 4747 MDIO_AN_DEVAD, MDIO_AN_REG_LINK_STATUS, 4748 &val2); 4749 bnx2x_cl45_read(bp, params->port, ext_phy_type, 4750 ext_phy_addr, 4751 MDIO_AN_DEVAD, MDIO_AN_REG_LINK_STATUS, 4752 &val2); 4753 4754 DP(NETIF_MSG_LINK, "8706/8726 rx_sd 0x%x" 4755 " pcs_status 0x%x 1Gbps link_status 0x%x\n", 4756 rx_sd, pcs_status, val2); 4757 /* link is up if both bit 0 of pmd_rx_sd and 4758 * bit 0 of pcs_status are set, or if the autoneg bit 4759 1 is set 4760 */ 4761 ext_phy_link_up = ((rx_sd & pcs_status & 0x1) || 4762 (val2 & (1<<1))); 4763 if (ext_phy_link_up) { 4764 if (ext_phy_type == 4765 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726) { 4766 /* If transmitter is disabled, 4767 ignore false link up indication */ 4768 bnx2x_cl45_read(bp, params->port, 4769 ext_phy_type, 4770 ext_phy_addr, 4771 MDIO_PMA_DEVAD, 4772 MDIO_PMA_REG_PHY_IDENTIFIER, 4773 &val1); 4774 if (val1 & (1<<15)) { 4775 DP(NETIF_MSG_LINK, "Tx is " 4776 "disabled\n"); 4777 ext_phy_link_up = 0; 4778 break; 4779 } 4780 } 4781 if (val2 & (1<<1)) 4782 vars->line_speed = SPEED_1000; 4783 else 4784 vars->line_speed = SPEED_10000; 4785 } 4786 break; 4787 4788 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727: 4789 { 4790 u16 link_status = 0; 4791 u16 rx_alarm_status; 4792 /* Check the LASI */ 4793 bnx2x_cl45_read(bp, params->port, 4794 ext_phy_type, 4795 ext_phy_addr, 4796 MDIO_PMA_DEVAD, 4797 MDIO_PMA_REG_RX_ALARM, &rx_alarm_status); 4798 4799 DP(NETIF_MSG_LINK, "8727 RX_ALARM_STATUS 0x%x\n", 4800 rx_alarm_status); 4801 4802 bnx2x_cl45_read(bp, params->port, 4803 ext_phy_type, 4804 ext_phy_addr, 4805 MDIO_PMA_DEVAD, 4806 MDIO_PMA_REG_LASI_STATUS, &val1); 4807 4808 DP(NETIF_MSG_LINK, 4809 "8727 LASI status 0x%x\n", 4810 val1); 4811 4812 /* Clear MSG-OUT */ 4813 bnx2x_cl45_read(bp, params->port, 4814 ext_phy_type, 4815 ext_phy_addr, 4816 MDIO_PMA_DEVAD, 4817 MDIO_PMA_REG_M8051_MSGOUT_REG, 4818 &val1); 4819 4820 /* 4821 * If a module is present and there is need to check 4822 * for over current 4823 */ 4824 if (!(params->feature_config_flags & 4825 FEATURE_CONFIG_BCM8727_NOC) && 4826 !(rx_alarm_status & (1<<5))) { 4827 /* Check over-current using 8727 GPIO0 input*/ 4828 bnx2x_cl45_read(bp, params->port, 4829 ext_phy_type, 4830 ext_phy_addr, 4831 MDIO_PMA_DEVAD, 4832 MDIO_PMA_REG_8727_GPIO_CTRL, 4833 &val1); 4834 4835 if ((val1 & (1<<8)) == 0) { 4836 DP(NETIF_MSG_LINK, "8727 Power fault" 4837 " has been detected on " 4838 "port %d\n", 4839 params->port); 4840 netdev_err(bp->dev, "Error: Power fault on Port %d has been detected and the power to that SFP+ module has been removed to prevent failure of the card. Please remove the SFP+ module and restart the system to clear this error.\n", 4841 params->port); 4842 /* 4843 * Disable all RX_ALARMs except for 4844 * mod_abs 4845 */ 4846 bnx2x_cl45_write(bp, params->port, 4847 ext_phy_type, 4848 ext_phy_addr, 4849 MDIO_PMA_DEVAD, 4850 MDIO_PMA_REG_RX_ALARM_CTRL, 4851 (1<<5)); 4852 4853 bnx2x_cl45_read(bp, params->port, 4854 ext_phy_type, 4855 ext_phy_addr, 4856 MDIO_PMA_DEVAD, 4857 MDIO_PMA_REG_PHY_IDENTIFIER, 4858 &val1); 4859 /* Wait for module_absent_event */ 4860 val1 |= (1<<8); 4861 bnx2x_cl45_write(bp, params->port, 4862 ext_phy_type, 4863 ext_phy_addr, 4864 MDIO_PMA_DEVAD, 4865 MDIO_PMA_REG_PHY_IDENTIFIER, 4866 val1); 4867 /* Clear RX alarm */ 4868 bnx2x_cl45_read(bp, params->port, 4869 ext_phy_type, 4870 ext_phy_addr, 4871 MDIO_PMA_DEVAD, 4872 MDIO_PMA_REG_RX_ALARM, 4873 &rx_alarm_status); 4874 break; 4875 } 4876 } /* Over current check */ 4877 4878 /* When module absent bit is set, check module */ 4879 if (rx_alarm_status & (1<<5)) { 4880 bnx2x_8727_handle_mod_abs(params); 4881 /* Enable all mod_abs and link detection bits */ 4882 bnx2x_cl45_write(bp, params->port, 4883 ext_phy_type, 4884 ext_phy_addr, 4885 MDIO_PMA_DEVAD, 4886 MDIO_PMA_REG_RX_ALARM_CTRL, 4887 ((1<<5) | (1<<2))); 4888 } 4889 4890 /* If transmitter is disabled, 4891 ignore false link up indication */ 4892 bnx2x_cl45_read(bp, params->port, 4893 ext_phy_type, 4894 ext_phy_addr, 4895 MDIO_PMA_DEVAD, 4896 MDIO_PMA_REG_PHY_IDENTIFIER, 4897 &val1); 4898 if (val1 & (1<<15)) { 4899 DP(NETIF_MSG_LINK, "Tx is disabled\n"); 4900 ext_phy_link_up = 0; 4901 break; 4902 } 4903 4904 bnx2x_cl45_read(bp, params->port, 4905 ext_phy_type, 4906 ext_phy_addr, 4907 MDIO_PMA_DEVAD, 4908 MDIO_PMA_REG_8073_SPEED_LINK_STATUS, 4909 &link_status); 4910 4911 /* Bits 0..2 --> speed detected, 4912 bits 13..15--> link is down */ 4913 if ((link_status & (1<<2)) && 4914 (!(link_status & (1<<15)))) { 4915 ext_phy_link_up = 1; 4916 vars->line_speed = SPEED_10000; 4917 } else if ((link_status & (1<<0)) && 4918 (!(link_status & (1<<13)))) { 4919 ext_phy_link_up = 1; 4920 vars->line_speed = SPEED_1000; 4921 DP(NETIF_MSG_LINK, 4922 "port %x: External link" 4923 " up in 1G\n", params->port); 4924 } else { 4925 ext_phy_link_up = 0; 4926 DP(NETIF_MSG_LINK, 4927 "port %x: External link" 4928 " is down\n", params->port); 4929 } 4930 break; 4931 } 4932 4933 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072: 4934 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073: 4935 { 4936 u16 link_status = 0; 4937 u16 an1000_status = 0; 4938 4939 if (ext_phy_type == 4940 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072) { 4941 bnx2x_cl45_read(bp, params->port, 4942 ext_phy_type, 4943 ext_phy_addr, 4944 MDIO_PCS_DEVAD, 4945 MDIO_PCS_REG_LASI_STATUS, &val1); 4946 bnx2x_cl45_read(bp, params->port, 4947 ext_phy_type, 4948 ext_phy_addr, 4949 MDIO_PCS_DEVAD, 4950 MDIO_PCS_REG_LASI_STATUS, &val2); 4951 DP(NETIF_MSG_LINK, 4952 "870x LASI status 0x%x->0x%x\n", 4953 val1, val2); 4954 } else { 4955 /* In 8073, port1 is directed through emac0 and 4956 * port0 is directed through emac1 4957 */ 4958 bnx2x_cl45_read(bp, params->port, 4959 ext_phy_type, 4960 ext_phy_addr, 4961 MDIO_PMA_DEVAD, 4962 MDIO_PMA_REG_LASI_STATUS, &val1); 4963 4964 DP(NETIF_MSG_LINK, 4965 "8703 LASI status 0x%x\n", 4966 val1); 4967 } 4968 4969 /* clear the interrupt LASI status register */ 4970 bnx2x_cl45_read(bp, params->port, 4971 ext_phy_type, 4972 ext_phy_addr, 4973 MDIO_PCS_DEVAD, 4974 MDIO_PCS_REG_STATUS, &val2); 4975 bnx2x_cl45_read(bp, params->port, 4976 ext_phy_type, 4977 ext_phy_addr, 4978 MDIO_PCS_DEVAD, 4979 MDIO_PCS_REG_STATUS, &val1); 4980 DP(NETIF_MSG_LINK, "807x PCS status 0x%x->0x%x\n", 4981 val2, val1); 4982 /* Clear MSG-OUT */ 4983 bnx2x_cl45_read(bp, params->port, 4984 ext_phy_type, 4985 ext_phy_addr, 4986 MDIO_PMA_DEVAD, 4987 MDIO_PMA_REG_M8051_MSGOUT_REG, 4988 &val1); 4989 4990 /* Check the LASI */ 4991 bnx2x_cl45_read(bp, params->port, 4992 ext_phy_type, 4993 ext_phy_addr, 4994 MDIO_PMA_DEVAD, 4995 MDIO_PMA_REG_RX_ALARM, &val2); 4996 4997 DP(NETIF_MSG_LINK, "KR 0x9003 0x%x\n", val2); 4998 4999 /* Check the link status */ 5000 bnx2x_cl45_read(bp, params->port, 5001 ext_phy_type, 5002 ext_phy_addr, 5003 MDIO_PCS_DEVAD, 5004 MDIO_PCS_REG_STATUS, &val2); 5005 DP(NETIF_MSG_LINK, "KR PCS status 0x%x\n", val2); 5006 5007 bnx2x_cl45_read(bp, params->port, 5008 ext_phy_type, 5009 ext_phy_addr, 5010 MDIO_PMA_DEVAD, 5011 MDIO_PMA_REG_STATUS, &val2); 5012 bnx2x_cl45_read(bp, params->port, 5013 ext_phy_type, 5014 ext_phy_addr, 5015 MDIO_PMA_DEVAD, 5016 MDIO_PMA_REG_STATUS, &val1); 5017 ext_phy_link_up = ((val1 & 4) == 4); 5018 DP(NETIF_MSG_LINK, "PMA_REG_STATUS=0x%x\n", val1); 5019 if (ext_phy_type == 5020 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073) { 5021 5022 if (ext_phy_link_up && 5023 ((params->req_line_speed != 5024 SPEED_10000))) { 5025 if (bnx2x_bcm8073_xaui_wa(params) 5026 != 0) { 5027 ext_phy_link_up = 0; 5028 break; 5029 } 5030 } 5031 bnx2x_cl45_read(bp, params->port, 5032 ext_phy_type, 5033 ext_phy_addr, 5034 MDIO_AN_DEVAD, 5035 MDIO_AN_REG_LINK_STATUS, 5036 &an1000_status); 5037 bnx2x_cl45_read(bp, params->port, 5038 ext_phy_type, 5039 ext_phy_addr, 5040 MDIO_AN_DEVAD, 5041 MDIO_AN_REG_LINK_STATUS, 5042 &an1000_status); 5043 5044 /* Check the link status on 1.1.2 */ 5045 bnx2x_cl45_read(bp, params->port, 5046 ext_phy_type, 5047 ext_phy_addr, 5048 MDIO_PMA_DEVAD, 5049 MDIO_PMA_REG_STATUS, &val2); 5050 bnx2x_cl45_read(bp, params->port, 5051 ext_phy_type, 5052 ext_phy_addr, 5053 MDIO_PMA_DEVAD, 5054 MDIO_PMA_REG_STATUS, &val1); 5055 DP(NETIF_MSG_LINK, "KR PMA status 0x%x->0x%x," 5056 "an_link_status=0x%x\n", 5057 val2, val1, an1000_status); 5058 5059 ext_phy_link_up = (((val1 & 4) == 4) || 5060 (an1000_status & (1<<1))); 5061 if (ext_phy_link_up && 5062 bnx2x_8073_is_snr_needed(params)) { 5063 /* The SNR will improve about 2dbby 5064 changing the BW and FEE main tap.*/ 5065 5066 /* The 1st write to change FFE main 5067 tap is set before restart AN */ 5068 /* Change PLL Bandwidth in EDC 5069 register */ 5070 bnx2x_cl45_write(bp, port, ext_phy_type, 5071 ext_phy_addr, 5072 MDIO_PMA_DEVAD, 5073 MDIO_PMA_REG_PLL_BANDWIDTH, 5074 0x26BC); 5075 5076 /* Change CDR Bandwidth in EDC 5077 register */ 5078 bnx2x_cl45_write(bp, port, ext_phy_type, 5079 ext_phy_addr, 5080 MDIO_PMA_DEVAD, 5081 MDIO_PMA_REG_CDR_BANDWIDTH, 5082 0x0333); 5083 } 5084 bnx2x_cl45_read(bp, params->port, 5085 ext_phy_type, 5086 ext_phy_addr, 5087 MDIO_PMA_DEVAD, 5088 MDIO_PMA_REG_8073_SPEED_LINK_STATUS, 5089 &link_status); 5090 5091 /* Bits 0..2 --> speed detected, 5092 bits 13..15--> link is down */ 5093 if ((link_status & (1<<2)) && 5094 (!(link_status & (1<<15)))) { 5095 ext_phy_link_up = 1; 5096 vars->line_speed = SPEED_10000; 5097 DP(NETIF_MSG_LINK, 5098 "port %x: External link" 5099 " up in 10G\n", params->port); 5100 } else if ((link_status & (1<<1)) && 5101 (!(link_status & (1<<14)))) { 5102 ext_phy_link_up = 1; 5103 vars->line_speed = SPEED_2500; 5104 DP(NETIF_MSG_LINK, 5105 "port %x: External link" 5106 " up in 2.5G\n", params->port); 5107 } else if ((link_status & (1<<0)) && 5108 (!(link_status & (1<<13)))) { 5109 ext_phy_link_up = 1; 5110 vars->line_speed = SPEED_1000; 5111 DP(NETIF_MSG_LINK, 5112 "port %x: External link" 5113 " up in 1G\n", params->port); 5114 } else { 5115 ext_phy_link_up = 0; 5116 DP(NETIF_MSG_LINK, 5117 "port %x: External link" 5118 " is down\n", params->port); 5119 } 5120 } else { 5121 /* See if 1G link is up for the 8072 */ 5122 bnx2x_cl45_read(bp, params->port, 5123 ext_phy_type, 5124 ext_phy_addr, 5125 MDIO_AN_DEVAD, 5126 MDIO_AN_REG_LINK_STATUS, 5127 &an1000_status); 5128 bnx2x_cl45_read(bp, params->port, 5129 ext_phy_type, 5130 ext_phy_addr, 5131 MDIO_AN_DEVAD, 5132 MDIO_AN_REG_LINK_STATUS, 5133 &an1000_status); 5134 if (an1000_status & (1<<1)) { 5135 ext_phy_link_up = 1; 5136 vars->line_speed = SPEED_1000; 5137 DP(NETIF_MSG_LINK, 5138 "port %x: External link" 5139 " up in 1G\n", params->port); 5140 } else if (ext_phy_link_up) { 5141 ext_phy_link_up = 1; 5142 vars->line_speed = SPEED_10000; 5143 DP(NETIF_MSG_LINK, 5144 "port %x: External link" 5145 " up in 10G\n", params->port); 5146 } 5147 } 5148 5149 5150 break; 5151 } 5152 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_SFX7101: 5153 bnx2x_cl45_read(bp, params->port, ext_phy_type, 5154 ext_phy_addr, 5155 MDIO_PMA_DEVAD, 5156 MDIO_PMA_REG_LASI_STATUS, &val2); 5157 bnx2x_cl45_read(bp, params->port, ext_phy_type, 5158 ext_phy_addr, 5159 MDIO_PMA_DEVAD, 5160 MDIO_PMA_REG_LASI_STATUS, &val1); 5161 DP(NETIF_MSG_LINK, 5162 "10G-base-T LASI status 0x%x->0x%x\n", 5163 val2, val1); 5164 bnx2x_cl45_read(bp, params->port, ext_phy_type, 5165 ext_phy_addr, 5166 MDIO_PMA_DEVAD, 5167 MDIO_PMA_REG_STATUS, &val2); 5168 bnx2x_cl45_read(bp, params->port, ext_phy_type, 5169 ext_phy_addr, 5170 MDIO_PMA_DEVAD, 5171 MDIO_PMA_REG_STATUS, &val1); 5172 DP(NETIF_MSG_LINK, 5173 "10G-base-T PMA status 0x%x->0x%x\n", 5174 val2, val1); 5175 ext_phy_link_up = ((val1 & 4) == 4); 5176 /* if link is up 5177 * print the AN outcome of the SFX7101 PHY 5178 */ 5179 if (ext_phy_link_up) { 5180 bnx2x_cl45_read(bp, params->port, 5181 ext_phy_type, 5182 ext_phy_addr, 5183 MDIO_AN_DEVAD, 5184 MDIO_AN_REG_MASTER_STATUS, 5185 &val2); 5186 vars->line_speed = SPEED_10000; 5187 DP(NETIF_MSG_LINK, 5188 "SFX7101 AN status 0x%x->Master=%x\n", 5189 val2, 5190 (val2 & (1<<14))); 5191 } 5192 break; 5193 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481: 5194 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM84823: 5195 /* Check 10G-BaseT link status */ 5196 /* Check PMD signal ok */ 5197 bnx2x_cl45_read(bp, params->port, ext_phy_type, 5198 ext_phy_addr, 5199 MDIO_AN_DEVAD, 5200 0xFFFA, 5201 &val1); 5202 bnx2x_cl45_read(bp, params->port, ext_phy_type, 5203 ext_phy_addr, 5204 MDIO_PMA_DEVAD, 5205 MDIO_PMA_REG_8481_PMD_SIGNAL, 5206 &val2); 5207 DP(NETIF_MSG_LINK, "PMD_SIGNAL 1.a811 = 0x%x\n", val2); 5208 5209 /* Check link 10G */ 5210 if (val2 & (1<<11)) { 5211 vars->line_speed = SPEED_10000; 5212 ext_phy_link_up = 1; 5213 bnx2x_8481_set_10G_led_mode(params, 5214 ext_phy_type, 5215 ext_phy_addr); 5216 } else { /* Check Legacy speed link */ 5217 u16 legacy_status, legacy_speed; 5218 5219 /* Enable expansion register 0x42 5220 (Operation mode status) */ 5221 bnx2x_cl45_write(bp, params->port, 5222 ext_phy_type, 5223 ext_phy_addr, 5224 MDIO_AN_DEVAD, 5225 MDIO_AN_REG_8481_EXPANSION_REG_ACCESS, 5226 0xf42); 5227 5228 /* Get legacy speed operation status */ 5229 bnx2x_cl45_read(bp, params->port, 5230 ext_phy_type, 5231 ext_phy_addr, 5232 MDIO_AN_DEVAD, 5233 MDIO_AN_REG_8481_EXPANSION_REG_RD_RW, 5234 &legacy_status); 5235 5236 DP(NETIF_MSG_LINK, "Legacy speed status" 5237 " = 0x%x\n", legacy_status); 5238 ext_phy_link_up = ((legacy_status & (1<<11)) 5239 == (1<<11)); 5240 if (ext_phy_link_up) { 5241 legacy_speed = (legacy_status & (3<<9)); 5242 if (legacy_speed == (0<<9)) 5243 vars->line_speed = SPEED_10; 5244 else if (legacy_speed == (1<<9)) 5245 vars->line_speed = 5246 SPEED_100; 5247 else if (legacy_speed == (2<<9)) 5248 vars->line_speed = 5249 SPEED_1000; 5250 else /* Should not happen */ 5251 vars->line_speed = 0; 5252 5253 if (legacy_status & (1<<8)) 5254 vars->duplex = DUPLEX_FULL; 5255 else 5256 vars->duplex = DUPLEX_HALF; 5257 5258 DP(NETIF_MSG_LINK, "Link is up " 5259 "in %dMbps, is_duplex_full" 5260 "= %d\n", 5261 vars->line_speed, 5262 (vars->duplex == DUPLEX_FULL)); 5263 bnx2x_8481_set_legacy_led_mode(params, 5264 ext_phy_type, 5265 ext_phy_addr); 5266 } 5267 } 5268 break; 5269 default: 5270 DP(NETIF_MSG_LINK, "BAD XGXS ext_phy_config 0x%x\n", 5271 params->ext_phy_config); 5272 ext_phy_link_up = 0; 5273 break; 5274 } 5275 /* Set SGMII mode for external phy */ 5276 if (ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT) { 5277 if (vars->line_speed < SPEED_1000) 5278 vars->phy_flags |= PHY_SGMII_FLAG; 5279 else 5280 vars->phy_flags &= ~PHY_SGMII_FLAG; 5281 } 5282 5283 } else { /* SerDes */ 5284 ext_phy_type = SERDES_EXT_PHY_TYPE(params->ext_phy_config); 5285 switch (ext_phy_type) { 5286 case PORT_HW_CFG_SERDES_EXT_PHY_TYPE_DIRECT: 5287 DP(NETIF_MSG_LINK, "SerDes Direct\n"); 5288 ext_phy_link_up = 1; 5289 break; 5290 5291 case PORT_HW_CFG_SERDES_EXT_PHY_TYPE_BCM5482: 5292 DP(NETIF_MSG_LINK, "SerDes 5482\n"); 5293 ext_phy_link_up = 1; 5294 break; 5295 5296 default: 5297 DP(NETIF_MSG_LINK, 5298 "BAD SerDes ext_phy_config 0x%x\n", 5299 params->ext_phy_config); 5300 ext_phy_link_up = 0; 5301 break; 5302 } 5303 } 5304 5305 return ext_phy_link_up; 5306} 5307 5308static void bnx2x_link_int_enable(struct link_params *params) 5309{ 5310 u8 port = params->port; 5311 u32 ext_phy_type; 5312 u32 mask; 5313 struct bnx2x *bp = params->bp; 5314 5315 /* setting the status to report on link up 5316 for either XGXS or SerDes */ 5317 5318 if (params->switch_cfg == SWITCH_CFG_10G) { 5319 mask = (NIG_MASK_XGXS0_LINK10G | 5320 NIG_MASK_XGXS0_LINK_STATUS); 5321 DP(NETIF_MSG_LINK, "enabled XGXS interrupt\n"); 5322 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 5323 if ((ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT) && 5324 (ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_FAILURE) && 5325 (ext_phy_type != 5326 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_NOT_CONN)) { 5327 mask |= NIG_MASK_MI_INT; 5328 DP(NETIF_MSG_LINK, "enabled external phy int\n"); 5329 } 5330 5331 } else { /* SerDes */ 5332 mask = NIG_MASK_SERDES0_LINK_STATUS; 5333 DP(NETIF_MSG_LINK, "enabled SerDes interrupt\n"); 5334 ext_phy_type = SERDES_EXT_PHY_TYPE(params->ext_phy_config); 5335 if ((ext_phy_type != 5336 PORT_HW_CFG_SERDES_EXT_PHY_TYPE_DIRECT) && 5337 (ext_phy_type != 5338 PORT_HW_CFG_SERDES_EXT_PHY_TYPE_NOT_CONN)) { 5339 mask |= NIG_MASK_MI_INT; 5340 DP(NETIF_MSG_LINK, "enabled external phy int\n"); 5341 } 5342 } 5343 bnx2x_bits_en(bp, 5344 NIG_REG_MASK_INTERRUPT_PORT0 + port*4, 5345 mask); 5346 5347 DP(NETIF_MSG_LINK, "port %x, is_xgxs %x, int_status 0x%x\n", port, 5348 (params->switch_cfg == SWITCH_CFG_10G), 5349 REG_RD(bp, NIG_REG_STATUS_INTERRUPT_PORT0 + port*4)); 5350 DP(NETIF_MSG_LINK, " int_mask 0x%x, MI_INT %x, SERDES_LINK %x\n", 5351 REG_RD(bp, NIG_REG_MASK_INTERRUPT_PORT0 + port*4), 5352 REG_RD(bp, NIG_REG_EMAC0_STATUS_MISC_MI_INT + port*0x18), 5353 REG_RD(bp, NIG_REG_SERDES0_STATUS_LINK_STATUS+port*0x3c)); 5354 DP(NETIF_MSG_LINK, " 10G %x, XGXS_LINK %x\n", 5355 REG_RD(bp, NIG_REG_XGXS0_STATUS_LINK10G + port*0x68), 5356 REG_RD(bp, NIG_REG_XGXS0_STATUS_LINK_STATUS + port*0x68)); 5357} 5358 5359static void bnx2x_8481_rearm_latch_signal(struct bnx2x *bp, u8 port, 5360 u8 is_mi_int) 5361{ 5362 u32 latch_status = 0, is_mi_int_status; 5363 /* Disable the MI INT ( external phy int ) 5364 * by writing 1 to the status register. Link down indication 5365 * is high-active-signal, so in this case we need to write the 5366 * status to clear the XOR 5367 */ 5368 /* Read Latched signals */ 5369 latch_status = REG_RD(bp, 5370 NIG_REG_LATCH_STATUS_0 + port*8); 5371 is_mi_int_status = REG_RD(bp, 5372 NIG_REG_STATUS_INTERRUPT_PORT0 + port*4); 5373 DP(NETIF_MSG_LINK, "original_signal = 0x%x, nig_status = 0x%x," 5374 "latch_status = 0x%x\n", 5375 is_mi_int, is_mi_int_status, latch_status); 5376 /* Handle only those with latched-signal=up.*/ 5377 if (latch_status & 1) { 5378 /* For all latched-signal=up,Write original_signal to status */ 5379 if (is_mi_int) 5380 bnx2x_bits_en(bp, 5381 NIG_REG_STATUS_INTERRUPT_PORT0 5382 + port*4, 5383 NIG_STATUS_EMAC0_MI_INT); 5384 else 5385 bnx2x_bits_dis(bp, 5386 NIG_REG_STATUS_INTERRUPT_PORT0 5387 + port*4, 5388 NIG_STATUS_EMAC0_MI_INT); 5389 /* For all latched-signal=up : Re-Arm Latch signals */ 5390 REG_WR(bp, NIG_REG_LATCH_STATUS_0 + port*8, 5391 (latch_status & 0xfffe) | (latch_status & 1)); 5392 } 5393} 5394/* 5395 * link management 5396 */ 5397static void bnx2x_link_int_ack(struct link_params *params, 5398 struct link_vars *vars, u8 is_10g, 5399 u8 is_mi_int) 5400{ 5401 struct bnx2x *bp = params->bp; 5402 u8 port = params->port; 5403 5404 /* first reset all status 5405 * we assume only one line will be change at a time */ 5406 bnx2x_bits_dis(bp, NIG_REG_STATUS_INTERRUPT_PORT0 + port*4, 5407 (NIG_STATUS_XGXS0_LINK10G | 5408 NIG_STATUS_XGXS0_LINK_STATUS | 5409 NIG_STATUS_SERDES0_LINK_STATUS)); 5410 if ((XGXS_EXT_PHY_TYPE(params->ext_phy_config) 5411 == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481) || 5412 (XGXS_EXT_PHY_TYPE(params->ext_phy_config) 5413 == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM84823)) { 5414 bnx2x_8481_rearm_latch_signal(bp, port, is_mi_int); 5415 } 5416 if (vars->phy_link_up) { 5417 if (is_10g) { 5418 /* Disable the 10G link interrupt 5419 * by writing 1 to the status register 5420 */ 5421 DP(NETIF_MSG_LINK, "10G XGXS phy link up\n"); 5422 bnx2x_bits_en(bp, 5423 NIG_REG_STATUS_INTERRUPT_PORT0 + port*4, 5424 NIG_STATUS_XGXS0_LINK10G); 5425 5426 } else if (params->switch_cfg == SWITCH_CFG_10G) { 5427 /* Disable the link interrupt 5428 * by writing 1 to the relevant lane 5429 * in the status register 5430 */ 5431 u32 ser_lane = ((params->lane_config & 5432 PORT_HW_CFG_LANE_SWAP_CFG_MASTER_MASK) >> 5433 PORT_HW_CFG_LANE_SWAP_CFG_MASTER_SHIFT); 5434 5435 DP(NETIF_MSG_LINK, "%d speed XGXS phy link up\n", 5436 vars->line_speed); 5437 bnx2x_bits_en(bp, 5438 NIG_REG_STATUS_INTERRUPT_PORT0 + port*4, 5439 ((1 << ser_lane) << 5440 NIG_STATUS_XGXS0_LINK_STATUS_SIZE)); 5441 5442 } else { /* SerDes */ 5443 DP(NETIF_MSG_LINK, "SerDes phy link up\n"); 5444 /* Disable the link interrupt 5445 * by writing 1 to the status register 5446 */ 5447 bnx2x_bits_en(bp, 5448 NIG_REG_STATUS_INTERRUPT_PORT0 + port*4, 5449 NIG_STATUS_SERDES0_LINK_STATUS); 5450 } 5451 5452 } else { /* link_down */ 5453 } 5454} 5455 5456static u8 bnx2x_format_ver(u32 num, u8 *str, u16 len) 5457{ 5458 u8 *str_ptr = str; 5459 u32 mask = 0xf0000000; 5460 u8 shift = 8*4; 5461 u8 digit; 5462 if (len < 10) { 5463 /* Need more than 10chars for this format */ 5464 *str_ptr = '\0'; 5465 return -EINVAL; 5466 } 5467 while (shift > 0) { 5468 5469 shift -= 4; 5470 digit = ((num & mask) >> shift); 5471 if (digit < 0xa) 5472 *str_ptr = digit + '0'; 5473 else 5474 *str_ptr = digit - 0xa + 'a'; 5475 str_ptr++; 5476 mask = mask >> 4; 5477 if (shift == 4*4) { 5478 *str_ptr = ':'; 5479 str_ptr++; 5480 } 5481 } 5482 *str_ptr = '\0'; 5483 return 0; 5484} 5485 5486u8 bnx2x_get_ext_phy_fw_version(struct link_params *params, u8 driver_loaded, 5487 u8 *version, u16 len) 5488{ 5489 struct bnx2x *bp; 5490 u32 ext_phy_type = 0; 5491 u32 spirom_ver = 0; 5492 u8 status; 5493 5494 if (version == NULL || params == NULL) 5495 return -EINVAL; 5496 bp = params->bp; 5497 5498 spirom_ver = REG_RD(bp, params->shmem_base + 5499 offsetof(struct shmem_region, 5500 port_mb[params->port].ext_phy_fw_version)); 5501 5502 status = 0; 5503 /* reset the returned value to zero */ 5504 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 5505 switch (ext_phy_type) { 5506 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_SFX7101: 5507 5508 if (len < 5) 5509 return -EINVAL; 5510 5511 version[0] = (spirom_ver & 0xFF); 5512 version[1] = (spirom_ver & 0xFF00) >> 8; 5513 version[2] = (spirom_ver & 0xFF0000) >> 16; 5514 version[3] = (spirom_ver & 0xFF000000) >> 24; 5515 version[4] = '\0'; 5516 5517 break; 5518 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072: 5519 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073: 5520 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727: 5521 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706: 5522 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726: 5523 status = bnx2x_format_ver(spirom_ver, version, len); 5524 break; 5525 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481: 5526 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM84823: 5527 spirom_ver = ((spirom_ver & 0xF80) >> 7) << 16 | 5528 (spirom_ver & 0x7F); 5529 status = bnx2x_format_ver(spirom_ver, version, len); 5530 break; 5531 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT: 5532 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705: 5533 version[0] = '\0'; 5534 break; 5535 5536 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_FAILURE: 5537 DP(NETIF_MSG_LINK, "bnx2x_get_ext_phy_fw_version:" 5538 " type is FAILURE!\n"); 5539 status = -EINVAL; 5540 break; 5541 5542 default: 5543 break; 5544 } 5545 return status; 5546} 5547 5548static void bnx2x_set_xgxs_loopback(struct link_params *params, 5549 struct link_vars *vars, 5550 u8 is_10g) 5551{ 5552 u8 port = params->port; 5553 struct bnx2x *bp = params->bp; 5554 5555 if (is_10g) { 5556 u32 md_devad; 5557 5558 DP(NETIF_MSG_LINK, "XGXS 10G loopback enable\n"); 5559 5560 /* change the uni_phy_addr in the nig */ 5561 md_devad = REG_RD(bp, (NIG_REG_XGXS0_CTRL_MD_DEVAD + 5562 port*0x18)); 5563 5564 REG_WR(bp, NIG_REG_XGXS0_CTRL_MD_DEVAD + port*0x18, 0x5); 5565 5566 bnx2x_cl45_write(bp, port, 0, 5567 params->phy_addr, 5568 5, 5569 (MDIO_REG_BANK_AER_BLOCK + 5570 (MDIO_AER_BLOCK_AER_REG & 0xf)), 5571 0x2800); 5572 5573 bnx2x_cl45_write(bp, port, 0, 5574 params->phy_addr, 5575 5, 5576 (MDIO_REG_BANK_CL73_IEEEB0 + 5577 (MDIO_CL73_IEEEB0_CL73_AN_CONTROL & 0xf)), 5578 0x6041); 5579 msleep(200); 5580 /* set aer mmd back */ 5581 bnx2x_set_aer_mmd(params, vars); 5582 5583 /* and md_devad */ 5584 REG_WR(bp, NIG_REG_XGXS0_CTRL_MD_DEVAD + port*0x18, 5585 md_devad); 5586 5587 } else { 5588 u16 mii_control; 5589 5590 DP(NETIF_MSG_LINK, "XGXS 1G loopback enable\n"); 5591 5592 CL45_RD_OVER_CL22(bp, port, 5593 params->phy_addr, 5594 MDIO_REG_BANK_COMBO_IEEE0, 5595 MDIO_COMBO_IEEE0_MII_CONTROL, 5596 &mii_control); 5597 5598 CL45_WR_OVER_CL22(bp, port, 5599 params->phy_addr, 5600 MDIO_REG_BANK_COMBO_IEEE0, 5601 MDIO_COMBO_IEEE0_MII_CONTROL, 5602 (mii_control | 5603 MDIO_COMBO_IEEO_MII_CONTROL_LOOPBACK)); 5604 } 5605} 5606 5607 5608static void bnx2x_ext_phy_loopback(struct link_params *params) 5609{ 5610 struct bnx2x *bp = params->bp; 5611 u8 ext_phy_addr; 5612 u32 ext_phy_type; 5613 5614 if (params->switch_cfg == SWITCH_CFG_10G) { 5615 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 5616 ext_phy_addr = XGXS_EXT_PHY_ADDR(params->ext_phy_config); 5617 /* CL37 Autoneg Enabled */ 5618 switch (ext_phy_type) { 5619 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT: 5620 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_NOT_CONN: 5621 DP(NETIF_MSG_LINK, 5622 "ext_phy_loopback: We should not get here\n"); 5623 break; 5624 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705: 5625 DP(NETIF_MSG_LINK, "ext_phy_loopback: 8705\n"); 5626 break; 5627 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706: 5628 DP(NETIF_MSG_LINK, "ext_phy_loopback: 8706\n"); 5629 break; 5630 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726: 5631 DP(NETIF_MSG_LINK, "PMA/PMD ext_phy_loopback: 8726\n"); 5632 bnx2x_cl45_write(bp, params->port, ext_phy_type, 5633 ext_phy_addr, 5634 MDIO_PMA_DEVAD, 5635 MDIO_PMA_REG_CTRL, 5636 0x0001); 5637 break; 5638 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_SFX7101: 5639 /* SFX7101_XGXS_TEST1 */ 5640 bnx2x_cl45_write(bp, params->port, ext_phy_type, 5641 ext_phy_addr, 5642 MDIO_XS_DEVAD, 5643 MDIO_XS_SFX7101_XGXS_TEST1, 5644 0x100); 5645 DP(NETIF_MSG_LINK, 5646 "ext_phy_loopback: set ext phy loopback\n"); 5647 break; 5648 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072: 5649 5650 break; 5651 } /* switch external PHY type */ 5652 } else { 5653 /* serdes */ 5654 ext_phy_type = SERDES_EXT_PHY_TYPE(params->ext_phy_config); 5655 ext_phy_addr = (params->ext_phy_config & 5656 PORT_HW_CFG_SERDES_EXT_PHY_ADDR_MASK) 5657 >> PORT_HW_CFG_SERDES_EXT_PHY_ADDR_SHIFT; 5658 } 5659} 5660 5661 5662/* 5663 *------------------------------------------------------------------------ 5664 * bnx2x_override_led_value - 5665 * 5666 * Override the led value of the requsted led 5667 * 5668 *------------------------------------------------------------------------ 5669 */ 5670u8 bnx2x_override_led_value(struct bnx2x *bp, u8 port, 5671 u32 led_idx, u32 value) 5672{ 5673 u32 reg_val; 5674 5675 /* If port 0 then use EMAC0, else use EMAC1*/ 5676 u32 emac_base = (port) ? GRCBASE_EMAC1 : GRCBASE_EMAC0; 5677 5678 DP(NETIF_MSG_LINK, 5679 "bnx2x_override_led_value() port %x led_idx %d value %d\n", 5680 port, led_idx, value); 5681 5682 switch (led_idx) { 5683 case 0: /* 10MB led */ 5684 /* Read the current value of the LED register in 5685 the EMAC block */ 5686 reg_val = REG_RD(bp, emac_base + EMAC_REG_EMAC_LED); 5687 /* Set the OVERRIDE bit to 1 */ 5688 reg_val |= EMAC_LED_OVERRIDE; 5689 /* If value is 1, set the 10M_OVERRIDE bit, 5690 otherwise reset it.*/ 5691 reg_val = (value == 1) ? (reg_val | EMAC_LED_10MB_OVERRIDE) : 5692 (reg_val & ~EMAC_LED_10MB_OVERRIDE); 5693 REG_WR(bp, emac_base + EMAC_REG_EMAC_LED, reg_val); 5694 break; 5695 case 1: /*100MB led */ 5696 /*Read the current value of the LED register in 5697 the EMAC block */ 5698 reg_val = REG_RD(bp, emac_base + EMAC_REG_EMAC_LED); 5699 /* Set the OVERRIDE bit to 1 */ 5700 reg_val |= EMAC_LED_OVERRIDE; 5701 /* If value is 1, set the 100M_OVERRIDE bit, 5702 otherwise reset it.*/ 5703 reg_val = (value == 1) ? (reg_val | EMAC_LED_100MB_OVERRIDE) : 5704 (reg_val & ~EMAC_LED_100MB_OVERRIDE); 5705 REG_WR(bp, emac_base + EMAC_REG_EMAC_LED, reg_val); 5706 break; 5707 case 2: /* 1000MB led */ 5708 /* Read the current value of the LED register in the 5709 EMAC block */ 5710 reg_val = REG_RD(bp, emac_base + EMAC_REG_EMAC_LED); 5711 /* Set the OVERRIDE bit to 1 */ 5712 reg_val |= EMAC_LED_OVERRIDE; 5713 /* If value is 1, set the 1000M_OVERRIDE bit, otherwise 5714 reset it. */ 5715 reg_val = (value == 1) ? (reg_val | EMAC_LED_1000MB_OVERRIDE) : 5716 (reg_val & ~EMAC_LED_1000MB_OVERRIDE); 5717 REG_WR(bp, emac_base + EMAC_REG_EMAC_LED, reg_val); 5718 break; 5719 case 3: /* 2500MB led */ 5720 /* Read the current value of the LED register in the 5721 EMAC block*/ 5722 reg_val = REG_RD(bp, emac_base + EMAC_REG_EMAC_LED); 5723 /* Set the OVERRIDE bit to 1 */ 5724 reg_val |= EMAC_LED_OVERRIDE; 5725 /* If value is 1, set the 2500M_OVERRIDE bit, otherwise 5726 reset it.*/ 5727 reg_val = (value == 1) ? (reg_val | EMAC_LED_2500MB_OVERRIDE) : 5728 (reg_val & ~EMAC_LED_2500MB_OVERRIDE); 5729 REG_WR(bp, emac_base + EMAC_REG_EMAC_LED, reg_val); 5730 break; 5731 case 4: /*10G led */ 5732 if (port == 0) { 5733 REG_WR(bp, NIG_REG_LED_10G_P0, 5734 value); 5735 } else { 5736 REG_WR(bp, NIG_REG_LED_10G_P1, 5737 value); 5738 } 5739 break; 5740 case 5: /* TRAFFIC led */ 5741 /* Find if the traffic control is via BMAC or EMAC */ 5742 if (port == 0) 5743 reg_val = REG_RD(bp, NIG_REG_NIG_EMAC0_EN); 5744 else 5745 reg_val = REG_RD(bp, NIG_REG_NIG_EMAC1_EN); 5746 5747 /* Override the traffic led in the EMAC:*/ 5748 if (reg_val == 1) { 5749 /* Read the current value of the LED register in 5750 the EMAC block */ 5751 reg_val = REG_RD(bp, emac_base + 5752 EMAC_REG_EMAC_LED); 5753 /* Set the TRAFFIC_OVERRIDE bit to 1 */ 5754 reg_val |= EMAC_LED_OVERRIDE; 5755 /* If value is 1, set the TRAFFIC bit, otherwise 5756 reset it.*/ 5757 reg_val = (value == 1) ? (reg_val | EMAC_LED_TRAFFIC) : 5758 (reg_val & ~EMAC_LED_TRAFFIC); 5759 REG_WR(bp, emac_base + EMAC_REG_EMAC_LED, reg_val); 5760 } else { /* Override the traffic led in the BMAC: */ 5761 REG_WR(bp, NIG_REG_LED_CONTROL_OVERRIDE_TRAFFIC_P0 5762 + port*4, 1); 5763 REG_WR(bp, NIG_REG_LED_CONTROL_TRAFFIC_P0 + port*4, 5764 value); 5765 } 5766 break; 5767 default: 5768 DP(NETIF_MSG_LINK, 5769 "bnx2x_override_led_value() unknown led index %d " 5770 "(should be 0-5)\n", led_idx); 5771 return -EINVAL; 5772 } 5773 5774 return 0; 5775} 5776 5777 5778u8 bnx2x_set_led(struct link_params *params, u8 mode, u32 speed) 5779{ 5780 u8 port = params->port; 5781 u16 hw_led_mode = params->hw_led_mode; 5782 u8 rc = 0; 5783 u32 tmp; 5784 u32 emac_base = port ? GRCBASE_EMAC1 : GRCBASE_EMAC0; 5785 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 5786 struct bnx2x *bp = params->bp; 5787 DP(NETIF_MSG_LINK, "bnx2x_set_led: port %x, mode %d\n", port, mode); 5788 DP(NETIF_MSG_LINK, "speed 0x%x, hw_led_mode 0x%x\n", 5789 speed, hw_led_mode); 5790 switch (mode) { 5791 case LED_MODE_OFF: 5792 REG_WR(bp, NIG_REG_LED_10G_P0 + port*4, 0); 5793 REG_WR(bp, NIG_REG_LED_MODE_P0 + port*4, 5794 SHARED_HW_CFG_LED_MAC1); 5795 5796 tmp = EMAC_RD(bp, EMAC_REG_EMAC_LED); 5797 EMAC_WR(bp, EMAC_REG_EMAC_LED, (tmp | EMAC_LED_OVERRIDE)); 5798 break; 5799 5800 case LED_MODE_OPER: 5801 if (ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT) { 5802 REG_WR(bp, NIG_REG_LED_MODE_P0 + port*4, 0); 5803 REG_WR(bp, NIG_REG_LED_10G_P0 + port*4, 1); 5804 } else { 5805 REG_WR(bp, NIG_REG_LED_MODE_P0 + port*4, 5806 hw_led_mode); 5807 } 5808 5809 REG_WR(bp, NIG_REG_LED_CONTROL_OVERRIDE_TRAFFIC_P0 + 5810 port*4, 0); 5811 /* Set blinking rate to ~15.9Hz */ 5812 REG_WR(bp, NIG_REG_LED_CONTROL_BLINK_RATE_P0 + port*4, 5813 LED_BLINK_RATE_VAL); 5814 REG_WR(bp, NIG_REG_LED_CONTROL_BLINK_RATE_ENA_P0 + 5815 port*4, 1); 5816 tmp = EMAC_RD(bp, EMAC_REG_EMAC_LED); 5817 EMAC_WR(bp, EMAC_REG_EMAC_LED, 5818 (tmp & (~EMAC_LED_OVERRIDE))); 5819 5820 if (CHIP_IS_E1(bp) && 5821 ((speed == SPEED_2500) || 5822 (speed == SPEED_1000) || 5823 (speed == SPEED_100) || 5824 (speed == SPEED_10))) { 5825 /* On Everest 1 Ax chip versions for speeds less than 5826 10G LED scheme is different */ 5827 REG_WR(bp, NIG_REG_LED_CONTROL_OVERRIDE_TRAFFIC_P0 5828 + port*4, 1); 5829 REG_WR(bp, NIG_REG_LED_CONTROL_TRAFFIC_P0 + 5830 port*4, 0); 5831 REG_WR(bp, NIG_REG_LED_CONTROL_BLINK_TRAFFIC_P0 + 5832 port*4, 1); 5833 } 5834 break; 5835 5836 default: 5837 rc = -EINVAL; 5838 DP(NETIF_MSG_LINK, "bnx2x_set_led: Invalid led mode %d\n", 5839 mode); 5840 break; 5841 } 5842 return rc; 5843 5844} 5845 5846u8 bnx2x_test_link(struct link_params *params, struct link_vars *vars) 5847{ 5848 struct bnx2x *bp = params->bp; 5849 u16 gp_status = 0; 5850 5851 CL45_RD_OVER_CL22(bp, params->port, 5852 params->phy_addr, 5853 MDIO_REG_BANK_GP_STATUS, 5854 MDIO_GP_STATUS_TOP_AN_STATUS1, 5855 &gp_status); 5856 /* link is up only if both local phy and external phy are up */ 5857 if ((gp_status & MDIO_GP_STATUS_TOP_AN_STATUS1_LINK_STATUS) && 5858 bnx2x_ext_phy_is_link_up(params, vars, 1)) 5859 return 0; 5860 5861 return -ESRCH; 5862} 5863 5864static u8 bnx2x_link_initialize(struct link_params *params, 5865 struct link_vars *vars) 5866{ 5867 struct bnx2x *bp = params->bp; 5868 u8 port = params->port; 5869 u8 rc = 0; 5870 u8 non_ext_phy; 5871 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 5872 5873 /* Activate the external PHY */ 5874 bnx2x_ext_phy_reset(params, vars); 5875 5876 bnx2x_set_aer_mmd(params, vars); 5877 5878 if (vars->phy_flags & PHY_XGXS_FLAG) 5879 bnx2x_set_master_ln(params); 5880 5881 rc = bnx2x_reset_unicore(params); 5882 /* reset the SerDes and wait for reset bit return low */ 5883 if (rc != 0) 5884 return rc; 5885 5886 bnx2x_set_aer_mmd(params, vars); 5887 5888 /* setting the masterLn_def again after the reset */ 5889 if (vars->phy_flags & PHY_XGXS_FLAG) { 5890 bnx2x_set_master_ln(params); 5891 bnx2x_set_swap_lanes(params); 5892 } 5893 5894 if (vars->phy_flags & PHY_XGXS_FLAG) { 5895 if ((params->req_line_speed && 5896 ((params->req_line_speed == SPEED_100) || 5897 (params->req_line_speed == SPEED_10))) || 5898 (!params->req_line_speed && 5899 (params->speed_cap_mask >= 5900 PORT_HW_CFG_SPEED_CAPABILITY_D0_10M_FULL) && 5901 (params->speed_cap_mask < 5902 PORT_HW_CFG_SPEED_CAPABILITY_D0_1G) 5903 )) { 5904 vars->phy_flags |= PHY_SGMII_FLAG; 5905 } else { 5906 vars->phy_flags &= ~PHY_SGMII_FLAG; 5907 } 5908 } 5909 /* In case of external phy existance, the line speed would be the 5910 line speed linked up by the external phy. In case it is direct only, 5911 then the line_speed during initialization will be equal to the 5912 req_line_speed*/ 5913 vars->line_speed = params->req_line_speed; 5914 5915 bnx2x_calc_ieee_aneg_adv(params, &vars->ieee_fc); 5916 5917 /* init ext phy and enable link state int */ 5918 non_ext_phy = ((ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT) || 5919 (params->loopback_mode == LOOPBACK_XGXS_10)); 5920 5921 if (non_ext_phy || 5922 (ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705) || 5923 (ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706) || 5924 (ext_phy_type == PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726) || 5925 (params->loopback_mode == LOOPBACK_EXT_PHY)) { 5926 if (params->req_line_speed == SPEED_AUTO_NEG) 5927 bnx2x_set_parallel_detection(params, vars->phy_flags); 5928 bnx2x_init_internal_phy(params, vars, non_ext_phy); 5929 } 5930 5931 if (!non_ext_phy) 5932 rc |= bnx2x_ext_phy_init(params, vars); 5933 5934 bnx2x_bits_dis(bp, NIG_REG_STATUS_INTERRUPT_PORT0 + port*4, 5935 (NIG_STATUS_XGXS0_LINK10G | 5936 NIG_STATUS_XGXS0_LINK_STATUS | 5937 NIG_STATUS_SERDES0_LINK_STATUS)); 5938 5939 return rc; 5940 5941} 5942 5943 5944u8 bnx2x_phy_init(struct link_params *params, struct link_vars *vars) 5945{ 5946 struct bnx2x *bp = params->bp; 5947 u32 val; 5948 5949 DP(NETIF_MSG_LINK, "Phy Initialization started\n"); 5950 DP(NETIF_MSG_LINK, "req_speed %d, req_flowctrl %d\n", 5951 params->req_line_speed, params->req_flow_ctrl); 5952 vars->link_status = 0; 5953 vars->phy_link_up = 0; 5954 vars->link_up = 0; 5955 vars->line_speed = 0; 5956 vars->duplex = DUPLEX_FULL; 5957 vars->flow_ctrl = BNX2X_FLOW_CTRL_NONE; 5958 vars->mac_type = MAC_TYPE_NONE; 5959 5960 if (params->switch_cfg == SWITCH_CFG_1G) 5961 vars->phy_flags = PHY_SERDES_FLAG; 5962 else 5963 vars->phy_flags = PHY_XGXS_FLAG; 5964 5965 /* disable attentions */ 5966 bnx2x_bits_dis(bp, NIG_REG_MASK_INTERRUPT_PORT0 + params->port*4, 5967 (NIG_MASK_XGXS0_LINK_STATUS | 5968 NIG_MASK_XGXS0_LINK10G | 5969 NIG_MASK_SERDES0_LINK_STATUS | 5970 NIG_MASK_MI_INT)); 5971 5972 bnx2x_emac_init(params, vars); 5973 5974 if (CHIP_REV_IS_FPGA(bp)) { 5975 5976 vars->link_up = 1; 5977 vars->line_speed = SPEED_10000; 5978 vars->duplex = DUPLEX_FULL; 5979 vars->flow_ctrl = BNX2X_FLOW_CTRL_NONE; 5980 vars->link_status = (LINK_STATUS_LINK_UP | LINK_10GTFD); 5981 /* enable on E1.5 FPGA */ 5982 if (CHIP_IS_E1H(bp)) { 5983 vars->flow_ctrl |= 5984 (BNX2X_FLOW_CTRL_TX | 5985 BNX2X_FLOW_CTRL_RX); 5986 vars->link_status |= 5987 (LINK_STATUS_TX_FLOW_CONTROL_ENABLED | 5988 LINK_STATUS_RX_FLOW_CONTROL_ENABLED); 5989 } 5990 5991 bnx2x_emac_enable(params, vars, 0); 5992 bnx2x_pbf_update(params, vars->flow_ctrl, vars->line_speed); 5993 /* disable drain */ 5994 REG_WR(bp, NIG_REG_EGRESS_DRAIN0_MODE + params->port*4, 0); 5995 5996 /* update shared memory */ 5997 bnx2x_update_mng(params, vars->link_status); 5998 5999 return 0; 6000 6001 } else 6002 if (CHIP_REV_IS_EMUL(bp)) { 6003 6004 vars->link_up = 1; 6005 vars->line_speed = SPEED_10000; 6006 vars->duplex = DUPLEX_FULL; 6007 vars->flow_ctrl = BNX2X_FLOW_CTRL_NONE; 6008 vars->link_status = (LINK_STATUS_LINK_UP | LINK_10GTFD); 6009 6010 bnx2x_bmac_enable(params, vars, 0); 6011 6012 bnx2x_pbf_update(params, vars->flow_ctrl, vars->line_speed); 6013 /* Disable drain */ 6014 REG_WR(bp, NIG_REG_EGRESS_DRAIN0_MODE 6015 + params->port*4, 0); 6016 6017 /* update shared memory */ 6018 bnx2x_update_mng(params, vars->link_status); 6019 6020 return 0; 6021 6022 } else 6023 if (params->loopback_mode == LOOPBACK_BMAC) { 6024 6025 vars->link_up = 1; 6026 vars->line_speed = SPEED_10000; 6027 vars->duplex = DUPLEX_FULL; 6028 vars->flow_ctrl = BNX2X_FLOW_CTRL_NONE; 6029 vars->mac_type = MAC_TYPE_BMAC; 6030 6031 vars->phy_flags = PHY_XGXS_FLAG; 6032 6033 bnx2x_phy_deassert(params, vars->phy_flags); 6034 /* set bmac loopback */ 6035 bnx2x_bmac_enable(params, vars, 1); 6036 6037 REG_WR(bp, NIG_REG_EGRESS_DRAIN0_MODE + 6038 params->port*4, 0); 6039 6040 } else if (params->loopback_mode == LOOPBACK_EMAC) { 6041 6042 vars->link_up = 1; 6043 vars->line_speed = SPEED_1000; 6044 vars->duplex = DUPLEX_FULL; 6045 vars->flow_ctrl = BNX2X_FLOW_CTRL_NONE; 6046 vars->mac_type = MAC_TYPE_EMAC; 6047 6048 vars->phy_flags = PHY_XGXS_FLAG; 6049 6050 bnx2x_phy_deassert(params, vars->phy_flags); 6051 /* set bmac loopback */ 6052 bnx2x_emac_enable(params, vars, 1); 6053 bnx2x_emac_program(params, vars->line_speed, 6054 vars->duplex); 6055 REG_WR(bp, NIG_REG_EGRESS_DRAIN0_MODE + 6056 params->port*4, 0); 6057 6058 } else if ((params->loopback_mode == LOOPBACK_XGXS_10) || 6059 (params->loopback_mode == LOOPBACK_EXT_PHY)) { 6060 6061 vars->link_up = 1; 6062 vars->line_speed = SPEED_10000; 6063 vars->duplex = DUPLEX_FULL; 6064 vars->flow_ctrl = BNX2X_FLOW_CTRL_NONE; 6065 6066 vars->phy_flags = PHY_XGXS_FLAG; 6067 6068 val = REG_RD(bp, 6069 NIG_REG_XGXS0_CTRL_PHY_ADDR+ 6070 params->port*0x18); 6071 params->phy_addr = (u8)val; 6072 6073 bnx2x_phy_deassert(params, vars->phy_flags); 6074 bnx2x_link_initialize(params, vars); 6075 6076 vars->mac_type = MAC_TYPE_BMAC; 6077 6078 bnx2x_bmac_enable(params, vars, 0); 6079 6080 if (params->loopback_mode == LOOPBACK_XGXS_10) { 6081 /* set 10G XGXS loopback */ 6082 bnx2x_set_xgxs_loopback(params, vars, 1); 6083 } else { 6084 /* set external phy loopback */ 6085 bnx2x_ext_phy_loopback(params); 6086 } 6087 REG_WR(bp, NIG_REG_EGRESS_DRAIN0_MODE + 6088 params->port*4, 0); 6089 6090 bnx2x_set_led(params, LED_MODE_OPER, vars->line_speed); 6091 } else 6092 /* No loopback */ 6093 { 6094 bnx2x_phy_deassert(params, vars->phy_flags); 6095 switch (params->switch_cfg) { 6096 case SWITCH_CFG_1G: 6097 vars->phy_flags |= PHY_SERDES_FLAG; 6098 if ((params->ext_phy_config & 6099 PORT_HW_CFG_SERDES_EXT_PHY_TYPE_MASK) == 6100 PORT_HW_CFG_SERDES_EXT_PHY_TYPE_BCM5482) { 6101 vars->phy_flags |= PHY_SGMII_FLAG; 6102 } 6103 6104 val = REG_RD(bp, 6105 NIG_REG_SERDES0_CTRL_PHY_ADDR+ 6106 params->port*0x10); 6107 6108 params->phy_addr = (u8)val; 6109 6110 break; 6111 case SWITCH_CFG_10G: 6112 vars->phy_flags |= PHY_XGXS_FLAG; 6113 val = REG_RD(bp, 6114 NIG_REG_XGXS0_CTRL_PHY_ADDR+ 6115 params->port*0x18); 6116 params->phy_addr = (u8)val; 6117 6118 break; 6119 default: 6120 DP(NETIF_MSG_LINK, "Invalid switch_cfg\n"); 6121 return -EINVAL; 6122 } 6123 DP(NETIF_MSG_LINK, "Phy address = 0x%x\n", params->phy_addr); 6124 6125 bnx2x_link_initialize(params, vars); 6126 msleep(30); 6127 bnx2x_link_int_enable(params); 6128 } 6129 return 0; 6130} 6131 6132static void bnx2x_8726_reset_phy(struct bnx2x *bp, u8 port, u8 ext_phy_addr) 6133{ 6134 DP(NETIF_MSG_LINK, "bnx2x_8726_reset_phy port %d\n", port); 6135 6136 /* Set serial boot control for external load */ 6137 bnx2x_cl45_write(bp, port, 6138 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726, ext_phy_addr, 6139 MDIO_PMA_DEVAD, 6140 MDIO_PMA_REG_GEN_CTRL, 0x0001); 6141} 6142 6143u8 bnx2x_link_reset(struct link_params *params, struct link_vars *vars, 6144 u8 reset_ext_phy) 6145{ 6146 struct bnx2x *bp = params->bp; 6147 u32 ext_phy_config = params->ext_phy_config; 6148 u8 port = params->port; 6149 u32 ext_phy_type = XGXS_EXT_PHY_TYPE(ext_phy_config); 6150 u32 val = REG_RD(bp, params->shmem_base + 6151 offsetof(struct shmem_region, dev_info. 6152 port_feature_config[params->port]. 6153 config)); 6154 DP(NETIF_MSG_LINK, "Resetting the link of port %d\n", port); 6155 /* disable attentions */ 6156 vars->link_status = 0; 6157 bnx2x_update_mng(params, vars->link_status); 6158 bnx2x_bits_dis(bp, NIG_REG_MASK_INTERRUPT_PORT0 + port*4, 6159 (NIG_MASK_XGXS0_LINK_STATUS | 6160 NIG_MASK_XGXS0_LINK10G | 6161 NIG_MASK_SERDES0_LINK_STATUS | 6162 NIG_MASK_MI_INT)); 6163 6164 /* activate nig drain */ 6165 REG_WR(bp, NIG_REG_EGRESS_DRAIN0_MODE + port*4, 1); 6166 6167 /* disable nig egress interface */ 6168 REG_WR(bp, NIG_REG_BMAC0_OUT_EN + port*4, 0); 6169 REG_WR(bp, NIG_REG_EGRESS_EMAC0_OUT_EN + port*4, 0); 6170 6171 /* Stop BigMac rx */ 6172 bnx2x_bmac_rx_disable(bp, port); 6173 6174 /* disable emac */ 6175 REG_WR(bp, NIG_REG_NIG_EMAC0_EN + port*4, 0); 6176 6177 msleep(10); 6178 /* The PHY reset is controled by GPIO 1 6179 * Hold it as vars low 6180 */ 6181 /* clear link led */ 6182 bnx2x_set_led(params, LED_MODE_OFF, 0); 6183 if (reset_ext_phy) { 6184 switch (ext_phy_type) { 6185 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT: 6186 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072: 6187 break; 6188 6189 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727: 6190 { 6191 6192 /* Disable Transmitter */ 6193 u8 ext_phy_addr = 6194 XGXS_EXT_PHY_ADDR(params->ext_phy_config); 6195 if ((val & PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_MASK) == 6196 PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_DISABLE_TX_LASER) 6197 bnx2x_sfp_set_transmitter(bp, port, 6198 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 6199 ext_phy_addr, 0); 6200 break; 6201 } 6202 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073: 6203 DP(NETIF_MSG_LINK, "Setting 8073 port %d into " 6204 "low power mode\n", 6205 port); 6206 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_2, 6207 MISC_REGISTERS_GPIO_OUTPUT_LOW, 6208 port); 6209 break; 6210 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726: 6211 { 6212 u8 ext_phy_addr = 6213 XGXS_EXT_PHY_ADDR(params->ext_phy_config); 6214 /* Set soft reset */ 6215 bnx2x_8726_reset_phy(bp, params->port, ext_phy_addr); 6216 break; 6217 } 6218 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM84823: 6219 { 6220 u8 ext_phy_addr = 6221 XGXS_EXT_PHY_ADDR(params->ext_phy_config); 6222 bnx2x_cl45_write(bp, port, 6223 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 6224 ext_phy_addr, 6225 MDIO_AN_DEVAD, 6226 MDIO_AN_REG_CTRL, 0x0000); 6227 bnx2x_cl45_write(bp, port, 6228 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481, 6229 ext_phy_addr, 6230 MDIO_PMA_DEVAD, 6231 MDIO_PMA_REG_CTRL, 1); 6232 break; 6233 } 6234 default: 6235 /* HW reset */ 6236 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_1, 6237 MISC_REGISTERS_GPIO_OUTPUT_LOW, 6238 port); 6239 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_2, 6240 MISC_REGISTERS_GPIO_OUTPUT_LOW, 6241 port); 6242 DP(NETIF_MSG_LINK, "reset external PHY\n"); 6243 } 6244 } 6245 /* reset the SerDes/XGXS */ 6246 REG_WR(bp, GRCBASE_MISC + MISC_REGISTERS_RESET_REG_3_CLEAR, 6247 (0x1ff << (port*16))); 6248 6249 /* reset BigMac */ 6250 REG_WR(bp, GRCBASE_MISC + MISC_REGISTERS_RESET_REG_2_CLEAR, 6251 (MISC_REGISTERS_RESET_REG_2_RST_BMAC0 << port)); 6252 6253 /* disable nig ingress interface */ 6254 REG_WR(bp, NIG_REG_BMAC0_IN_EN + port*4, 0); 6255 REG_WR(bp, NIG_REG_EMAC0_IN_EN + port*4, 0); 6256 REG_WR(bp, NIG_REG_BMAC0_OUT_EN + port*4, 0); 6257 REG_WR(bp, NIG_REG_EGRESS_EMAC0_OUT_EN + port*4, 0); 6258 vars->link_up = 0; 6259 return 0; 6260} 6261 6262static u8 bnx2x_update_link_down(struct link_params *params, 6263 struct link_vars *vars) 6264{ 6265 struct bnx2x *bp = params->bp; 6266 u8 port = params->port; 6267 6268 DP(NETIF_MSG_LINK, "Port %x: Link is down\n", port); 6269 bnx2x_set_led(params, LED_MODE_OFF, 0); 6270 6271 /* indicate no mac active */ 6272 vars->mac_type = MAC_TYPE_NONE; 6273 6274 /* update shared memory */ 6275 vars->link_status = 0; 6276 vars->line_speed = 0; 6277 bnx2x_update_mng(params, vars->link_status); 6278 6279 /* activate nig drain */ 6280 REG_WR(bp, NIG_REG_EGRESS_DRAIN0_MODE + port*4, 1); 6281 6282 /* disable emac */ 6283 REG_WR(bp, NIG_REG_NIG_EMAC0_EN + port*4, 0); 6284 6285 msleep(10); 6286 6287 /* reset BigMac */ 6288 bnx2x_bmac_rx_disable(bp, params->port); 6289 REG_WR(bp, GRCBASE_MISC + 6290 MISC_REGISTERS_RESET_REG_2_CLEAR, 6291 (MISC_REGISTERS_RESET_REG_2_RST_BMAC0 << port)); 6292 return 0; 6293} 6294 6295static u8 bnx2x_update_link_up(struct link_params *params, 6296 struct link_vars *vars, 6297 u8 link_10g, u32 gp_status) 6298{ 6299 struct bnx2x *bp = params->bp; 6300 u8 port = params->port; 6301 u8 rc = 0; 6302 6303 vars->link_status |= LINK_STATUS_LINK_UP; 6304 if (link_10g) { 6305 bnx2x_bmac_enable(params, vars, 0); 6306 bnx2x_set_led(params, LED_MODE_OPER, SPEED_10000); 6307 } else { 6308 rc = bnx2x_emac_program(params, vars->line_speed, 6309 vars->duplex); 6310 6311 bnx2x_emac_enable(params, vars, 0); 6312 6313 /* AN complete? */ 6314 if (gp_status & MDIO_AN_CL73_OR_37_COMPLETE) { 6315 if (!(vars->phy_flags & 6316 PHY_SGMII_FLAG)) 6317 bnx2x_set_gmii_tx_driver(params); 6318 } 6319 } 6320 6321 /* PBF - link up */ 6322 rc |= bnx2x_pbf_update(params, vars->flow_ctrl, 6323 vars->line_speed); 6324 6325 /* disable drain */ 6326 REG_WR(bp, NIG_REG_EGRESS_DRAIN0_MODE + port*4, 0); 6327 6328 /* update shared memory */ 6329 bnx2x_update_mng(params, vars->link_status); 6330 msleep(20); 6331 return rc; 6332} 6333/* This function should called upon link interrupt */ 6334/* In case vars->link_up, driver needs to 6335 1. Update the pbf 6336 2. Disable drain 6337 3. Update the shared memory 6338 4. Indicate link up 6339 5. Set LEDs 6340 Otherwise, 6341 1. Update shared memory 6342 2. Reset BigMac 6343 3. Report link down 6344 4. Unset LEDs 6345*/ 6346u8 bnx2x_link_update(struct link_params *params, struct link_vars *vars) 6347{ 6348 struct bnx2x *bp = params->bp; 6349 u8 port = params->port; 6350 u16 gp_status; 6351 u8 link_10g; 6352 u8 ext_phy_link_up, rc = 0; 6353 u32 ext_phy_type; 6354 u8 is_mi_int = 0; 6355 6356 DP(NETIF_MSG_LINK, "port %x, XGXS?%x, int_status 0x%x\n", 6357 port, (vars->phy_flags & PHY_XGXS_FLAG), 6358 REG_RD(bp, NIG_REG_STATUS_INTERRUPT_PORT0 + port*4)); 6359 6360 is_mi_int = (u8)(REG_RD(bp, NIG_REG_EMAC0_STATUS_MISC_MI_INT + 6361 port*0x18) > 0); 6362 DP(NETIF_MSG_LINK, "int_mask 0x%x MI_INT %x, SERDES_LINK %x\n", 6363 REG_RD(bp, NIG_REG_MASK_INTERRUPT_PORT0 + port*4), 6364 is_mi_int, 6365 REG_RD(bp, 6366 NIG_REG_SERDES0_STATUS_LINK_STATUS + port*0x3c)); 6367 6368 DP(NETIF_MSG_LINK, " 10G %x, XGXS_LINK %x\n", 6369 REG_RD(bp, NIG_REG_XGXS0_STATUS_LINK10G + port*0x68), 6370 REG_RD(bp, NIG_REG_XGXS0_STATUS_LINK_STATUS + port*0x68)); 6371 6372 /* disable emac */ 6373 REG_WR(bp, NIG_REG_NIG_EMAC0_EN + port*4, 0); 6374 6375 ext_phy_type = XGXS_EXT_PHY_TYPE(params->ext_phy_config); 6376 6377 /* Check external link change only for non-direct */ 6378 ext_phy_link_up = bnx2x_ext_phy_is_link_up(params, vars, is_mi_int); 6379 6380 /* Read gp_status */ 6381 CL45_RD_OVER_CL22(bp, port, params->phy_addr, 6382 MDIO_REG_BANK_GP_STATUS, 6383 MDIO_GP_STATUS_TOP_AN_STATUS1, 6384 &gp_status); 6385 6386 rc = bnx2x_link_settings_status(params, vars, gp_status, 6387 ext_phy_link_up); 6388 if (rc != 0) 6389 return rc; 6390 6391 /* anything 10 and over uses the bmac */ 6392 link_10g = ((vars->line_speed == SPEED_10000) || 6393 (vars->line_speed == SPEED_12000) || 6394 (vars->line_speed == SPEED_12500) || 6395 (vars->line_speed == SPEED_13000) || 6396 (vars->line_speed == SPEED_15000) || 6397 (vars->line_speed == SPEED_16000)); 6398 6399 bnx2x_link_int_ack(params, vars, link_10g, is_mi_int); 6400 6401 /* In case external phy link is up, and internal link is down 6402 ( not initialized yet probably after link initialization, it needs 6403 to be initialized. 6404 Note that after link down-up as result of cable plug, 6405 the xgxs link would probably become up again without the need to 6406 initialize it*/ 6407 6408 if ((ext_phy_type != PORT_HW_CFG_SERDES_EXT_PHY_TYPE_DIRECT) && 6409 (ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705) && 6410 (ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706) && 6411 (ext_phy_type != PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726) && 6412 (ext_phy_link_up && !vars->phy_link_up)) 6413 bnx2x_init_internal_phy(params, vars, 0); 6414 6415 /* link is up only if both local phy and external phy are up */ 6416 vars->link_up = (ext_phy_link_up && vars->phy_link_up); 6417 6418 if (vars->link_up) 6419 rc = bnx2x_update_link_up(params, vars, link_10g, gp_status); 6420 else 6421 rc = bnx2x_update_link_down(params, vars); 6422 6423 return rc; 6424} 6425 6426static u8 bnx2x_8073_common_init_phy(struct bnx2x *bp, u32 shmem_base) 6427{ 6428 u8 ext_phy_addr[PORT_MAX]; 6429 u16 val; 6430 s8 port; 6431 6432 /* PART1 - Reset both phys */ 6433 for (port = PORT_MAX - 1; port >= PORT_0; port--) { 6434 /* Extract the ext phy address for the port */ 6435 u32 ext_phy_config = REG_RD(bp, shmem_base + 6436 offsetof(struct shmem_region, 6437 dev_info.port_hw_config[port].external_phy_config)); 6438 6439 /* disable attentions */ 6440 bnx2x_bits_dis(bp, NIG_REG_MASK_INTERRUPT_PORT0 + port*4, 6441 (NIG_MASK_XGXS0_LINK_STATUS | 6442 NIG_MASK_XGXS0_LINK10G | 6443 NIG_MASK_SERDES0_LINK_STATUS | 6444 NIG_MASK_MI_INT)); 6445 6446 ext_phy_addr[port] = XGXS_EXT_PHY_ADDR(ext_phy_config); 6447 6448 /* Need to take the phy out of low power mode in order 6449 to write to access its registers */ 6450 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_2, 6451 MISC_REGISTERS_GPIO_OUTPUT_HIGH, port); 6452 6453 /* Reset the phy */ 6454 bnx2x_cl45_write(bp, port, 6455 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 6456 ext_phy_addr[port], 6457 MDIO_PMA_DEVAD, 6458 MDIO_PMA_REG_CTRL, 6459 1<<15); 6460 } 6461 6462 /* Add delay of 150ms after reset */ 6463 msleep(150); 6464 6465 /* PART2 - Download firmware to both phys */ 6466 for (port = PORT_MAX - 1; port >= PORT_0; port--) { 6467 u16 fw_ver1; 6468 6469 bnx2x_bcm8073_external_rom_boot(bp, port, 6470 ext_phy_addr[port], shmem_base); 6471 6472 bnx2x_cl45_read(bp, port, PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 6473 ext_phy_addr[port], 6474 MDIO_PMA_DEVAD, 6475 MDIO_PMA_REG_ROM_VER1, &fw_ver1); 6476 if (fw_ver1 == 0 || fw_ver1 == 0x4321) { 6477 DP(NETIF_MSG_LINK, 6478 "bnx2x_8073_common_init_phy port %x:" 6479 "Download failed. fw version = 0x%x\n", 6480 port, fw_ver1); 6481 return -EINVAL; 6482 } 6483 6484 /* Only set bit 10 = 1 (Tx power down) */ 6485 bnx2x_cl45_read(bp, port, 6486 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 6487 ext_phy_addr[port], 6488 MDIO_PMA_DEVAD, 6489 MDIO_PMA_REG_TX_POWER_DOWN, &val); 6490 6491 /* Phase1 of TX_POWER_DOWN reset */ 6492 bnx2x_cl45_write(bp, port, 6493 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 6494 ext_phy_addr[port], 6495 MDIO_PMA_DEVAD, 6496 MDIO_PMA_REG_TX_POWER_DOWN, 6497 (val | 1<<10)); 6498 } 6499 6500 /* Toggle Transmitter: Power down and then up with 600ms 6501 delay between */ 6502 msleep(600); 6503 6504 /* PART3 - complete TX_POWER_DOWN process, and set GPIO2 back to low */ 6505 for (port = PORT_MAX - 1; port >= PORT_0; port--) { 6506 /* Phase2 of POWER_DOWN_RESET */ 6507 /* Release bit 10 (Release Tx power down) */ 6508 bnx2x_cl45_read(bp, port, 6509 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 6510 ext_phy_addr[port], 6511 MDIO_PMA_DEVAD, 6512 MDIO_PMA_REG_TX_POWER_DOWN, &val); 6513 6514 bnx2x_cl45_write(bp, port, 6515 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 6516 ext_phy_addr[port], 6517 MDIO_PMA_DEVAD, 6518 MDIO_PMA_REG_TX_POWER_DOWN, (val & (~(1<<10)))); 6519 msleep(15); 6520 6521 /* Read modify write the SPI-ROM version select register */ 6522 bnx2x_cl45_read(bp, port, 6523 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 6524 ext_phy_addr[port], 6525 MDIO_PMA_DEVAD, 6526 MDIO_PMA_REG_EDC_FFE_MAIN, &val); 6527 bnx2x_cl45_write(bp, port, 6528 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073, 6529 ext_phy_addr[port], 6530 MDIO_PMA_DEVAD, 6531 MDIO_PMA_REG_EDC_FFE_MAIN, (val | (1<<12))); 6532 6533 /* set GPIO2 back to LOW */ 6534 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_2, 6535 MISC_REGISTERS_GPIO_OUTPUT_LOW, port); 6536 } 6537 return 0; 6538 6539} 6540 6541static u8 bnx2x_8727_common_init_phy(struct bnx2x *bp, u32 shmem_base) 6542{ 6543 u8 ext_phy_addr[PORT_MAX]; 6544 s8 port, first_port, i; 6545 u32 swap_val, swap_override; 6546 DP(NETIF_MSG_LINK, "Executing BCM8727 common init\n"); 6547 swap_val = REG_RD(bp, NIG_REG_PORT_SWAP); 6548 swap_override = REG_RD(bp, NIG_REG_STRAP_OVERRIDE); 6549 6550 bnx2x_ext_phy_hw_reset(bp, 1 ^ (swap_val && swap_override)); 6551 msleep(5); 6552 6553 if (swap_val && swap_override) 6554 first_port = PORT_0; 6555 else 6556 first_port = PORT_1; 6557 6558 /* PART1 - Reset both phys */ 6559 for (i = 0, port = first_port; i < PORT_MAX; i++, port = !port) { 6560 /* Extract the ext phy address for the port */ 6561 u32 ext_phy_config = REG_RD(bp, shmem_base + 6562 offsetof(struct shmem_region, 6563 dev_info.port_hw_config[port].external_phy_config)); 6564 6565 /* disable attentions */ 6566 bnx2x_bits_dis(bp, NIG_REG_MASK_INTERRUPT_PORT0 + port*4, 6567 (NIG_MASK_XGXS0_LINK_STATUS | 6568 NIG_MASK_XGXS0_LINK10G | 6569 NIG_MASK_SERDES0_LINK_STATUS | 6570 NIG_MASK_MI_INT)); 6571 6572 ext_phy_addr[port] = XGXS_EXT_PHY_ADDR(ext_phy_config); 6573 6574 /* Reset the phy */ 6575 bnx2x_cl45_write(bp, port, 6576 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 6577 ext_phy_addr[port], 6578 MDIO_PMA_DEVAD, 6579 MDIO_PMA_REG_CTRL, 6580 1<<15); 6581 } 6582 6583 /* Add delay of 150ms after reset */ 6584 msleep(150); 6585 6586 /* PART2 - Download firmware to both phys */ 6587 for (i = 0, port = first_port; i < PORT_MAX; i++, port = !port) { 6588 u16 fw_ver1; 6589 6590 bnx2x_bcm8727_external_rom_boot(bp, port, 6591 ext_phy_addr[port], shmem_base); 6592 6593 bnx2x_cl45_read(bp, port, PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727, 6594 ext_phy_addr[port], 6595 MDIO_PMA_DEVAD, 6596 MDIO_PMA_REG_ROM_VER1, &fw_ver1); 6597 if (fw_ver1 == 0 || fw_ver1 == 0x4321) { 6598 DP(NETIF_MSG_LINK, 6599 "bnx2x_8727_common_init_phy port %x:" 6600 "Download failed. fw version = 0x%x\n", 6601 port, fw_ver1); 6602 return -EINVAL; 6603 } 6604 } 6605 6606 return 0; 6607} 6608 6609 6610static u8 bnx2x_8726_common_init_phy(struct bnx2x *bp, u32 shmem_base) 6611{ 6612 u8 ext_phy_addr; 6613 u32 val; 6614 s8 port; 6615 6616 /* Use port1 because of the static port-swap */ 6617 /* Enable the module detection interrupt */ 6618 val = REG_RD(bp, MISC_REG_GPIO_EVENT_EN); 6619 val |= ((1<<MISC_REGISTERS_GPIO_3)| 6620 (1<<(MISC_REGISTERS_GPIO_3 + MISC_REGISTERS_GPIO_PORT_SHIFT))); 6621 REG_WR(bp, MISC_REG_GPIO_EVENT_EN, val); 6622 6623 bnx2x_ext_phy_hw_reset(bp, 1); 6624 msleep(5); 6625 for (port = 0; port < PORT_MAX; port++) { 6626 /* Extract the ext phy address for the port */ 6627 u32 ext_phy_config = REG_RD(bp, shmem_base + 6628 offsetof(struct shmem_region, 6629 dev_info.port_hw_config[port].external_phy_config)); 6630 6631 ext_phy_addr = XGXS_EXT_PHY_ADDR(ext_phy_config); 6632 DP(NETIF_MSG_LINK, "8726_common_init : ext_phy_addr = 0x%x\n", 6633 ext_phy_addr); 6634 6635 bnx2x_8726_reset_phy(bp, port, ext_phy_addr); 6636 6637 /* Set fault module detected LED on */ 6638 bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_0, 6639 MISC_REGISTERS_GPIO_HIGH, 6640 port); 6641 } 6642 6643 return 0; 6644} 6645 6646 6647static u8 bnx2x_84823_common_init_phy(struct bnx2x *bp, u32 shmem_base) 6648{ 6649 /* HW reset */ 6650 bnx2x_ext_phy_hw_reset(bp, 1); 6651 return 0; 6652} 6653u8 bnx2x_common_init_phy(struct bnx2x *bp, u32 shmem_base) 6654{ 6655 u8 rc = 0; 6656 u32 ext_phy_type; 6657 6658 DP(NETIF_MSG_LINK, "Begin common phy init\n"); 6659 6660 /* Read the ext_phy_type for arbitrary port(0) */ 6661 ext_phy_type = XGXS_EXT_PHY_TYPE( 6662 REG_RD(bp, shmem_base + 6663 offsetof(struct shmem_region, 6664 dev_info.port_hw_config[0].external_phy_config))); 6665 6666 switch (ext_phy_type) { 6667 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073: 6668 { 6669 rc = bnx2x_8073_common_init_phy(bp, shmem_base); 6670 break; 6671 } 6672 6673 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727: 6674 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8727_NOC: 6675 rc = bnx2x_8727_common_init_phy(bp, shmem_base); 6676 break; 6677 6678 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726: 6679 /* GPIO1 affects both ports, so there's need to pull 6680 it for single port alone */ 6681 rc = bnx2x_8726_common_init_phy(bp, shmem_base); 6682 break; 6683 case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM84823: 6684 rc = bnx2x_84823_common_init_phy(bp, shmem_base); 6685 break; 6686 default: 6687 DP(NETIF_MSG_LINK, 6688 "bnx2x_common_init_phy: ext_phy 0x%x not required\n", 6689 ext_phy_type); 6690 break; 6691 } 6692 6693 return rc; 6694} 6695 6696void bnx2x_sfx7101_sp_sw_reset(struct bnx2x *bp, u8 port, u8 phy_addr) 6697{ 6698 u16 val, cnt; 6699 6700 bnx2x_cl45_read(bp, port, 6701 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_SFX7101, 6702 phy_addr, 6703 MDIO_PMA_DEVAD, 6704 MDIO_PMA_REG_7101_RESET, &val); 6705 6706 for (cnt = 0; cnt < 10; cnt++) { 6707 msleep(50); 6708 /* Writes a self-clearing reset */ 6709 bnx2x_cl45_write(bp, port, 6710 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_SFX7101, 6711 phy_addr, 6712 MDIO_PMA_DEVAD, 6713 MDIO_PMA_REG_7101_RESET, 6714 (val | (1<<15))); 6715 /* Wait for clear */ 6716 bnx2x_cl45_read(bp, port, 6717 PORT_HW_CFG_XGXS_EXT_PHY_TYPE_SFX7101, 6718 phy_addr, 6719 MDIO_PMA_DEVAD, 6720 MDIO_PMA_REG_7101_RESET, &val); 6721 6722 if ((val & (1<<15)) == 0) 6723 break; 6724 } 6725} 6726