linux-imx/include/linux/pcs/pcs-xpcs.h
Clark Wang f5d7b7a0ff LF-10639-4 net: pcs: xpcs: add mx95 serdes support
The serdes and pcs in the mx95 chip are closely related.
Both serdes and pcs are accessed through the IMDIO bus.
PCS's clock is provided by serdes' clock. Before accessing the ID register
of PCS, need to lock the access permission by accessing the MAC_ADAPTER
register of serdes, and then check whether the PCS is initialized normally.

This is different from the initialization sequence in the original PCS driver.
Therefore, add xpcs_create_mdiodev_with_phy() function to initialize xpcs
with serdes.

Because the ID of mx95 PCS is the same as the default ID of XPCS,
the initialization function for pma/serdes cannot be added.
In mx95, use the PMA's ID to match xpcs_id.

Signed-off-by: Clark Wang <xiaoning.wang@nxp.com>
Reviewed-by: Wei Fang <wei.fang@nxp.com>
2023-11-22 16:27:47 +08:00

74 lines
2.0 KiB
C

/* SPDX-License-Identifier: GPL-2.0 */
/*
* Copyright (c) 2020 Synopsys, Inc. and/or its affiliates.
* Synopsys DesignWare XPCS helpers
*/
#ifndef __LINUX_PCS_XPCS_H
#define __LINUX_PCS_XPCS_H
#include <linux/phy.h>
#include <linux/phylink.h>
#define NXP_SJA1105_XPCS_ID 0x00000010
#define NXP_SJA1110_XPCS_ID 0x00000020
#define NXP_MX95_XPCS_ID 0x1b3274cd
/* AN mode */
#define DW_AN_C73 1
#define DW_AN_C37_SGMII 2
#define DW_2500BASEX 3
#define DW_AN_C37_1000BASEX 4
#define DW_10GBASER 5
/* device vendor OUI */
#define DW_OUI_WX 0x0018fc80
/* dev_flag */
#define DW_DEV_TXGBE BIT(0)
struct xpcs_id;
struct dw_xpcs {
struct mdio_device *mdiodev;
struct mdio_device *phydev;
const struct xpcs_id *id;
struct phylink_pcs pcs;
phy_interface_t interface;
int dev_flag;
};
#define phylink_pcs_to_xpcs(pl_pcs) container_of((pl_pcs), struct dw_xpcs, pcs)
int xpcs_get_an_mode(struct dw_xpcs *xpcs, phy_interface_t interface);
void xpcs_link_up(struct phylink_pcs *pcs, unsigned int neg_mode,
phy_interface_t interface, int speed, int duplex);
int xpcs_do_config(struct dw_xpcs *xpcs, phy_interface_t interface,
const unsigned long *advertising, unsigned int neg_mode);
void xpcs_get_interfaces(struct dw_xpcs *xpcs, unsigned long *interfaces);
int xpcs_config_eee(struct dw_xpcs *xpcs, int mult_fact_100ns,
int enable);
struct dw_xpcs *xpcs_create_mdiodev(struct mii_bus *bus, int addr,
phy_interface_t interface);
void xpcs_destroy(struct dw_xpcs *xpcs);
#if IS_ENABLED(CONFIG_PCS_XPCS)
struct phylink_pcs *xpcs_create_mdiodev_with_phy(struct mii_bus *bus,
int mdioaddr, int phyaddr,
phy_interface_t interface);
void xpcs_pcs_destroy(struct phylink_pcs *pcs);
#else
static inline struct phylink_pcs *xpcs_create_mdiodev_with_phy(struct mii_bus *bus,
int mdioaddr, int phyaddr,
phy_interface_t interface)
{
return ERR_PTR(-EOPNOTSUPP);
}
static inline void xpcs_pcs_destroy(struct phylink_pcs *pcs)
{
return;
}
#endif /* IS_ENABLED(CONFIG_PCS_XPCS) */
#endif /* __LINUX_PCS_XPCS_H */