Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 589abe3a authored by Eilon Greenstein's avatar Eilon Greenstein Committed by David S. Miller
Browse files

bnx2x: Supporting BCM8726 PHY



Also adding the ability to recognize the optic module and disable it if it is
not authorized for safety reasons - since this feature might upset some users
which are willing to take the risk, it is optional and can be disabled by
setting an nvram bit (or a trivial driver patch to set this bit).
This dual port PHY requires special handling if the ports are swapped.

Signed-off-by: default avatarYaniv Rosner <yanivr@broadcom.com>
Signed-off-by: default avatarEilon Greenstein <eilong@broadcom.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 4acac6a5
Loading
Loading
Loading
Loading
+12 −1
Original line number Diff line number Diff line
@@ -245,7 +245,7 @@ struct port_hw_cfg { /* port 0: 0x12c port 1: 0x2bc */
#define PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073	    0x00000300
#define PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705	    0x00000400
#define PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706	    0x00000500
#define PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8276	    0x00000600
#define PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726	    0x00000600
#define PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8481	    0x00000700
#define PORT_HW_CFG_XGXS_EXT_PHY_TYPE_SFX7101	    0x00000800
#define PORT_HW_CFG_XGXS_EXT_PHY_TYPE_FAILURE	    0x0000fd00
@@ -299,6 +299,12 @@ struct shared_feat_cfg { /* NVRAM Offset */

	u32 config;						/* 0x450 */
#define SHARED_FEATURE_BMC_ECHO_MODE_EN 	    0x00000001

	/*  Use the values from options 47 and 48 instead of the HW default
	  values */
#define SHARED_FEAT_CFG_OVERRIDE_PREEMPHASIS_CFG_DISABLED     0x00000000
#define SHARED_FEAT_CFG_OVERRIDE_PREEMPHASIS_CFG_ENABLED      0x00000002

#define SHARED_FEATURE_MF_MODE_DISABLED 	    0x00000100

};
@@ -352,6 +358,11 @@ struct port_feat_cfg { /* port 0: 0x454 port 1: 0x4c8 */
#define PORT_FEATURE_MBA_ENABLED		    0x02000000
#define PORT_FEATURE_MFW_ENABLED		    0x04000000

	/*  Check the optic vendor via i2c before allowing it to be used by
	  SW */
#define PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_DISABLED 	      0x00000000
#define PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_ENABLED		      0x08000000

	u32 wol_config;
	/* Default is used when driver sets to "auto" mode */
#define PORT_FEATURE_WOL_DEFAULT_MASK		    0x00000003
+730 −46

File changed.

Preview size limit exceeded, changes collapsed.

+12 −2
Original line number Diff line number Diff line
@@ -89,6 +89,9 @@ struct link_params {

	/* phy_addr populated by the CLC */
	u8 phy_addr;
	u32 feature_config_flags;
#define FEATURE_CONFIG_OVERRIDE_PREEMPHASIS_ENABLED (1<<0)
#define FEATURE_CONFIG_MODULE_ENFORCMENT_ENABLED	(2<<0)
	/* Device pointer passed to all callback functions */
	struct bnx2x *bp;
};
@@ -125,8 +128,11 @@ struct link_vars {
/* Initialize the phy */
u8 bnx2x_phy_init(struct link_params *input, struct link_vars *output);

/* Reset the link. Should be called when driver or interface goes down */
u8 bnx2x_link_reset(struct link_params *params, struct link_vars *vars);
/* Reset the link. Should be called when driver or interface goes down
   Before calling phy firmware upgrade, the reset_ext_phy should be set
   to 0 */
u8 bnx2x_link_reset(struct link_params *params, struct link_vars *vars,
		  u8 reset_ext_phy);

/* bnx2x_link_update should be called upon link interrupt */
u8 bnx2x_link_update(struct link_params *input, struct link_vars *output);
@@ -163,6 +169,10 @@ u8 bnx2x_override_led_value(struct bnx2x *bp, u8 port, u32 led_idx, u32 value);

u8 bnx2x_flash_download(struct bnx2x *bp, u8 port, u32 ext_phy_config,
		      u8 driver_loaded, char data[], u32 size);
/* bnx2x_handle_module_detect_int should be called upon module detection
   interrupt */
void bnx2x_handle_module_detect_int(struct link_params *params);

/* Get the actual link status. In case it returns 0, link is up,
	otherwise link is down*/
u8 bnx2x_test_link(struct link_params *input, struct link_vars *vars);
+75 −15
Original line number Diff line number Diff line
@@ -2112,7 +2112,7 @@ static void bnx2x__link_reset(struct bnx2x *bp)
{
	if (!BP_NOMCP(bp)) {
		bnx2x_acquire_phy_lock(bp);
		bnx2x_link_reset(&bp->link_params, &bp->link_vars);
		bnx2x_link_reset(&bp->link_params, &bp->link_vars, 1);
		bnx2x_release_phy_lock(bp);
	} else
		BNX2X_ERR("Bootcode is missing -not resetting link\n");
@@ -2613,6 +2613,13 @@ static inline void bnx2x_attn_int_deasserted0(struct bnx2x *bp, u32 attn)
		}
	}

	if (attn & (AEU_INPUTS_ATTN_BITS_GPIO3_FUNCTION_0 |
		    AEU_INPUTS_ATTN_BITS_GPIO3_FUNCTION_1)) {
		bnx2x_acquire_phy_lock(bp);
		bnx2x_handle_module_detect_int(&bp->link_params);
		bnx2x_release_phy_lock(bp);
	}

	if (attn & HW_INTERRUT_ASSERT_SET_0) {

		val = REG_RD(bp, reg_offset);
@@ -5905,6 +5912,37 @@ static int bnx2x_init_port(struct bnx2x *bp)
	/* Port DMAE comes here */

	switch (XGXS_EXT_PHY_TYPE(bp->link_params.ext_phy_config)) {
	case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726:
		{
		u32 swap_val, swap_override, aeu_gpio_mask, offset;

		bnx2x_set_gpio(bp, MISC_REGISTERS_GPIO_3,
			       MISC_REGISTERS_GPIO_INPUT_HI_Z, port);

		/* The GPIO should be swapped if the swap register is
		   set and active */
		swap_val = REG_RD(bp, NIG_REG_PORT_SWAP);
		swap_override = REG_RD(bp, NIG_REG_STRAP_OVERRIDE);

		/* Select function upon port-swap configuration */
		if (port == 0) {
			offset = MISC_REG_AEU_ENABLE1_FUNC_0_OUT_0;
			aeu_gpio_mask = (swap_val && swap_override) ?
				AEU_INPUTS_ATTN_BITS_GPIO3_FUNCTION_1 :
				AEU_INPUTS_ATTN_BITS_GPIO3_FUNCTION_0;
		} else {
			offset = MISC_REG_AEU_ENABLE1_FUNC_1_OUT_0;
			aeu_gpio_mask = (swap_val && swap_override) ?
				AEU_INPUTS_ATTN_BITS_GPIO3_FUNCTION_0 :
				AEU_INPUTS_ATTN_BITS_GPIO3_FUNCTION_1;
		}
		val = REG_RD(bp, offset);
		/* add GPIO3 to group */
		val |= aeu_gpio_mask;
		REG_WR(bp, offset, val);
		}
		break;

	case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_SFX7101:
		/* add SPIO 5 to group 0 */
		val = REG_RD(bp, MISC_REG_AEU_ENABLE1_FUNC_0_OUT_0);
@@ -7623,48 +7661,60 @@ static void __devinit bnx2x_link_settings_supported(struct bnx2x *bp,
					       SUPPORTED_Asym_Pause);
			break;

		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705:
			BNX2X_DEV_INFO("ext_phy_type 0x%x (8705)\n",
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072:
			BNX2X_DEV_INFO("ext_phy_type 0x%x (8072)\n",
				       ext_phy_type);

			bp->port.supported |= (SUPPORTED_10000baseT_Full |
					       SUPPORTED_1000baseT_Full |
					       SUPPORTED_FIBRE |
					       SUPPORTED_Autoneg |
					       SUPPORTED_Pause |
					       SUPPORTED_Asym_Pause);
			break;

		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706:
			BNX2X_DEV_INFO("ext_phy_type 0x%x (8706)\n",
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073:
			BNX2X_DEV_INFO("ext_phy_type 0x%x (8073)\n",
				       ext_phy_type);

			bp->port.supported |= (SUPPORTED_10000baseT_Full |
					       SUPPORTED_2500baseX_Full |
					       SUPPORTED_1000baseT_Full |
					       SUPPORTED_FIBRE |
					       SUPPORTED_Autoneg |
					       SUPPORTED_Pause |
					       SUPPORTED_Asym_Pause);
			break;

		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072:
			BNX2X_DEV_INFO("ext_phy_type 0x%x (8072)\n",
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705:
			BNX2X_DEV_INFO("ext_phy_type 0x%x (8705)\n",
				       ext_phy_type);

			bp->port.supported |= (SUPPORTED_10000baseT_Full |
					       SUPPORTED_1000baseT_Full |
					       SUPPORTED_FIBRE |
					       SUPPORTED_Autoneg |
					       SUPPORTED_Pause |
					       SUPPORTED_Asym_Pause);
			break;

		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073:
			BNX2X_DEV_INFO("ext_phy_type 0x%x (8073)\n",
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706:
			BNX2X_DEV_INFO("ext_phy_type 0x%x (8706)\n",
				       ext_phy_type);

			bp->port.supported |= (SUPPORTED_10000baseT_Full |
					       SUPPORTED_2500baseX_Full |
					       SUPPORTED_1000baseT_Full |
					       SUPPORTED_FIBRE |
					       SUPPORTED_Pause |
					       SUPPORTED_Asym_Pause);
			break;

		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726:
			BNX2X_DEV_INFO("ext_phy_type 0x%x (8726)\n",
				       ext_phy_type);

			bp->port.supported |= (SUPPORTED_10000baseT_Full |
					       SUPPORTED_1000baseT_Full |
					       SUPPORTED_Autoneg |
					       SUPPORTED_FIBRE |
					       SUPPORTED_Pause |
					       SUPPORTED_Asym_Pause);
			break;
@@ -7905,6 +7955,7 @@ static void __devinit bnx2x_get_port_hwinfo(struct bnx2x *bp)
{
	int port = BP_PORT(bp);
	u32 val, val2;
	u32 config;

	bp->link_params.bp = bp;
	bp->link_params.port = port;
@@ -7923,6 +7974,14 @@ static void __devinit bnx2x_get_port_hwinfo(struct bnx2x *bp)
	bp->port.link_config =
		SHMEM_RD(bp, dev_info.port_feature_config[port].link_config);

	config = SHMEM_RD(bp, dev_info.port_feature_config[port].config);
	if (config & PORT_FEAT_CFG_OPT_MDL_ENFRCMNT_ENABLED)
		bp->link_params.feature_config_flags |=
				FEATURE_CONFIG_MODULE_ENFORCMENT_ENABLED;
	else
		bp->link_params.feature_config_flags &=
				~FEATURE_CONFIG_MODULE_ENFORCMENT_ENABLED;

	BNX2X_DEV_INFO("serdes_config 0x%08x  lane_config 0x%08x\n"
	     KERN_INFO "  ext_phy_config 0x%08x  speed_cap_mask 0x%08x"
		       "  link_config 0x%08x\n",
@@ -8121,10 +8180,11 @@ static int bnx2x_get_settings(struct net_device *dev, struct ethtool_cmd *cmd)

		switch (ext_phy_type) {
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_DIRECT:
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705:
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706:
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8072:
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8073:
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8705:
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8706:
		case PORT_HW_CFG_XGXS_EXT_PHY_TYPE_BCM8726:
			cmd->port = PORT_FIBRE;
			break;

@@ -8807,7 +8867,7 @@ static int bnx2x_set_eeprom(struct net_device *dev,
			if ((bp->state == BNX2X_STATE_OPEN) ||
			    (bp->state == BNX2X_STATE_DISABLED)) {
				rc |= bnx2x_link_reset(&bp->link_params,
						       &bp->link_vars);
						       &bp->link_vars, 1);
				rc |= bnx2x_phy_init(&bp->link_params,
						     &bp->link_vars);
			}
+22 −0
Original line number Diff line number Diff line
@@ -5800,9 +5800,25 @@ Theotherbitsarereservedandshouldbezero*/
#define MDIO_PMA_REG_ROM_VER2		0xca1a
#define MDIO_PMA_REG_EDC_FFE_MAIN	0xca1b
#define MDIO_PMA_REG_PLL_BANDWIDTH	0xca1d
#define MDIO_PMA_REG_MISC_CTRL0 	0xca23
#define MDIO_PMA_REG_LRM_MODE		0xca3f
#define MDIO_PMA_REG_CDR_BANDWIDTH	0xca46
#define MDIO_PMA_REG_MISC_CTRL1 	0xca85

#define MDIO_PMA_REG_8726_TWO_WIRE_CTRL 	0x8000
#define MDIO_PMA_REG_8726_TWO_WIRE_CTRL_STATUS_MASK	0x000c
#define MDIO_PMA_REG_8726_TWO_WIRE_STATUS_IDLE		0x0000
#define MDIO_PMA_REG_8726_TWO_WIRE_STATUS_COMPLETE	0x0004
#define MDIO_PMA_REG_8726_TWO_WIRE_STATUS_IN_PROGRESS	0x0008
#define MDIO_PMA_REG_8726_TWO_WIRE_STATUS_FAILED	0x000c
#define MDIO_PMA_REG_8726_TWO_WIRE_BYTE_CNT	0x8002
#define MDIO_PMA_REG_8726_TWO_WIRE_MEM_ADDR	0x8003
#define MDIO_PMA_REG_8726_TWO_WIRE_DATA_BUF	0xc820
#define MDIO_PMA_REG_8726_TWO_WIRE_DATA_MASK 0xff
#define MDIO_PMA_REG_8726_TX_CTRL1		0xca01
#define MDIO_PMA_REG_8726_TX_CTRL2		0xca05


#define MDIO_PMA_REG_7101_RESET 	0xc000
#define MDIO_PMA_REG_7107_LED_CNTL	0xc007
#define MDIO_PMA_REG_7101_VER1		0xc026
@@ -5832,6 +5848,12 @@ Theotherbitsarereservedandshouldbezero*/
#define MDIO_XS_PLL_SEQUENCER		0x8000
#define MDIO_XS_SFX7101_XGXS_TEST1	0xc00a

#define MDIO_XS_8706_REG_BANK_RX0	0x80bc
#define MDIO_XS_8706_REG_BANK_RX1	0x80cc
#define MDIO_XS_8706_REG_BANK_RX2	0x80dc
#define MDIO_XS_8706_REG_BANK_RX3	0x80ec
#define MDIO_XS_8706_REG_BANK_RXA	0x80fc

#define MDIO_AN_DEVAD			0x7
/*ieee*/
#define MDIO_AN_REG_CTRL		0x0000