Merge branch 'next' of https://source.denx.de/u-boot/custodians/u-boot-net into next
- Various DSA additions - bootp: fix for VCI string - tsec: support for promiscuous mode - add Aspeed MDIO driver
This commit is contained in:
commit
5a24e12f13
@ -14,6 +14,81 @@
|
||||
enet1-sgmii-phy = &sgmii_phy1;
|
||||
spi0 = &qspi;
|
||||
spi1 = &dspi1;
|
||||
ethernet0 = &enet0;
|
||||
ethernet1 = &enet1;
|
||||
ethernet2 = &enet2;
|
||||
ethernet3 = &swp2;
|
||||
ethernet4 = &swp3;
|
||||
ethernet5 = &swp4;
|
||||
ethernet6 = &swp5;
|
||||
};
|
||||
};
|
||||
|
||||
&dspi0 {
|
||||
bus-num = <0>;
|
||||
status = "okay";
|
||||
|
||||
sja1105: ethernet-switch@1 {
|
||||
reg = <0x1>;
|
||||
#address-cells = <1>;
|
||||
#size-cells = <0>;
|
||||
compatible = "nxp,sja1105t";
|
||||
/* 12 MHz */
|
||||
spi-max-frequency = <12000000>;
|
||||
/* Sample data on trailing clock edge */
|
||||
spi-cpha;
|
||||
/* SPI controller settings for SJA1105 timing requirements */
|
||||
fsl,spi-cs-sck-delay = <1000>;
|
||||
fsl,spi-sck-cs-delay = <1000>;
|
||||
|
||||
ports {
|
||||
#address-cells = <1>;
|
||||
#size-cells = <0>;
|
||||
|
||||
swp5: port@0 {
|
||||
/* ETH5 written on chassis */
|
||||
label = "swp5";
|
||||
phy-handle = <&rgmii_phy6>;
|
||||
phy-mode = "rgmii-id";
|
||||
reg = <0>;
|
||||
};
|
||||
|
||||
swp2: port@1 {
|
||||
/* ETH2 written on chassis */
|
||||
label = "swp2";
|
||||
phy-handle = <&rgmii_phy3>;
|
||||
phy-mode = "rgmii-id";
|
||||
reg = <1>;
|
||||
};
|
||||
|
||||
swp3: port@2 {
|
||||
/* ETH3 written on chassis */
|
||||
label = "swp3";
|
||||
phy-handle = <&rgmii_phy4>;
|
||||
phy-mode = "rgmii-id";
|
||||
reg = <2>;
|
||||
};
|
||||
|
||||
swp4: port@3 {
|
||||
/* ETH4 written on chassis */
|
||||
label = "swp4";
|
||||
phy-handle = <&rgmii_phy5>;
|
||||
phy-mode = "rgmii-id";
|
||||
reg = <3>;
|
||||
};
|
||||
|
||||
port@4 {
|
||||
/* Internal port connected to eth2 */
|
||||
ethernet = <&enet2>;
|
||||
phy-mode = "rgmii";
|
||||
reg = <4>;
|
||||
|
||||
fixed-link {
|
||||
speed = <1000>;
|
||||
full-duplex;
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
@ -31,6 +106,17 @@
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
/* RGMII delays added via PCB traces */
|
||||
&enet2 {
|
||||
phy-mode = "rgmii";
|
||||
status = "okay";
|
||||
|
||||
fixed-link {
|
||||
speed = <1000>;
|
||||
full-duplex;
|
||||
};
|
||||
};
|
||||
|
||||
&i2c0 {
|
||||
status = "okay";
|
||||
};
|
||||
@ -46,6 +132,23 @@
|
||||
reg = <0x2>;
|
||||
};
|
||||
|
||||
/* BCM5464 quad PHY */
|
||||
rgmii_phy3: ethernet-phy@3 {
|
||||
reg = <0x3>;
|
||||
};
|
||||
|
||||
rgmii_phy4: ethernet-phy@4 {
|
||||
reg = <0x4>;
|
||||
};
|
||||
|
||||
rgmii_phy5: ethernet-phy@5 {
|
||||
reg = <0x5>;
|
||||
};
|
||||
|
||||
rgmii_phy6: ethernet-phy@6 {
|
||||
reg = <0x6>;
|
||||
};
|
||||
|
||||
/* SGMII PCS for enet0 */
|
||||
tbi0: tbi-phy@1f {
|
||||
reg = <0x1f>;
|
||||
|
@ -550,7 +550,10 @@ static int label_boot(struct pxe_context *ctx, struct pxe_label *label)
|
||||
* Scenario 2: If there is an fdt_addr specified, pass it along to
|
||||
* bootm, and adjust argc appropriately.
|
||||
*
|
||||
* Scenario 3: fdt blob is not available.
|
||||
* Scenario 3: If there is an fdtcontroladdr specified, pass it along to
|
||||
* bootm, and adjust argc appropriately.
|
||||
*
|
||||
* Scenario 4: fdt blob is not available.
|
||||
*/
|
||||
bootm_argv[3] = env_get("fdt_addr_r");
|
||||
|
||||
@ -652,6 +655,9 @@ static int label_boot(struct pxe_context *ctx, struct pxe_label *label)
|
||||
if (!bootm_argv[3])
|
||||
bootm_argv[3] = env_get("fdt_addr");
|
||||
|
||||
if (!bootm_argv[3])
|
||||
bootm_argv[3] = env_get("fdtcontroladdr");
|
||||
|
||||
if (bootm_argv[3]) {
|
||||
if (!bootm_argv[2])
|
||||
bootm_argv[2] = "-";
|
||||
|
@ -51,8 +51,11 @@ CONFIG_SPI_FLASH_DATAFLASH=y
|
||||
CONFIG_PHY_ATHEROS=y
|
||||
CONFIG_PHY_BROADCOM=y
|
||||
CONFIG_PHY_FIXED=y
|
||||
CONFIG_NET_RANDOM_ETHADDR=y
|
||||
CONFIG_DM_ETH=y
|
||||
CONFIG_DM_MDIO=y
|
||||
CONFIG_DM_DSA=y
|
||||
CONFIG_SJA1105=y
|
||||
CONFIG_PHY_GIGE=y
|
||||
CONFIG_MII=y
|
||||
CONFIG_TSEC_ENET=y
|
||||
|
@ -66,8 +66,11 @@ CONFIG_SPI_FLASH_DATAFLASH=y
|
||||
CONFIG_PHY_ATHEROS=y
|
||||
CONFIG_PHY_BROADCOM=y
|
||||
CONFIG_PHY_FIXED=y
|
||||
CONFIG_NET_RANDOM_ETHADDR=y
|
||||
CONFIG_DM_ETH=y
|
||||
CONFIG_DM_MDIO=y
|
||||
CONFIG_DM_DSA=y
|
||||
CONFIG_SJA1105=y
|
||||
CONFIG_PHY_GIGE=y
|
||||
CONFIG_MII=y
|
||||
CONFIG_TSEC_ENET=y
|
||||
|
@ -8,7 +8,6 @@ CONFIG_PINE64_DT_SELECTION=y
|
||||
# CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set
|
||||
CONFIG_OF_LIST="sun50i-a64-pine64 sun50i-a64-pine64-plus"
|
||||
CONFIG_PHY_REALTEK=y
|
||||
CONFIG_RTL8211E_PINE64_GIGABIT_FIX=y
|
||||
CONFIG_SUN8I_EMAC=y
|
||||
CONFIG_USB_EHCI_HCD=y
|
||||
CONFIG_USB_OHCI_HCD=y
|
||||
|
@ -155,3 +155,15 @@ bool ofnode_phy_is_fixed_link(ofnode eth_node, ofnode *phy_node)
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ofnode_eth_uses_inband_aneg(ofnode eth_node)
|
||||
{
|
||||
bool inband_aneg = false;
|
||||
const char *managed;
|
||||
|
||||
managed = ofnode_read_string(eth_node, "managed");
|
||||
if (managed && !strcmp(managed, "in-band-status"))
|
||||
inband_aneg = true;
|
||||
|
||||
return inband_aneg;
|
||||
}
|
||||
|
@ -554,6 +554,22 @@ config RTL8169
|
||||
This driver supports Realtek 8169 series gigabit ethernet family of
|
||||
PCI/PCIe chipsets/adapters.
|
||||
|
||||
config SJA1105
|
||||
bool "NXP SJA1105 Ethernet switch family driver"
|
||||
depends on DM_DSA && DM_SPI
|
||||
select BITREVERSE
|
||||
help
|
||||
This is the driver for the NXP SJA1105 automotive Ethernet switch
|
||||
family. These are 5-port devices and are managed over an SPI
|
||||
interface. Probing is handled based on OF bindings. The driver
|
||||
supports the following revisions:
|
||||
- SJA1105E (Gen. 1, No TT-Ethernet)
|
||||
- SJA1105T (Gen. 1, TT-Ethernet)
|
||||
- SJA1105P (Gen. 2, No SGMII, No TT-Ethernet)
|
||||
- SJA1105Q (Gen. 2, No SGMII, TT-Ethernet)
|
||||
- SJA1105R (Gen. 2, SGMII, No TT-Ethernet)
|
||||
- SJA1105S (Gen. 2, SGMII, TT-Ethernet)
|
||||
|
||||
config SMC911X
|
||||
bool "SMSC LAN911x and LAN921x controller driver"
|
||||
|
||||
@ -835,6 +851,13 @@ config FSL_LS_MDIO
|
||||
This driver supports the MDIO bus found on the Fman 10G Ethernet MACs and
|
||||
on the mEMAC (which supports both Clauses 22 and 45).
|
||||
|
||||
config ASPEED_MDIO
|
||||
bool "Aspeed MDIO interface support"
|
||||
depends on DM_MDIO
|
||||
help
|
||||
This driver supports the MDIO bus of Aspeed AST2600 SOC. The driver
|
||||
currently supports Clause 22.
|
||||
|
||||
config MDIO_MUX_MMIOREG
|
||||
bool "MDIO MUX accessed as a MMIO register access"
|
||||
depends on DM_MDIO_MUX
|
||||
|
@ -29,6 +29,7 @@ obj-$(CONFIG_DM_ETH_PHY) += eth-phy-uclass.o
|
||||
obj-$(CONFIG_E1000) += e1000.o
|
||||
obj-$(CONFIG_E1000_SPI) += e1000_spi.o
|
||||
obj-$(CONFIG_EEPRO100) += eepro100.o
|
||||
obj-$(CONFIG_SJA1105) += sja1105.o
|
||||
obj-$(CONFIG_SUN4I_EMAC) += sunxi_emac.o
|
||||
obj-$(CONFIG_SUN8I_EMAC) += sun8i_emac.o
|
||||
obj-$(CONFIG_EP93XX) += ep93xx_eth.o
|
||||
@ -101,3 +102,4 @@ obj-$(CONFIG_HIGMACV300_ETH) += higmacv300.o
|
||||
obj-$(CONFIG_MDIO_SANDBOX) += mdio_sandbox.o
|
||||
obj-$(CONFIG_FSL_ENETC) += fsl_enetc.o fsl_enetc_mdio.o
|
||||
obj-$(CONFIG_FSL_LS_MDIO) += fsl_ls_mdio.o
|
||||
obj-$(CONFIG_ASPEED_MDIO) += aspeed_mdio.o
|
||||
|
128
drivers/net/aspeed_mdio.c
Normal file
128
drivers/net/aspeed_mdio.c
Normal file
@ -0,0 +1,128 @@
|
||||
// SPDX-License-Identifier: GPL-2.0+
|
||||
/*
|
||||
* Aspeed MDIO driver
|
||||
*
|
||||
* (C) Copyright 2021 Aspeed Technology Inc.
|
||||
*
|
||||
* This file is inspired from the Linux kernel driver drivers/net/phy/mdio-aspeed.c
|
||||
*/
|
||||
|
||||
#include <common.h>
|
||||
#include <dm.h>
|
||||
#include <log.h>
|
||||
#include <miiphy.h>
|
||||
#include <net.h>
|
||||
#include <reset.h>
|
||||
#include <linux/bitops.h>
|
||||
#include <linux/bitfield.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/iopoll.h>
|
||||
|
||||
#define ASPEED_MDIO_CTRL 0x0
|
||||
#define ASPEED_MDIO_CTRL_FIRE BIT(31)
|
||||
#define ASPEED_MDIO_CTRL_ST BIT(28)
|
||||
#define ASPEED_MDIO_CTRL_ST_C45 0
|
||||
#define ASPEED_MDIO_CTRL_ST_C22 1
|
||||
#define ASPEED_MDIO_CTRL_OP GENMASK(27, 26)
|
||||
#define MDIO_C22_OP_WRITE 0b01
|
||||
#define MDIO_C22_OP_READ 0b10
|
||||
#define ASPEED_MDIO_CTRL_PHYAD GENMASK(25, 21)
|
||||
#define ASPEED_MDIO_CTRL_REGAD GENMASK(20, 16)
|
||||
#define ASPEED_MDIO_CTRL_MIIWDATA GENMASK(15, 0)
|
||||
|
||||
#define ASPEED_MDIO_DATA 0x4
|
||||
#define ASPEED_MDIO_DATA_MDC_THRES GENMASK(31, 24)
|
||||
#define ASPEED_MDIO_DATA_MDIO_EDGE BIT(23)
|
||||
#define ASPEED_MDIO_DATA_MDIO_LATCH GENMASK(22, 20)
|
||||
#define ASPEED_MDIO_DATA_IDLE BIT(16)
|
||||
#define ASPEED_MDIO_DATA_MIIRDATA GENMASK(15, 0)
|
||||
|
||||
#define ASPEED_MDIO_TIMEOUT_US 1000
|
||||
|
||||
struct aspeed_mdio_priv {
|
||||
void *base;
|
||||
};
|
||||
|
||||
static int aspeed_mdio_read(struct udevice *mdio_dev, int addr, int devad, int reg)
|
||||
{
|
||||
struct aspeed_mdio_priv *priv = dev_get_priv(mdio_dev);
|
||||
u32 ctrl;
|
||||
u32 data;
|
||||
int rc;
|
||||
|
||||
if (devad != MDIO_DEVAD_NONE)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
ctrl = ASPEED_MDIO_CTRL_FIRE
|
||||
| FIELD_PREP(ASPEED_MDIO_CTRL_ST, ASPEED_MDIO_CTRL_ST_C22)
|
||||
| FIELD_PREP(ASPEED_MDIO_CTRL_OP, MDIO_C22_OP_READ)
|
||||
| FIELD_PREP(ASPEED_MDIO_CTRL_PHYAD, addr)
|
||||
| FIELD_PREP(ASPEED_MDIO_CTRL_REGAD, reg);
|
||||
|
||||
writel(ctrl, priv->base + ASPEED_MDIO_CTRL);
|
||||
|
||||
rc = readl_poll_timeout(priv->base + ASPEED_MDIO_DATA, data,
|
||||
data & ASPEED_MDIO_DATA_IDLE,
|
||||
ASPEED_MDIO_TIMEOUT_US);
|
||||
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
|
||||
return FIELD_GET(ASPEED_MDIO_DATA_MIIRDATA, data);
|
||||
}
|
||||
|
||||
static int aspeed_mdio_write(struct udevice *mdio_dev, int addr, int devad, int reg, u16 val)
|
||||
{
|
||||
struct aspeed_mdio_priv *priv = dev_get_priv(mdio_dev);
|
||||
u32 ctrl;
|
||||
|
||||
if (devad != MDIO_DEVAD_NONE)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
ctrl = ASPEED_MDIO_CTRL_FIRE
|
||||
| FIELD_PREP(ASPEED_MDIO_CTRL_ST, ASPEED_MDIO_CTRL_ST_C22)
|
||||
| FIELD_PREP(ASPEED_MDIO_CTRL_OP, MDIO_C22_OP_WRITE)
|
||||
| FIELD_PREP(ASPEED_MDIO_CTRL_PHYAD, addr)
|
||||
| FIELD_PREP(ASPEED_MDIO_CTRL_REGAD, reg)
|
||||
| FIELD_PREP(ASPEED_MDIO_CTRL_MIIWDATA, val);
|
||||
|
||||
writel(ctrl, priv->base + ASPEED_MDIO_CTRL);
|
||||
|
||||
return readl_poll_timeout(priv->base + ASPEED_MDIO_CTRL, ctrl,
|
||||
!(ctrl & ASPEED_MDIO_CTRL_FIRE),
|
||||
ASPEED_MDIO_TIMEOUT_US);
|
||||
}
|
||||
|
||||
static const struct mdio_ops aspeed_mdio_ops = {
|
||||
.read = aspeed_mdio_read,
|
||||
.write = aspeed_mdio_write,
|
||||
};
|
||||
|
||||
static int aspeed_mdio_probe(struct udevice *dev)
|
||||
{
|
||||
struct aspeed_mdio_priv *priv = dev_get_priv(dev);
|
||||
struct reset_ctl reset_ctl;
|
||||
int ret = 0;
|
||||
|
||||
priv->base = dev_read_addr_ptr(dev);
|
||||
|
||||
ret = reset_get_by_index(dev, 0, &reset_ctl);
|
||||
reset_deassert(&reset_ctl);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const struct udevice_id aspeed_mdio_ids[] = {
|
||||
{ .compatible = "aspeed,ast2600-mdio" },
|
||||
{ }
|
||||
};
|
||||
|
||||
U_BOOT_DRIVER(aspeed_mdio) = {
|
||||
.name = "aspeed_mdio",
|
||||
.id = UCLASS_MDIO,
|
||||
.of_match = aspeed_mdio_ids,
|
||||
.probe = aspeed_mdio_probe,
|
||||
.ops = &aspeed_mdio_ops,
|
||||
.plat_auto = sizeof(struct mdio_perdev_priv),
|
||||
.priv_auto = sizeof(struct aspeed_mdio_priv),
|
||||
};
|
@ -272,7 +272,7 @@ struct fec_priv {
|
||||
struct clk clk_ref;
|
||||
struct clk clk_ptp;
|
||||
u32 clk_rate;
|
||||
char promisc;
|
||||
bool promisc;
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -16,6 +16,7 @@
|
||||
*/
|
||||
|
||||
#include <dm/device_compat.h>
|
||||
#include <dm/of_extra.h>
|
||||
#include <linux/delay.h>
|
||||
#include <net/dsa.h>
|
||||
#include <asm/io.h>
|
||||
@ -210,17 +211,14 @@ static int felix_init_sxgmii(struct mii_dev *imdio, int pidx)
|
||||
static void felix_start_pcs(struct udevice *dev, int port,
|
||||
struct phy_device *phy, struct mii_dev *imdio)
|
||||
{
|
||||
bool autoneg = true;
|
||||
|
||||
if (phy->phy_id == PHY_FIXED_ID ||
|
||||
phy->interface == PHY_INTERFACE_MODE_2500BASEX)
|
||||
autoneg = false;
|
||||
ofnode node = dsa_port_get_ofnode(dev, port);
|
||||
bool inband_an = ofnode_eth_uses_inband_aneg(node);
|
||||
|
||||
switch (phy->interface) {
|
||||
case PHY_INTERFACE_MODE_SGMII:
|
||||
case PHY_INTERFACE_MODE_2500BASEX:
|
||||
case PHY_INTERFACE_MODE_QSGMII:
|
||||
felix_init_sgmii(imdio, port, autoneg);
|
||||
felix_init_sgmii(imdio, port, inband_an);
|
||||
break;
|
||||
case PHY_INTERFACE_MODE_10GBASER:
|
||||
case PHY_INTERFACE_MODE_USXGMII:
|
||||
|
@ -214,16 +214,6 @@ config PHY_NXP_C45_TJA11XX
|
||||
config PHY_REALTEK
|
||||
bool "Realtek Ethernet PHYs support"
|
||||
|
||||
config RTL8211E_PINE64_GIGABIT_FIX
|
||||
bool "Fix gigabit throughput on some Pine64+ models"
|
||||
depends on PHY_REALTEK
|
||||
help
|
||||
Configure the Realtek RTL8211E found on some Pine64+ models differently to
|
||||
fix throughput on Gigabit links, turning off all internal delays in the
|
||||
process. The settings that this touches are not documented in the CONFREG
|
||||
section of the RTL8211E datasheet, but come from Realtek by way of the
|
||||
Pine64 engineering team.
|
||||
|
||||
config RTL8211X_PHY_FORCE_MASTER
|
||||
bool "Ethernet PHY RTL8211x: force 1000BASE-T master mode"
|
||||
depends on PHY_REALTEK
|
||||
|
@ -19,6 +19,7 @@
|
||||
/* Microsemi PHY ID's */
|
||||
#define PHY_ID_VSC8530 0x00070560
|
||||
#define PHY_ID_VSC8531 0x00070570
|
||||
#define PHY_ID_VSC8502 0x00070630
|
||||
#define PHY_ID_VSC8540 0x00070760
|
||||
#define PHY_ID_VSC8541 0x00070770
|
||||
#define PHY_ID_VSC8574 0x000704a0
|
||||
@ -1513,6 +1514,50 @@ static int vsc8584_config(struct phy_device *phydev)
|
||||
return vsc8584_config_init(phydev);
|
||||
}
|
||||
|
||||
static int vsc8502_config(struct phy_device *phydev)
|
||||
{
|
||||
bool rgmii_rx_delay = false, rgmii_tx_delay = false;
|
||||
u16 reg = 0;
|
||||
int ret;
|
||||
|
||||
/* Assume nothing needs to be done for the default GMII/MII mode */
|
||||
if (!phy_interface_is_rgmii(phydev))
|
||||
return 0;
|
||||
|
||||
/* Set Extended PHY Control 1 register to RGMII */
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MSCC_PHY_EXT_PHY_CNTL_1_REG,
|
||||
BIT(13) | BIT(12));
|
||||
|
||||
/* Soft reset required after changing PHY mode from the default
|
||||
* of GMII/MII
|
||||
*/
|
||||
ret = mscc_phy_soft_reset(phydev);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
if (phydev->interface == PHY_INTERFACE_MODE_RGMII_RXID ||
|
||||
phydev->interface == PHY_INTERFACE_MODE_RGMII_ID)
|
||||
rgmii_rx_delay = true;
|
||||
if (phydev->interface == PHY_INTERFACE_MODE_RGMII_TXID ||
|
||||
phydev->interface == PHY_INTERFACE_MODE_RGMII_ID)
|
||||
rgmii_tx_delay = true;
|
||||
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MSCC_EXT_PAGE_ACCESS,
|
||||
MSCC_PHY_PAGE_EXT2);
|
||||
|
||||
if (rgmii_rx_delay)
|
||||
reg |= VSC_PHY_RGMII_DELAY_2000_PS << RGMII_RX_CLK_DELAY_POS;
|
||||
if (rgmii_tx_delay)
|
||||
reg |= VSC_PHY_RGMII_DELAY_2000_PS << RGMII_TX_CLK_DELAY_POS;
|
||||
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MSCC_PHY_RGMII_CNTL_REG, reg);
|
||||
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MSCC_EXT_PAGE_ACCESS,
|
||||
MSCC_PHY_PAGE_STD);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct phy_driver VSC8530_driver = {
|
||||
.name = "Microsemi VSC8530",
|
||||
.uid = PHY_ID_VSC8530,
|
||||
@ -1533,6 +1578,16 @@ static struct phy_driver VSC8531_driver = {
|
||||
.shutdown = &genphy_shutdown,
|
||||
};
|
||||
|
||||
static struct phy_driver VSC8502_driver = {
|
||||
.name = "Microsemi VSC8502",
|
||||
.uid = PHY_ID_VSC8502,
|
||||
.mask = 0x000ffff0,
|
||||
.features = PHY_GBIT_FEATURES,
|
||||
.config = &vsc8502_config,
|
||||
.startup = &mscc_startup,
|
||||
.shutdown = &genphy_shutdown,
|
||||
};
|
||||
|
||||
static struct phy_driver VSC8540_driver = {
|
||||
.name = "Microsemi VSC8540",
|
||||
.uid = PHY_ID_VSC8540,
|
||||
@ -1577,6 +1632,7 @@ int phy_mscc_init(void)
|
||||
{
|
||||
phy_register(&VSC8530_driver);
|
||||
phy_register(&VSC8531_driver);
|
||||
phy_register(&VSC8502_driver);
|
||||
phy_register(&VSC8540_driver);
|
||||
phy_register(&VSC8541_driver);
|
||||
phy_register(&VSC8574_driver);
|
||||
|
@ -12,7 +12,6 @@
|
||||
#include <linux/delay.h>
|
||||
|
||||
#define PHY_RTL8211x_FORCE_MASTER BIT(1)
|
||||
#define PHY_RTL8211E_PINE64_GIGABIT_FIX BIT(2)
|
||||
#define PHY_RTL8211F_FORCE_EEE_RXC_ON BIT(3)
|
||||
#define PHY_RTL8201F_S700_RMII_TIMINGS BIT(4)
|
||||
|
||||
@ -49,10 +48,10 @@
|
||||
#define MIIM_RTL8211F_PHYSTAT_SPDDONE 0x0800
|
||||
#define MIIM_RTL8211F_PHYSTAT_LINK 0x0004
|
||||
|
||||
#define MIIM_RTL8211E_CONFREG 0x1c
|
||||
#define MIIM_RTL8211E_CONFREG_TXD 0x0002
|
||||
#define MIIM_RTL8211E_CONFREG_RXD 0x0004
|
||||
#define MIIM_RTL8211E_CONFREG_MAGIC 0xb400 /* Undocumented */
|
||||
#define MIIM_RTL8211E_CONFREG 0x1c
|
||||
#define MIIM_RTL8211E_CTRL_DELAY BIT(13)
|
||||
#define MIIM_RTL8211E_TX_DELAY BIT(12)
|
||||
#define MIIM_RTL8211E_RX_DELAY BIT(11)
|
||||
|
||||
#define MIIM_RTL8211E_EXT_PAGE_SELECT 0x1e
|
||||
|
||||
@ -108,10 +107,6 @@ static int rtl8211b_probe(struct phy_device *phydev)
|
||||
|
||||
static int rtl8211e_probe(struct phy_device *phydev)
|
||||
{
|
||||
#ifdef CONFIG_RTL8211E_PINE64_GIGABIT_FIX
|
||||
phydev->flags |= PHY_RTL8211E_PINE64_GIGABIT_FIX;
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -154,22 +149,6 @@ static int rtl8211x_config(struct phy_device *phydev)
|
||||
reg |= MIIM_RTL8211x_CTRL1000T_MASTER;
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MII_CTRL1000, reg);
|
||||
}
|
||||
if (phydev->flags & PHY_RTL8211E_PINE64_GIGABIT_FIX) {
|
||||
unsigned int reg;
|
||||
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211F_PAGE_SELECT,
|
||||
7);
|
||||
phy_write(phydev, MDIO_DEVAD_NONE,
|
||||
MIIM_RTL8211E_EXT_PAGE_SELECT, 0xa4);
|
||||
reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211E_CONFREG);
|
||||
/* Ensure both internal delays are turned off */
|
||||
reg &= ~(MIIM_RTL8211E_CONFREG_TXD | MIIM_RTL8211E_CONFREG_RXD);
|
||||
/* Flip the magic undocumented bits */
|
||||
reg |= MIIM_RTL8211E_CONFREG_MAGIC;
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211E_CONFREG, reg);
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211F_PAGE_SELECT,
|
||||
0);
|
||||
}
|
||||
/* read interrupt status just to clear it */
|
||||
phy_read(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211x_PHY_INER);
|
||||
|
||||
@ -201,6 +180,44 @@ static int rtl8201f_config(struct phy_device *phydev)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rtl8211e_config(struct phy_device *phydev)
|
||||
{
|
||||
int reg, val;
|
||||
|
||||
/* enable TX/RX delay for rgmii-* modes, and disable them for rgmii. */
|
||||
switch (phydev->interface) {
|
||||
case PHY_INTERFACE_MODE_RGMII:
|
||||
val = MIIM_RTL8211E_CTRL_DELAY;
|
||||
break;
|
||||
case PHY_INTERFACE_MODE_RGMII_ID:
|
||||
val = MIIM_RTL8211E_CTRL_DELAY | MIIM_RTL8211E_TX_DELAY |
|
||||
MIIM_RTL8211E_RX_DELAY;
|
||||
break;
|
||||
case PHY_INTERFACE_MODE_RGMII_RXID:
|
||||
val = MIIM_RTL8211E_CTRL_DELAY | MIIM_RTL8211E_RX_DELAY;
|
||||
break;
|
||||
case PHY_INTERFACE_MODE_RGMII_TXID:
|
||||
val = MIIM_RTL8211E_CTRL_DELAY | MIIM_RTL8211E_TX_DELAY;
|
||||
break;
|
||||
default: /* the rest of the modes imply leaving delays as is. */
|
||||
goto default_delay;
|
||||
}
|
||||
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211F_PAGE_SELECT, 7);
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211E_EXT_PAGE_SELECT, 0xa4);
|
||||
|
||||
reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211E_CONFREG);
|
||||
reg &= ~(MIIM_RTL8211E_TX_DELAY | MIIM_RTL8211E_RX_DELAY);
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211E_CONFREG, reg | val);
|
||||
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211F_PAGE_SELECT, 0);
|
||||
|
||||
default_delay:
|
||||
genphy_config_aneg(phydev);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rtl8211f_config(struct phy_device *phydev)
|
||||
{
|
||||
u16 reg;
|
||||
@ -410,7 +427,7 @@ static struct phy_driver RTL8211E_driver = {
|
||||
.mask = 0xffffff,
|
||||
.features = PHY_GBIT_FEATURES,
|
||||
.probe = &rtl8211e_probe,
|
||||
.config = &rtl8211x_config,
|
||||
.config = &rtl8211e_config,
|
||||
.startup = &rtl8211e_startup,
|
||||
.shutdown = &genphy_shutdown,
|
||||
};
|
||||
|
3376
drivers/net/sja1105.c
Normal file
3376
drivers/net/sja1105.c
Normal file
File diff suppressed because it is too large
Load Diff
@ -156,6 +156,19 @@ static int tsec_mcast_addr(struct udevice *dev, const u8 *mcast_mac, int join)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int __maybe_unused tsec_set_promisc(struct udevice *dev, bool enable)
|
||||
{
|
||||
struct tsec_private *priv = dev_get_priv(dev);
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
|
||||
if (enable)
|
||||
setbits_be32(®s->rctrl, RCTRL_PROM);
|
||||
else
|
||||
clrbits_be32(®s->rctrl, RCTRL_PROM);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Initialized required registers to appropriate values, zeroing
|
||||
* those we don't care about (unless zero is bad, in which case,
|
||||
@ -186,8 +199,6 @@ static void init_registers(struct tsec __iomem *regs)
|
||||
out_be32(®s->hash.gaddr6, 0);
|
||||
out_be32(®s->hash.gaddr7, 0);
|
||||
|
||||
out_be32(®s->rctrl, 0x00000000);
|
||||
|
||||
/* Init RMON mib registers */
|
||||
memset((void *)®s->rmon, 0, sizeof(regs->rmon));
|
||||
|
||||
@ -432,7 +443,7 @@ static void tsec_halt(struct udevice *dev)
|
||||
* of the eTSEC port initialization sequence,
|
||||
* the eTSEC Rx logic may not be properly initialized.
|
||||
*/
|
||||
void redundant_init(struct tsec_private *priv)
|
||||
static void redundant_init(struct tsec_private *priv)
|
||||
{
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
uint t, count = 0;
|
||||
@ -454,7 +465,7 @@ void redundant_init(struct tsec_private *priv)
|
||||
0x71, 0x72};
|
||||
|
||||
/* Enable promiscuous mode */
|
||||
setbits_be32(®s->rctrl, 0x8);
|
||||
setbits_be32(®s->rctrl, RCTRL_PROM);
|
||||
/* Enable loopback mode */
|
||||
setbits_be32(®s->maccfg1, MACCFG1_LOOPBACK);
|
||||
/* Enable transmit and receive */
|
||||
@ -506,7 +517,7 @@ void redundant_init(struct tsec_private *priv)
|
||||
if (fail)
|
||||
panic("eTSEC init fail!\n");
|
||||
/* Disable promiscuous mode */
|
||||
clrbits_be32(®s->rctrl, 0x8);
|
||||
clrbits_be32(®s->rctrl, RCTRL_PROM);
|
||||
/* Disable loopback mode */
|
||||
clrbits_be32(®s->maccfg1, MACCFG1_LOOPBACK);
|
||||
}
|
||||
@ -932,6 +943,7 @@ static const struct eth_ops tsec_ops = {
|
||||
.free_pkt = tsec_free_pkt,
|
||||
.stop = tsec_halt,
|
||||
.mcast = tsec_mcast_addr,
|
||||
.set_promisc = tsec_set_promisc,
|
||||
};
|
||||
|
||||
static struct tsec_data etsec2_data = {
|
||||
|
@ -114,4 +114,18 @@ int ofnode_decode_memory_region(ofnode config_node, const char *mem_type,
|
||||
*/
|
||||
bool ofnode_phy_is_fixed_link(ofnode eth_node, ofnode *phy_node);
|
||||
|
||||
/**
|
||||
* ofnode_eth_uses_inband_aneg() - Detect whether MAC should use in-band autoneg
|
||||
*
|
||||
* This function detects whether the Ethernet controller should use IEEE 802.3
|
||||
* clause 37 in-band autonegotiation for serial protocols such as 1000base-x,
|
||||
* SGMII, USXGMII, etc. The property is relevant when the Ethernet controller
|
||||
* is connected to an on-board PHY or an SFP cage, and is not relevant when it
|
||||
* has a fixed link (in that case, in-band autoneg should not be used).
|
||||
*
|
||||
* @param eth_node ofnode belonging to the Ethernet controller
|
||||
* @return true if in-band autoneg should be used, false otherwise
|
||||
*/
|
||||
bool ofnode_eth_uses_inband_aneg(ofnode eth_node);
|
||||
|
||||
#endif
|
||||
|
26
include/linux/if_vlan.h
Normal file
26
include/linux/if_vlan.h
Normal file
@ -0,0 +1,26 @@
|
||||
/* SPDX-License-Identifier: GPL-2.0-or-later */
|
||||
/*
|
||||
* VLAN An implementation of 802.1Q VLAN tagging.
|
||||
*
|
||||
* Authors: Ben Greear <greearb@candelatech.com>
|
||||
*/
|
||||
#ifndef _LINUX_IF_VLAN_H_
|
||||
#define _LINUX_IF_VLAN_H_
|
||||
|
||||
/**
|
||||
* struct vlan_ethhdr - vlan ethernet header (ethhdr + vlan_hdr)
|
||||
* @h_dest: destination ethernet address
|
||||
* @h_source: source ethernet address
|
||||
* @h_vlan_proto: ethernet protocol
|
||||
* @h_vlan_TCI: priority and VLAN ID
|
||||
* @h_vlan_encapsulated_proto: packet type ID or len
|
||||
*/
|
||||
struct vlan_ethhdr {
|
||||
unsigned char h_dest[ETH_ALEN];
|
||||
unsigned char h_source[ETH_ALEN];
|
||||
__be16 h_vlan_proto;
|
||||
__be16 h_vlan_TCI;
|
||||
__be16 h_vlan_encapsulated_proto;
|
||||
};
|
||||
|
||||
#endif /* !(_LINUX_IF_VLAN_H_) */
|
@ -6,6 +6,7 @@
|
||||
#ifndef __DSA_H__
|
||||
#define __DSA_H__
|
||||
|
||||
#include <dm/ofnode.h>
|
||||
#include <phy.h>
|
||||
#include <net.h>
|
||||
|
||||
@ -145,6 +146,17 @@ int dsa_set_tagging(struct udevice *dev, ushort headroom, ushort tailroom);
|
||||
*/
|
||||
struct udevice *dsa_get_master(struct udevice *dev);
|
||||
|
||||
/**
|
||||
* dsa_port_get_ofnode() - Return a reference to the given port's OF node
|
||||
*
|
||||
* Can be called at driver probe time or later.
|
||||
*
|
||||
* @dev: DSA switch udevice pointer
|
||||
* @port: Port index
|
||||
* @return OF node reference if OK, NULL on error
|
||||
*/
|
||||
ofnode dsa_port_get_ofnode(struct udevice *dev, int port);
|
||||
|
||||
/**
|
||||
* dsa_port_get_pdata() - Helper that returns the platdata of an active
|
||||
* (non-CPU) DSA port device.
|
||||
|
@ -122,6 +122,8 @@
|
||||
#define ECNTRL_REDUCED_MII_MODE 0x00000004
|
||||
#define ECNTRL_SGMII_MODE 0x00000002
|
||||
|
||||
#define RCTRL_PROM 0x00000008
|
||||
|
||||
#ifndef CONFIG_SYS_TBIPA_VALUE
|
||||
# define CONFIG_SYS_TBIPA_VALUE 0x1f
|
||||
#endif
|
||||
|
@ -647,7 +647,7 @@ static int bootp_extended(u8 *e)
|
||||
*e++ = (576 - 312 + OPT_FIELD_SIZE) & 0xff;
|
||||
#endif
|
||||
|
||||
add_vci(e);
|
||||
e = add_vci(e);
|
||||
|
||||
#if defined(CONFIG_BOOTP_SUBNETMASK)
|
||||
*e++ = 1; /* Subnet mask request */
|
||||
|
@ -44,6 +44,26 @@ int dsa_set_tagging(struct udevice *dev, ushort headroom, ushort tailroom)
|
||||
return 0;
|
||||
}
|
||||
|
||||
ofnode dsa_port_get_ofnode(struct udevice *dev, int port)
|
||||
{
|
||||
struct dsa_pdata *pdata = dev_get_uclass_plat(dev);
|
||||
struct dsa_port_pdata *port_pdata;
|
||||
struct udevice *pdev;
|
||||
|
||||
if (port == pdata->cpu_port)
|
||||
return pdata->cpu_port_node;
|
||||
|
||||
for (device_find_first_child(dev, &pdev);
|
||||
pdev;
|
||||
device_find_next_child(&pdev)) {
|
||||
port_pdata = dev_get_parent_plat(pdev);
|
||||
if (port_pdata->index == port)
|
||||
return dev_ofnode(pdev);
|
||||
}
|
||||
|
||||
return ofnode_null();
|
||||
}
|
||||
|
||||
/* returns the DSA master Ethernet device */
|
||||
struct udevice *dsa_get_master(struct udevice *dev)
|
||||
{
|
||||
@ -250,7 +270,7 @@ static void dsa_port_set_hwaddr(struct udevice *pdev, struct udevice *master)
|
||||
struct eth_ops *eth_ops = eth_get_ops(master);
|
||||
|
||||
if (eth_ops->set_promisc)
|
||||
eth_ops->set_promisc(master, 1);
|
||||
eth_ops->set_promisc(master, true);
|
||||
|
||||
return;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user