[U-Boot] [PATCH v3 00/16] Add more commands for VSC9953 L2 Switch

This patch set adds several features for VSC9953 L2 Switch: - VLAN configuration; - port statistics; - FDB table operations; - enable/disable HW learning; - private/shared VLAN learning.
Also, the parser needed to be changed to allow commands with optional parameters and to allow developers to easily add new commands. This set also creates a parser with generic commands for L2 Ethernet Switche drivers.
Since new features are added, the default configuration had to be changed to: - HW learning enabled on all ports; (HW default) - All ports are in VLAN 1; - All ports are VLAN aware; - All ports have POP_COUNT 1; - All ports have PVID 1; - All ports have TPID 0x8100; (HW default) - All ports tag frames classified to all VLANs that are not PVID;
If the user decides to compile the VSC9953 driver without the support for commands, the above default configuration should be sufficient to make the L2 Switch work in unmanaged mode.
New supported commands: - show a port's statistics; - enable/disable/show learning configuration on a port; - add/delete a MAC entry in FDB; show the FDB table; - add/remove a VLAN to/from a port (VLAN members); - set/show PVID (ingress and egress VLAN tagging) for a port; - set egress tagging mod for a port; - configure VID source for egress tag; - make VLAN learning shared or private; - enable/disable VLAN ingress filtering on a port.
Changes for v2: - removed Change-id field; - Added the patch that changes the License at the end of the patch set for an easier integration;
Changes for v3: - added a patch that creates a parser with generic commands for Ethernet switch drivers - added a patch that adds new functions for working with bitfields; - added a patch that exports a function that verifies if a string has the format of a MAC address - added a patch to rename macros from vsc9953.h that started with "CONFIG_" - added a patch with a bug fix fdone in the Cleanup patch - all patches declare each variable on a line, without using tabs - in the parser, the MAC address is no longer remembered dynamically, but statically - the parser now returns CMD_RET_* macros instead of 1 and 0 - small code fixes
Codrin Ciubotariu (16): drivers/net/vsc9953: Remove 'CONFIG_' from macros' name drivers/net/vsc9953: Cleanup patch drivers/net/vsc9953: Fix bug when enabling a port drivers/net/vsc9953: Fix missing reserved register include/bitfield: Add new bitfield operations drivers/net/vsc9953: Add default configuration for VSC9953 L2 Switch common/cmd_ethsw: Add generic commands for Ethernet Switches drivers/net/vsc9953: Use the generic Ethernet Switch parser drivers/net/vsc9953: Add command to show/clear port counters drivers/net/vsc9953: Add commands to enable/disable HW learning net/eth.c: Add function to validate a MAC address drivers/net/vsc9953: Add commands to manipulate the FDB for VSC9953 drivers/net/vsc9953: Add VLAN commands for VSC9953 drivers/net/vsc9953: Add command for shared/private VLAN learning drivers/net/vsc9953: Add commands for VLAN ingress filtering drivers/net/vsc9953: Add GPL-2.0+ SPDX-License-Identifier
common/Makefile | 1 + common/cmd_ethsw.c | 1025 ++++++++++++++++++++ common/env_flags.c | 15 +- drivers/net/vsc9953.c | 2247 +++++++++++++++++++++++++++++++++++++++----- include/bitfield.h | 32 + include/configs/T104xRDB.h | 2 +- include/ethsw.h | 95 ++ include/net.h | 1 + include/vsc9953.h | 389 ++++++-- net/eth.c | 30 + 10 files changed, 3502 insertions(+), 335 deletions(-) create mode 100644 common/cmd_ethsw.c create mode 100644 include/ethsw.h

Signed-off-by: Codrin Ciubotariu codrin.ciubotariu@freescale.com ---
Changes for v3: - none; new patch;
drivers/net/vsc9953.c | 38 +++++++++++++++++++------------------- include/vsc9953.h | 46 +++++++++++++++++++++++----------------------- 2 files changed, 42 insertions(+), 42 deletions(-)
diff --git a/drivers/net/vsc9953.c b/drivers/net/vsc9953.c index fed7358..068ab86 100644 --- a/drivers/net/vsc9953.c +++ b/drivers/net/vsc9953.c @@ -202,26 +202,26 @@ void vsc9953_init(bd_t *bis) VSC9953_DEVCPU_GCB);
out_le32(&l2dev_gcb->chip_regs.soft_rst, - CONFIG_VSC9953_SOFT_SWC_RST_ENA); + VSC9953_SOFT_SWC_RST_ENA); timeout = 50000; while ((in_le32(&l2dev_gcb->chip_regs.soft_rst) & - CONFIG_VSC9953_SOFT_SWC_RST_ENA) && --timeout) + VSC9953_SOFT_SWC_RST_ENA) && --timeout) udelay(1); /* busy wait for vsc9953 soft reset */ if (timeout == 0) debug("Timeout waiting for VSC9953 to reset\n");
- out_le32(&l2sys_reg->sys.reset_cfg, CONFIG_VSC9953_MEM_ENABLE | - CONFIG_VSC9953_MEM_INIT); + out_le32(&l2sys_reg->sys.reset_cfg, VSC9953_MEM_ENABLE | + VSC9953_MEM_INIT);
timeout = 50000; while ((in_le32(&l2sys_reg->sys.reset_cfg) & - CONFIG_VSC9953_MEM_INIT) && --timeout) + VSC9953_MEM_INIT) && --timeout) udelay(1); /* busy wait for vsc9953 memory init */ if (timeout == 0) debug("Timeout waiting for VSC9953 memory to initialize\n");
out_le32(&l2sys_reg->sys.reset_cfg, (in_le32(&l2sys_reg->sys.reset_cfg) - | CONFIG_VSC9953_CORE_ENABLE)); + | VSC9953_CORE_ENABLE));
/* VSC9953 Setting to be done once only */ out_le32(&l2qsys_reg->sys.ext_cpu_cfg, 0x00000b00); @@ -233,34 +233,34 @@ void vsc9953_init(bd_t *bis) /* Enable VSC9953 GMII Ports Port ID 0 - 7 */ if (VSC9953_INTERNAL_PORT_CHECK(i)) { out_le32(&l2ana_reg->pfc[i].pfc_cfg, - CONFIG_VSC9953_PFC_FC_QSGMII); + VSC9953_PFC_FC_QSGMII); out_le32(&l2sys_reg->pause_cfg.mac_fc_cfg[i], - CONFIG_VSC9953_MAC_FC_CFG_QSGMII); + VSC9953_MAC_FC_CFG_QSGMII); } else { out_le32(&l2ana_reg->pfc[i].pfc_cfg, - CONFIG_VSC9953_PFC_FC); + VSC9953_PFC_FC); out_le32(&l2sys_reg->pause_cfg.mac_fc_cfg[i], - CONFIG_VSC9953_MAC_FC_CFG); + VSC9953_MAC_FC_CFG); } out_le32(&l2dev_gmii_reg->port_mode.clock_cfg, - CONFIG_VSC9953_CLOCK_CFG); + VSC9953_CLOCK_CFG); out_le32(&l2dev_gmii_reg->mac_cfg_status.mac_ena_cfg, - CONFIG_VSC9953_MAC_ENA_CFG); + VSC9953_MAC_ENA_CFG); out_le32(&l2dev_gmii_reg->mac_cfg_status.mac_mode_cfg, - CONFIG_VSC9953_MAC_MODE_CFG); + VSC9953_MAC_MODE_CFG); out_le32(&l2dev_gmii_reg->mac_cfg_status.mac_ifg_cfg, - CONFIG_VSC9953_MAC_IFG_CFG); + VSC9953_MAC_IFG_CFG); /* mac_hdx_cfg varies with port id*/ - hdx_cfg = (CONFIG_VSC9953_MAC_HDX_CFG | (i << 16)); + hdx_cfg = VSC9953_MAC_HDX_CFG | (i << 16); out_le32(&l2dev_gmii_reg->mac_cfg_status.mac_hdx_cfg, hdx_cfg); out_le32(&l2sys_reg->sys.front_port_mode[i], - CONFIG_VSC9953_FRONT_PORT_MODE); + VSC9953_FRONT_PORT_MODE); out_le32(&l2qsys_reg->sys.switch_port_mode[i], - CONFIG_VSC9953_PORT_ENA); + VSC9953_PORT_ENA); out_le32(&l2dev_gmii_reg->mac_cfg_status.mac_maxlen_cfg, - CONFIG_VSC9953_MAC_MAX_LEN); + VSC9953_MAC_MAX_LEN); out_le32(&l2sys_reg->pause_cfg.pause_cfg[i], - CONFIG_VSC9953_PAUSE_CFG); + VSC9953_PAUSE_CFG); /* WAIT FOR 2 us*/ udelay(2);
diff --git a/include/vsc9953.h b/include/vsc9953.h index 3d11b87..3f14dad 100644 --- a/include/vsc9953.h +++ b/include/vsc9953.h @@ -33,29 +33,29 @@ #define T1040_SWITCH_GMII_DEV_OFFSET 0x010000 #define VSC9953_PHY_REGS_OFFST 0x0000AC
-#define CONFIG_VSC9953_SOFT_SWC_RST_ENA 0x00000001 -#define CONFIG_VSC9953_CORE_ENABLE 0x80 -#define CONFIG_VSC9953_MEM_ENABLE 0x40 -#define CONFIG_VSC9953_MEM_INIT 0x20 - -#define CONFIG_VSC9953_PORT_ENA 0x00003a00 -#define CONFIG_VSC9953_MAC_ENA_CFG 0x00000011 -#define CONFIG_VSC9953_MAC_MODE_CFG 0x00000011 -#define CONFIG_VSC9953_MAC_IFG_CFG 0x00000515 -#define CONFIG_VSC9953_MAC_HDX_CFG 0x00001043 -#define CONFIG_VSC9953_CLOCK_CFG 0x00000001 -#define CONFIG_VSC9953_CLOCK_CFG_1000M 0x00000001 -#define CONFIG_VSC9953_PFC_FC 0x00000001 -#define CONFIG_VSC9953_PFC_FC_QSGMII 0x00000000 -#define CONFIG_VSC9953_MAC_FC_CFG 0x04700000 -#define CONFIG_VSC9953_MAC_FC_CFG_QSGMII 0x00700000 -#define CONFIG_VSC9953_PAUSE_CFG 0x001ffffe -#define CONFIG_VSC9953_TOT_TAIL_DROP_LVL 0x000003ff -#define CONFIG_VSC9953_FRONT_PORT_MODE 0x00000000 -#define CONFIG_VSC9953_MAC_MAX_LEN 0x000005ee - -#define CONFIG_VSC9953_VCAP_MV_CFG 0x0000ffff -#define CONFIG_VSC9953_VCAP_UPDATE_CTRL 0x01000004 +#define VSC9953_SOFT_SWC_RST_ENA 0x00000001 +#define VSC9953_CORE_ENABLE 0x80 +#define VSC9953_MEM_ENABLE 0x40 +#define VSC9953_MEM_INIT 0x20 + +#define VSC9953_PORT_ENA 0x00003a00 +#define VSC9953_MAC_ENA_CFG 0x00000011 +#define VSC9953_MAC_MODE_CFG 0x00000011 +#define VSC9953_MAC_IFG_CFG 0x00000515 +#define VSC9953_MAC_HDX_CFG 0x00001043 +#define VSC9953_CLOCK_CFG 0x00000001 +#define VSC9953_CLOCK_CFG_1000M 0x00000001 +#define VSC9953_PFC_FC 0x00000001 +#define VSC9953_PFC_FC_QSGMII 0x00000000 +#define VSC9953_MAC_FC_CFG 0x04700000 +#define VSC9953_MAC_FC_CFG_QSGMII 0x00700000 +#define VSC9953_PAUSE_CFG 0x001ffffe +#define VSC9953_TOT_TAIL_DROP_LVL 0x000003ff +#define VSC9953_FRONT_PORT_MODE 0x00000000 +#define VSC9953_MAC_MAX_LEN 0x000005ee + +#define VSC9953_VCAP_MV_CFG 0x0000ffff +#define VSC9953_VCAP_UPDATE_CTRL 0x01000004 #define VSC9953_MAX_PORTS 10 #define VSC9953_PORT_CHECK(port) \ (((port) < 0 || (port) >= VSC9953_MAX_PORTS) ? 0 : 1)

Hi Codrin,
On Fri, Jul 24, 2015 at 8:52 AM, Codrin Ciubotariu codrin.ciubotariu@freescale.com wrote:
Signed-off-by: Codrin Ciubotariu codrin.ciubotariu@freescale.com
Acked-by: Joe Hershberger joe.hershberger@ni.com

On 08/07/2015 01:17 PM, Joe Hershberger wrote:
Hi Codrin,
On Fri, Jul 24, 2015 at 8:52 AM, Codrin Ciubotariu codrin.ciubotariu@freescale.com wrote:
Signed-off-by: Codrin Ciubotariu codrin.ciubotariu@freescale.com
Acked-by: Joe Hershberger joe.hershberger@ni.com
Joe,
Do you want to take them in, or leave them to me?
York

Hi York,
On Fri, Aug 7, 2015 at 4:02 PM, York Sun yorksun@freescale.com wrote:
On 08/07/2015 01:17 PM, Joe Hershberger wrote:
Hi Codrin,
On Fri, Jul 24, 2015 at 8:52 AM, Codrin Ciubotariu codrin.ciubotariu@freescale.com wrote:
Signed-off-by: Codrin Ciubotariu codrin.ciubotariu@freescale.com
Acked-by: Joe Hershberger joe.hershberger@ni.com
Joe,
Do you want to take them in, or leave them to me?
They are only used on your platform, right? So it will probably be faster tested in that branch.
I think you should take them, but notice that there is an issue with patch 7. Maybe you can fix it inline and not resend the series.
Thanks, -Joe

On 08/07/2015 02:07 PM, Joe Hershberger wrote:
Hi York,
On Fri, Aug 7, 2015 at 4:02 PM, York Sun yorksun@freescale.com wrote:
On 08/07/2015 01:17 PM, Joe Hershberger wrote:
Hi Codrin,
On Fri, Jul 24, 2015 at 8:52 AM, Codrin Ciubotariu codrin.ciubotariu@freescale.com wrote:
Signed-off-by: Codrin Ciubotariu codrin.ciubotariu@freescale.com
Acked-by: Joe Hershberger joe.hershberger@ni.com
Joe,
Do you want to take them in, or leave them to me?
They are only used on your platform, right? So it will probably be faster tested in that branch.
I think you should take them, but notice that there is an issue with patch 7. Maybe you can fix it inline and not resend the series.
I will take care of them. Thanks.
York

This patch groups some macros defined for registers and replaces some magic numbers from vsc9953 with macros. Also, "port" and "port_nr" words are replaced with "port_no", puts each variable declaration on a line and removes unnecessary tabs.
Signed-off-by: Codrin Ciubotariu codrin.ciubotariu@freescale.com ---
Changes for v2: - removed Change-id field;
Changes for v3: - each variable is declared on a separate line, without using tabs - some functions return macros from errno.h insted of 1 or -1 - removed duplicate of macro CONFIG_VSC9953_PAUSE_CFG - code that fixed a small bug was moved in a new patch;
drivers/net/vsc9953.c | 144 +++++++++++++++++++++++++------------------------- include/vsc9953.h | 121 ++++++++++++++++++++++++++---------------- 2 files changed, 147 insertions(+), 118 deletions(-)
diff --git a/drivers/net/vsc9953.c b/drivers/net/vsc9953.c index 068ab86..524b979 100644 --- a/drivers/net/vsc9953.c +++ b/drivers/net/vsc9953.c @@ -10,6 +10,8 @@ #include <asm/fsl_serdes.h> #include <fm_eth.h> #include <fsl_memac.h> +#include <errno.h> +#include <malloc.h> #include <vsc9953.h>
static struct vsc9953_info vsc9953_l2sw = { @@ -25,50 +27,50 @@ static struct vsc9953_info vsc9953_l2sw = { .port[9] = VSC9953_PORT_INFO_INITIALIZER(9), };
-void vsc9953_port_info_set_mdio(int port, struct mii_dev *bus) +void vsc9953_port_info_set_mdio(int port_no, struct mii_dev *bus) { - if (!VSC9953_PORT_CHECK(port)) + if (!VSC9953_PORT_CHECK(port_no)) return;
- vsc9953_l2sw.port[port].bus = bus; + vsc9953_l2sw.port[port_no].bus = bus; }
-void vsc9953_port_info_set_phy_address(int port, int address) +void vsc9953_port_info_set_phy_address(int port_no, int address) { - if (!VSC9953_PORT_CHECK(port)) + if (!VSC9953_PORT_CHECK(port_no)) return;
- vsc9953_l2sw.port[port].phyaddr = address; + vsc9953_l2sw.port[port_no].phyaddr = address; }
-void vsc9953_port_info_set_phy_int(int port, phy_interface_t phy_int) +void vsc9953_port_info_set_phy_int(int port_no, phy_interface_t phy_int) { - if (!VSC9953_PORT_CHECK(port)) + if (!VSC9953_PORT_CHECK(port_no)) return;
- vsc9953_l2sw.port[port].enet_if = phy_int; + vsc9953_l2sw.port[port_no].enet_if = phy_int; }
-void vsc9953_port_enable(int port) +void vsc9953_port_enable(int port_no) { - if (!VSC9953_PORT_CHECK(port)) + if (!VSC9953_PORT_CHECK(port_no)) return;
- vsc9953_l2sw.port[port].enabled = 1; + vsc9953_l2sw.port[port_no].enabled = 1; }
-void vsc9953_port_disable(int port) +void vsc9953_port_disable(int port_no) { - if (!VSC9953_PORT_CHECK(port)) + if (!VSC9953_PORT_CHECK(port_no)) return;
- vsc9953_l2sw.port[port].enabled = 0; + vsc9953_l2sw.port[port_no].enabled = 0; }
static void vsc9953_mdio_write(struct vsc9953_mii_mng *phyregs, int port_addr, int regnum, int value) { - int timeout = 50000; + int timeout = 50000;
out_le32(&phyregs->miimcmd, (0x1 << 31) | ((port_addr & 0x1f) << 25) | ((regnum & 0x1f) << 20) | ((value & 0xffff) << 4) | @@ -85,8 +87,8 @@ static void vsc9953_mdio_write(struct vsc9953_mii_mng *phyregs, int port_addr, static int vsc9953_mdio_read(struct vsc9953_mii_mng *phyregs, int port_addr, int regnum) { - int value = 0xFFFF; - int timeout = 50000; + int value = 0xFFFF; + int timeout = 50000;
while ((in_le32(&phyregs->miimstatus) & MIIMIND_OPR_PEND) && --timeout) udelay(1); @@ -120,8 +122,8 @@ static int vsc9953_mdio_read(struct vsc9953_mii_mng *phyregs, int port_addr,
static int init_phy(struct eth_device *dev) { - struct vsc9953_port_info *l2sw_port = dev->priv; - struct phy_device *phydev = NULL; + struct vsc9953_port_info *l2sw_port = dev->priv; + struct phy_device *phydev = NULL;
#ifdef CONFIG_PHYLIB if (!l2sw_port->bus) @@ -148,21 +150,21 @@ static int init_phy(struct eth_device *dev) return 0; }
-static int vsc9953_port_init(int port) +static int vsc9953_port_init(int port_no) { - struct eth_device *dev; + struct eth_device *dev;
/* Internal ports never have a PHY */ - if (VSC9953_INTERNAL_PORT_CHECK(port)) + if (VSC9953_INTERNAL_PORT_CHECK(port_no)) return 0;
/* alloc eth device */ dev = (struct eth_device *)calloc(1, sizeof(struct eth_device)); if (!dev) - return 1; + return -ENOMEM;
- sprintf(dev->name, "SW@PORT%d", port); - dev->priv = &vsc9953_l2sw.port[port]; + sprintf(dev->name, "SW@PORT%d", port_no); + dev->priv = &vsc9953_l2sw.port[port_no]; dev->init = NULL; dev->halt = NULL; dev->send = NULL; @@ -170,7 +172,7 @@ static int vsc9953_port_init(int port)
if (init_phy(dev)) { free(dev); - return 1; + return -ENODEV; }
return 0; @@ -178,13 +180,15 @@ static int vsc9953_port_init(int port)
void vsc9953_init(bd_t *bis) { - u32 i, hdx_cfg = 0, phy_addr = 0; - int timeout; - struct vsc9953_system_reg *l2sys_reg; - struct vsc9953_qsys_reg *l2qsys_reg; - struct vsc9953_dev_gmii *l2dev_gmii_reg; - struct vsc9953_analyzer *l2ana_reg; - struct vsc9953_devcpu_gcb *l2dev_gcb; + u32 i; + u32 hdx_cfg = 0; + u32 phy_addr = 0; + int timeout; + struct vsc9953_system_reg *l2sys_reg; + struct vsc9953_qsys_reg *l2qsys_reg; + struct vsc9953_dev_gmii *l2dev_gmii_reg; + struct vsc9953_analyzer *l2ana_reg; + struct vsc9953_devcpu_gcb *l2dev_gcb;
l2dev_gmii_reg = (struct vsc9953_dev_gmii *)(VSC9953_OFFSET + VSC9953_DEV_GMII_OFFSET); @@ -312,83 +316,81 @@ void vsc9953_init(bd_t *bis)
#ifdef CONFIG_VSC9953_CMD /* Enable/disable status of a VSC9953 port */ -static void vsc9953_port_status_set(int port_nr, u8 enabled) +static void vsc9953_port_status_set(int port_no, u8 enabled) { - u32 val; - struct vsc9953_qsys_reg *l2qsys_reg; + struct vsc9953_qsys_reg *l2qsys_reg;
/* Administrative down */ - if (vsc9953_l2sw.port[port_nr].enabled == 0) + if (!vsc9953_l2sw.port[port_no].enabled) return;
l2qsys_reg = (struct vsc9953_qsys_reg *)(VSC9953_OFFSET + VSC9953_QSYS_OFFSET);
- val = in_le32(&l2qsys_reg->sys.switch_port_mode[port_nr]); - if (enabled == 1) - val |= (1 << 13); + if (enabled) + setbits_le32(&l2qsys_reg->sys.switch_port_mode[port_no], + VSC9953_PORT_ENA); else - val &= ~(1 << 13); - - out_le32(&l2qsys_reg->sys.switch_port_mode[port_nr], val); + clrbits_le32(&l2qsys_reg->sys.switch_port_mode[port_no], + VSC9953_PORT_ENA); }
/* Set all VSC9953 ports' status */ static void vsc9953_port_all_status_set(u8 enabled) { - int i; + int i;
for (i = 0; i < VSC9953_MAX_PORTS; i++) vsc9953_port_status_set(i, enabled); }
/* Start autonegotiation for a VSC9953 PHY */ -static void vsc9953_phy_autoneg(int port_nr) +static void vsc9953_phy_autoneg(int port_no) { - if (!vsc9953_l2sw.port[port_nr].phydev) + if (!vsc9953_l2sw.port[port_no].phydev) return;
- if (vsc9953_l2sw.port[port_nr].phydev->drv->startup( - vsc9953_l2sw.port[port_nr].phydev)) - printf("Failed to start PHY for port %d\n", port_nr); + if (vsc9953_l2sw.port[port_no].phydev->drv->startup( + vsc9953_l2sw.port[port_no].phydev)) + printf("Failed to start PHY for port %d\n", port_no); }
/* Start autonegotiation for all VSC9953 PHYs */ static void vsc9953_phy_all_autoneg(void) { - int i; + int i;
for (i = 0; i < VSC9953_MAX_PORTS; i++) vsc9953_phy_autoneg(i); }
/* Print a VSC9953 port's configuration */ -static void vsc9953_port_config_show(int port) +static void vsc9953_port_config_show(int port_no) { - int speed; - int duplex; - int link; - u8 enabled; - u32 val; + int speed; + int duplex; + int link; + u8 enabled; + u32 val; struct vsc9953_qsys_reg *l2qsys_reg;
l2qsys_reg = (struct vsc9953_qsys_reg *)(VSC9953_OFFSET + VSC9953_QSYS_OFFSET);
- val = in_le32(&l2qsys_reg->sys.switch_port_mode[port]); - enabled = vsc9953_l2sw.port[port].enabled & - ((val & 0x00002000) >> 13); + val = in_le32(&l2qsys_reg->sys.switch_port_mode[port_no]); + enabled = vsc9953_l2sw.port[port_no].enabled && + (val & VSC9953_PORT_ENA);
/* internal ports (8 and 9) are fixed */ - if (VSC9953_INTERNAL_PORT_CHECK(port)) { + if (VSC9953_INTERNAL_PORT_CHECK(port_no)) { link = 1; speed = SPEED_2500; duplex = DUPLEX_FULL; } else { - if (vsc9953_l2sw.port[port].phydev) { - link = vsc9953_l2sw.port[port].phydev->link; - speed = vsc9953_l2sw.port[port].phydev->speed; - duplex = vsc9953_l2sw.port[port].phydev->duplex; + if (vsc9953_l2sw.port[port_no].phydev) { + link = vsc9953_l2sw.port[port_no].phydev->link; + speed = vsc9953_l2sw.port[port_no].phydev->speed; + duplex = vsc9953_l2sw.port[port_no].phydev->duplex; } else { link = -1; speed = -1; @@ -396,7 +398,7 @@ static void vsc9953_port_config_show(int port) } }
- printf("%8d ", port); + printf("%8d ", port_no); printf("%8s ", enabled == 1 ? "enabled" : "disabled"); printf("%8s ", link == 1 ? "up" : "down");
@@ -426,7 +428,7 @@ static void vsc9953_port_config_show(int port) /* Print VSC9953 ports' configuration */ static void vsc9953_port_all_config_show(void) { - int i; + int i;
for (i = 0; i < VSC9953_MAX_PORTS; i++) vsc9953_port_config_show(i); @@ -487,11 +489,11 @@ static int do_ethsw(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
U_BOOT_CMD(ethsw, 5, 0, do_ethsw, "vsc9953 l2 switch commands", - "port <port_nr> enable|disable\n" + "port <port_no> enable|disable\n" " - enable/disable an l2 switch port\n" - " port_nr=0..9; use "all" for all ports\n" - "ethsw port <port_nr> show\n" + " port_no=0..9; use "all" for all ports\n" + "ethsw port <port_no> show\n" " - show an l2 switch port's configuration\n" - " port_nr=0..9; use "all" for all ports\n" + " port_no=0..9; use "all" for all ports\n" ); #endif /* CONFIG_VSC9953_CMD */ diff --git a/include/vsc9953.h b/include/vsc9953.h index 3f14dad..6ebe141 100644 --- a/include/vsc9953.h +++ b/include/vsc9953.h @@ -17,7 +17,6 @@ #include <config.h> #include <miiphy.h> #include <asm/types.h> -#include <malloc.h>
#define VSC9953_OFFSET (CONFIG_SYS_CCSRBAR_DEFAULT + 0x800000)
@@ -33,29 +32,57 @@ #define T1040_SWITCH_GMII_DEV_OFFSET 0x010000 #define VSC9953_PHY_REGS_OFFST 0x0000AC
+/* Macros for vsc9953_chip_regs.soft_rst register */ #define VSC9953_SOFT_SWC_RST_ENA 0x00000001 + +/* Macros for vsc9953_sys_sys.reset_cfg register */ #define VSC9953_CORE_ENABLE 0x80 #define VSC9953_MEM_ENABLE 0x40 #define VSC9953_MEM_INIT 0x20
-#define VSC9953_PORT_ENA 0x00003a00 +/* Macros for vsc9953_dev_gmii_mac_cfg_status.mac_ena_cfg register */ #define VSC9953_MAC_ENA_CFG 0x00000011 + +/* Macros for vsc9953_dev_gmii_mac_cfg_status.mac_mode_cfg register */ #define VSC9953_MAC_MODE_CFG 0x00000011 + +/* Macros for vsc9953_dev_gmii_mac_cfg_status.mac_ifg_cfg register */ #define VSC9953_MAC_IFG_CFG 0x00000515 + +/* Macros for vsc9953_dev_gmii_mac_cfg_status.mac_hdx_cfg register */ #define VSC9953_MAC_HDX_CFG 0x00001043 + +/* Macros for vsc9953_dev_gmii_mac_cfg_status.mac_maxlen_cfg register */ +#define VSC9953_MAC_MAX_LEN 0x000005ee + +/* Macros for vsc9953_dev_gmii_port_mode.clock_cfg register */ #define VSC9953_CLOCK_CFG 0x00000001 #define VSC9953_CLOCK_CFG_1000M 0x00000001 + +/* Macros for vsc9953_sys_sys.front_port_mode register */ +#define VSC9953_FRONT_PORT_MODE 0x00000000 + +/* Macros for vsc9953_ana_pfc.pfc_cfg register */ #define VSC9953_PFC_FC 0x00000001 #define VSC9953_PFC_FC_QSGMII 0x00000000 + +/* Macros for vsc9953_sys_pause_cfg.mac_fc_cfg register */ #define VSC9953_MAC_FC_CFG 0x04700000 #define VSC9953_MAC_FC_CFG_QSGMII 0x00700000 + +/* Macros for vsc9953_sys_pause_cfg.pause_cfg register */ #define VSC9953_PAUSE_CFG 0x001ffffe + +/* Macros for vsc9953_sys_pause_cfgtot_tail_drop_lvl register */ #define VSC9953_TOT_TAIL_DROP_LVL 0x000003ff -#define VSC9953_FRONT_PORT_MODE 0x00000000 -#define VSC9953_MAC_MAX_LEN 0x000005ee
+/* Macros for vsc9953_vcap_core_cfg.vcap_mv_cfg register */ #define VSC9953_VCAP_MV_CFG 0x0000ffff #define VSC9953_VCAP_UPDATE_CTRL 0x01000004 + +/* Macros for vsc9953_qsys_sys.switch_port_mode register */ +#define VSC9953_PORT_ENA 0x00003a00 + #define VSC9953_MAX_PORTS 10 #define VSC9953_PORT_CHECK(port) \ (((port) < 0 || (port) >= VSC9953_MAX_PORTS) ? 0 : 1) @@ -74,9 +101,9 @@ struct vsc9953_mdio_info { char *name; };
-/* VSC9953 ANA structure for T1040 U-boot*/ +/* VSC9953 ANA structure */
-struct vsc9953_ana_port { +struct vsc9953_ana_port { u32 vlan_cfg; u32 drop_cfg; u32 qos_cfg; @@ -138,7 +165,7 @@ struct vsc9953_ana_pgid { u32 port_grp_id[91]; };
-struct vsc9953_ana_pfc { +struct vsc9953_ana_pfc { u32 pfc_cfg; u32 reserved1[15]; }; @@ -149,7 +176,7 @@ struct vsc9953_ana_pol_misc { u32 pol_hyst; };
-struct vsc9953_ana_common { +struct vsc9953_ana_common { u32 aggr_cfg; u32 cpuq_cfg; u32 cpuq_8021_cfg; @@ -176,18 +203,18 @@ struct vsc9953_analyzer { u32 reserved5[196]; struct vsc9953_ana_common common; }; -/* END VSC9953 ANA structure for T1040 U-boot*/ +/* END VSC9953 ANA structure t*/
-/* VSC9953 DEV_GMII structure for T1040 U-boot*/ +/* VSC9953 DEV_GMII structure */
-struct vsc9953_dev_gmii_port_mode { +struct vsc9953_dev_gmii_port_mode { u32 clock_cfg; u32 port_misc; u32 reserved1; u32 eee_cfg; };
-struct vsc9953_dev_gmii_mac_cfg_status { +struct vsc9953_dev_gmii_mac_cfg_status { u32 mac_ena_cfg; u32 mac_mode_cfg; u32 mac_maxlen_cfg; @@ -205,11 +232,11 @@ struct vsc9953_dev_gmii { struct vsc9953_dev_gmii_mac_cfg_status mac_cfg_status; };
-/* END VSC9953 DEV_GMII structure for T1040 U-boot*/ +/* END VSC9953 DEV_GMII structure */
-/* VSC9953 QSYS structure for T1040 U-boot*/ +/* VSC9953 QSYS structure */
-struct vsc9953_qsys_hsch { +struct vsc9953_qsys_hsch { u32 cir_cfg; u32 reserved1; u32 se_cfg; @@ -218,7 +245,7 @@ struct vsc9953_qsys_hsch { u32 reserved2[20]; };
-struct vsc9953_qsys_sys { +struct vsc9953_qsys_sys { u32 port_mode[12]; u32 switch_port_mode[11]; u32 stat_cnt_cfg; @@ -232,32 +259,32 @@ struct vsc9953_qsys_sys { u32 reserved1[23]; };
-struct vsc9953_qsys_qos_cfg { +struct vsc9953_qsys_qos_cfg { u32 red_profile[16]; u32 res_qos_mode; };
-struct vsc9953_qsys_drop_cfg { +struct vsc9953_qsys_drop_cfg { u32 egr_drop_mode; };
-struct vsc9953_qsys_mmgt { +struct vsc9953_qsys_mmgt { u32 eq_cntrl; u32 reserved1; };
-struct vsc9953_qsys_hsch_misc { +struct vsc9953_qsys_hsch_misc { u32 hsch_misc_cfg; u32 reserved1[546]; };
-struct vsc9953_qsys_res_ctrl { +struct vsc9953_qsys_res_ctrl { u32 res_cfg; u32 res_stat;
};
-struct vsc9953_qsys_reg { +struct vsc9953_qsys_reg { struct vsc9953_qsys_hsch hsch[108]; struct vsc9953_qsys_sys sys; struct vsc9953_qsys_qos_cfg qos_cfg; @@ -267,18 +294,18 @@ struct vsc9953_qsys_reg { struct vsc9953_qsys_res_ctrl res_ctrl[1024]; };
-/* END VSC9953 QSYS structure for T1040 U-boot*/ +/* END VSC9953 QSYS structure */
-/* VSC9953 SYS structure for T1040 U-boot*/ +/* VSC9953 SYS structure */
-struct vsc9953_sys_stat { +struct vsc9953_sys_stat { u32 rx_cntrs[64]; u32 tx_cntrs[64]; u32 drop_cntrs[64]; u32 reserved1[6]; };
-struct vsc9953_sys_sys { +struct vsc9953_sys_sys { u32 reset_cfg; u32 reserved1; u32 vlan_etype_cfg; @@ -289,7 +316,7 @@ struct vsc9953_sys_sys { u32 reserved2[50]; };
-struct vsc9953_sys_pause_cfg { +struct vsc9953_sys_pause_cfg { u32 pause_cfg[11]; u32 pause_tot_cfg; u32 tail_drop_level[11]; @@ -297,29 +324,29 @@ struct vsc9953_sys_pause_cfg { u32 mac_fc_cfg[10]; };
-struct vsc9953_sys_mmgt { +struct vsc9953_sys_mmgt { u16 free_cnt; };
-struct vsc9953_system_reg { +struct vsc9953_system_reg { struct vsc9953_sys_stat stat; struct vsc9953_sys_sys sys; struct vsc9953_sys_pause_cfg pause_cfg; struct vsc9953_sys_mmgt mmgt; };
-/* END VSC9953 SYS structure for T1040 U-boot*/ +/* END VSC9953 SYS structure */
-/* VSC9953 DEVCPU_GCB structure for T1040 U-boot*/ +/* VSC9953 DEVCPU_GCB structure */
-struct vsc9953_chip_regs { +struct vsc9953_chip_regs { u32 chipd_id; u32 gpr; u32 soft_rst; };
-struct vsc9953_gpio { +struct vsc9953_gpio { u32 gpio_out_set[10]; u32 gpio_out_clr[10]; u32 gpio_out[10]; @@ -338,31 +365,31 @@ struct vsc9953_mii_mng { u32 miiscan_lst_rslts_valid; };
-struct vsc9953_mii_read_scan { +struct vsc9953_mii_read_scan { u32 mii_scan_results_sticky[2]; };
-struct vsc9953_devcpu_gcb { +struct vsc9953_devcpu_gcb { struct vsc9953_chip_regs chip_regs; struct vsc9953_gpio gpio; struct vsc9953_mii_mng mii_mng[2]; struct vsc9953_mii_read_scan mii_read_scan; };
-/* END VSC9953 DEVCPU_GCB structure for T1040 U-boot*/ +/* END VSC9953 DEVCPU_GCB structure */
-/* VSC9953 IS* structure for T1040 U-boot*/ +/* VSC9953 IS* structure */
-struct vsc9953_vcap_core_cfg { +struct vsc9953_vcap_core_cfg { u32 vcap_update_ctrl; u32 vcap_mv_cfg; };
-struct vsc9953_vcap { -struct vsc9953_vcap_core_cfg vcap_core_cfg; +struct vsc9953_vcap { + struct vsc9953_vcap_core_cfg vcap_core_cfg; };
-/* END VSC9953 IS* structure for T1040 U-boot*/ +/* END VSC9953 IS* structure */
#define VSC9953_PORT_INFO_INITIALIZER(idx) \ { \ @@ -388,15 +415,15 @@ struct vsc9953_port_info {
/* Structure to describe a VSC9953 switch */ struct vsc9953_info { - struct vsc9953_port_info port[VSC9953_MAX_PORTS]; + struct vsc9953_port_info port[VSC9953_MAX_PORTS]; };
void vsc9953_init(bd_t *bis);
-void vsc9953_port_info_set_mdio(int port, struct mii_dev *bus); -void vsc9953_port_info_set_phy_address(int port, int address); -void vsc9953_port_enable(int port); -void vsc9953_port_disable(int port); -void vsc9953_port_info_set_phy_int(int port, phy_interface_t phy_int); +void vsc9953_port_info_set_mdio(int port_no, struct mii_dev *bus); +void vsc9953_port_info_set_phy_address(int port_no, int address); +void vsc9953_port_enable(int port_no); +void vsc9953_port_disable(int port_no); +void vsc9953_port_info_set_phy_int(int port_no, phy_interface_t phy_int);
#endif /* _VSC9953_H_ */

Hi Codrin,
On Fri, Jul 24, 2015 at 8:52 AM, Codrin Ciubotariu codrin.ciubotariu@freescale.com wrote:
This patch groups some macros defined for registers and replaces some magic numbers from vsc9953 with macros. Also, "port" and "port_nr" words are replaced with "port_no", puts each variable declaration on a line and removes unnecessary tabs.
Signed-off-by: Codrin Ciubotariu codrin.ciubotariu@freescale.com
Changes for v2: - removed Change-id field;
Changes for v3: - each variable is declared on a separate line, without using tabs - some functions return macros from errno.h insted of 1 or -1 - removed duplicate of macro CONFIG_VSC9953_PAUSE_CFG - code that fixed a small bug was moved in a new patch;
drivers/net/vsc9953.c | 144 +++++++++++++++++++++++++------------------------- include/vsc9953.h | 121 ++++++++++++++++++++++++++---------------- 2 files changed, 147 insertions(+), 118 deletions(-)
Acked-by: Joe Hershberger joe.hershberger@ni.com

When a port is enabled at init time, the initializing function touches more bits than necessary to enable a port (also touches reserved bits and default bit values). This patch fixes this issue by changing the value of the define used to enable the port and assures that no other bits are changes by replacing out_le32() with setbits_le32().
Signed-off-by: Codrin Ciubotariu codrin.ciubotariu@freescale.com ---
Dhanges for v3: - none; new patch;
drivers/net/vsc9953.c | 4 ++-- include/vsc9953.h | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-)
diff --git a/drivers/net/vsc9953.c b/drivers/net/vsc9953.c index 524b979..2e8eec4 100644 --- a/drivers/net/vsc9953.c +++ b/drivers/net/vsc9953.c @@ -259,8 +259,8 @@ void vsc9953_init(bd_t *bis) out_le32(&l2dev_gmii_reg->mac_cfg_status.mac_hdx_cfg, hdx_cfg); out_le32(&l2sys_reg->sys.front_port_mode[i], VSC9953_FRONT_PORT_MODE); - out_le32(&l2qsys_reg->sys.switch_port_mode[i], - VSC9953_PORT_ENA); + setbits_le32(&l2qsys_reg->sys.switch_port_mode[i], + VSC9953_PORT_ENA); out_le32(&l2dev_gmii_reg->mac_cfg_status.mac_maxlen_cfg, VSC9953_MAC_MAX_LEN); out_le32(&l2sys_reg->pause_cfg.pause_cfg[i], diff --git a/include/vsc9953.h b/include/vsc9953.h index 6ebe141..6ae5fec 100644 --- a/include/vsc9953.h +++ b/include/vsc9953.h @@ -81,7 +81,7 @@ #define VSC9953_VCAP_UPDATE_CTRL 0x01000004
/* Macros for vsc9953_qsys_sys.switch_port_mode register */ -#define VSC9953_PORT_ENA 0x00003a00 +#define VSC9953_PORT_ENA 0x00002000
#define VSC9953_MAX_PORTS 10 #define VSC9953_PORT_CHECK(port) \

Hi Codrin,
On Fri, Jul 24, 2015 at 8:52 AM, Codrin Ciubotariu codrin.ciubotariu@freescale.com wrote:
When a port is enabled at init time, the initializing function touches more bits than necessary to enable a port (also touches reserved bits and default bit values). This patch fixes this issue by changing the value of the define used to enable the port and assures that no other bits are changes by replacing out_le32() with setbits_le32().
Signed-off-by: Codrin Ciubotariu codrin.ciubotariu@freescale.com
Dhanges for v3: - none; new patch;
drivers/net/vsc9953.c | 4 ++-- include/vsc9953.h | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-)
Acked-by: Joe Hershberger joe.hershberger@ni.com

On 07/24/2015 06:52 AM, Codrin Ciubotariu wrote:
This patch set adds several features for VSC9953 L2 Switch:
- VLAN configuration;
- port statistics;
- FDB table operations;
- enable/disable HW learning;
- private/shared VLAN learning.
Also, the parser needed to be changed to allow commands with optional parameters and to allow developers to easily add new commands. This set also creates a parser with generic commands for L2 Ethernet Switche drivers.
Since new features are added, the default configuration had to be changed to:
- HW learning enabled on all ports; (HW default)
- All ports are in VLAN 1;
- All ports are VLAN aware;
- All ports have POP_COUNT 1;
- All ports have PVID 1;
- All ports have TPID 0x8100; (HW default)
- All ports tag frames classified to all VLANs that are not PVID;
If the user decides to compile the VSC9953 driver without the support for commands, the above default configuration should be sufficient to make the L2 Switch work in unmanaged mode.
New supported commands:
- show a port's statistics;
- enable/disable/show learning configuration on a port;
- add/delete a MAC entry in FDB; show the FDB table;
- add/remove a VLAN to/from a port (VLAN members);
- set/show PVID (ingress and egress VLAN tagging) for a port;
- set egress tagging mod for a port;
- configure VID source for egress tag;
- make VLAN learning shared or private;
- enable/disable VLAN ingress filtering on a port.
Changes for v2:
- removed Change-id field;
- Added the patch that changes the License
at the end of the patch set for an easier integration;
Changes for v3:
- added a patch that creates a parser with generic commands for Ethernet switch drivers
- added a patch that adds new functions for working with bitfields;
- added a patch that exports a function that verifies if a string has the format of a MAC address
- added a patch to rename macros from vsc9953.h that started with "CONFIG_"
- added a patch with a bug fix fdone in the Cleanup patch
- all patches declare each variable on a line, without using tabs
- in the parser, the MAC address is no longer remembered dynamically, but statically
- the parser now returns CMD_RET_* macros instead of 1 and 0
- small code fixes
Codrin Ciubotariu (16): drivers/net/vsc9953: Remove 'CONFIG_' from macros' name drivers/net/vsc9953: Cleanup patch drivers/net/vsc9953: Fix bug when enabling a port drivers/net/vsc9953: Fix missing reserved register include/bitfield: Add new bitfield operations drivers/net/vsc9953: Add default configuration for VSC9953 L2 Switch common/cmd_ethsw: Add generic commands for Ethernet Switches drivers/net/vsc9953: Use the generic Ethernet Switch parser drivers/net/vsc9953: Add command to show/clear port counters drivers/net/vsc9953: Add commands to enable/disable HW learning net/eth.c: Add function to validate a MAC address drivers/net/vsc9953: Add commands to manipulate the FDB for VSC9953 drivers/net/vsc9953: Add VLAN commands for VSC9953 drivers/net/vsc9953: Add command for shared/private VLAN learning drivers/net/vsc9953: Add commands for VLAN ingress filtering drivers/net/vsc9953: Add GPL-2.0+ SPDX-License-Identifier
This set with updated patches are applied to fsl-qoriq master, awaiting upstream.
[PATCH v4 11/16] common/env_flags.c: Add function to validate a MAC address - function eth_validate_ethaddr_str() has been moved to common/env_flags.c and its header to include/env_flags.h; - patch desription updated; [PATCH v4 12/16] drivers/net/vsc9953: Add commands to manipulate the FDB for VSC9953 - eth_validate_ethaddr_str() is now declared in include/env_flags.h instead of include/net.h so we have to include net.h instead of env_flags.h;
York
participants (3)
-
Codrin Ciubotariu
-
Joe Hershberger
-
York Sun