Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0
0002 /* Copyright 2021 NXP
0003  */
0004 #include <linux/pcs/pcs-xpcs.h>
0005 #include "pcs-xpcs.h"
0006 
0007 /* LANE_DRIVER1_0 register */
0008 #define SJA1110_LANE_DRIVER1_0      0x8038
0009 #define SJA1110_TXDRV(x)        (((x) << 12) & GENMASK(14, 12))
0010 
0011 /* LANE_DRIVER2_0 register */
0012 #define SJA1110_LANE_DRIVER2_0      0x803a
0013 #define SJA1110_TXDRVTRIM_LSB(x)    ((x) & GENMASK_ULL(15, 0))
0014 
0015 /* LANE_DRIVER2_1 register */
0016 #define SJA1110_LANE_DRIVER2_1      0x803b
0017 #define SJA1110_LANE_DRIVER2_1_RSV  BIT(9)
0018 #define SJA1110_TXDRVTRIM_MSB(x)    (((x) & GENMASK_ULL(23, 16)) >> 16)
0019 
0020 /* LANE_TRIM register */
0021 #define SJA1110_LANE_TRIM       0x8040
0022 #define SJA1110_TXTEN           BIT(11)
0023 #define SJA1110_TXRTRIM(x)      (((x) << 8) & GENMASK(10, 8))
0024 #define SJA1110_TXPLL_BWSEL     BIT(7)
0025 #define SJA1110_RXTEN           BIT(6)
0026 #define SJA1110_RXRTRIM(x)      (((x) << 3) & GENMASK(5, 3))
0027 #define SJA1110_CDR_GAIN        BIT(2)
0028 #define SJA1110_ACCOUPLE_RXVCM_EN   BIT(0)
0029 
0030 /* LANE_DATAPATH_1 register */
0031 #define SJA1110_LANE_DATAPATH_1     0x8037
0032 
0033 /* POWERDOWN_ENABLE register */
0034 #define SJA1110_POWERDOWN_ENABLE    0x8041
0035 #define SJA1110_TXPLL_PD        BIT(12)
0036 #define SJA1110_TXPD            BIT(11)
0037 #define SJA1110_RXPKDETEN       BIT(10)
0038 #define SJA1110_RXCH_PD         BIT(9)
0039 #define SJA1110_RXBIAS_PD       BIT(8)
0040 #define SJA1110_RESET_SER_EN        BIT(7)
0041 #define SJA1110_RESET_SER       BIT(6)
0042 #define SJA1110_RESET_DES       BIT(5)
0043 #define SJA1110_RCVEN           BIT(4)
0044 
0045 /* RXPLL_CTRL0 register */
0046 #define SJA1110_RXPLL_CTRL0     0x8065
0047 #define SJA1110_RXPLL_FBDIV(x)      (((x) << 2) & GENMASK(9, 2))
0048 
0049 /* RXPLL_CTRL1 register */
0050 #define SJA1110_RXPLL_CTRL1     0x8066
0051 #define SJA1110_RXPLL_REFDIV(x)     ((x) & GENMASK(4, 0))
0052 
0053 /* TXPLL_CTRL0 register */
0054 #define SJA1110_TXPLL_CTRL0     0x806d
0055 #define SJA1110_TXPLL_FBDIV(x)      ((x) & GENMASK(11, 0))
0056 
0057 /* TXPLL_CTRL1 register */
0058 #define SJA1110_TXPLL_CTRL1     0x806e
0059 #define SJA1110_TXPLL_REFDIV(x)     ((x) & GENMASK(5, 0))
0060 
0061 /* RX_DATA_DETECT register */
0062 #define SJA1110_RX_DATA_DETECT      0x8045
0063 
0064 /* RX_CDR_CTLE register */
0065 #define SJA1110_RX_CDR_CTLE     0x8042
0066 
0067 /* In NXP SJA1105, the PCS is integrated with a PMA that has the TX lane
0068  * polarity inverted by default (PLUS is MINUS, MINUS is PLUS). To obtain
0069  * normal non-inverted behavior, the TX lane polarity must be inverted in the
0070  * PCS, via the DIGITAL_CONTROL_2 register.
0071  */
0072 int nxp_sja1105_sgmii_pma_config(struct dw_xpcs *xpcs)
0073 {
0074     return xpcs_write(xpcs, MDIO_MMD_VEND2, DW_VR_MII_DIG_CTRL2,
0075               DW_VR_MII_DIG_CTRL2_TX_POL_INV);
0076 }
0077 
0078 static int nxp_sja1110_pma_config(struct dw_xpcs *xpcs,
0079                   u16 txpll_fbdiv, u16 txpll_refdiv,
0080                   u16 rxpll_fbdiv, u16 rxpll_refdiv,
0081                   u16 rx_cdr_ctle)
0082 {
0083     u16 val;
0084     int ret;
0085 
0086     /* Program TX PLL feedback divider and reference divider settings for
0087      * correct oscillation frequency.
0088      */
0089     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_TXPLL_CTRL0,
0090              SJA1110_TXPLL_FBDIV(txpll_fbdiv));
0091     if (ret < 0)
0092         return ret;
0093 
0094     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_TXPLL_CTRL1,
0095              SJA1110_TXPLL_REFDIV(txpll_refdiv));
0096     if (ret < 0)
0097         return ret;
0098 
0099     /* Program transmitter amplitude and disable amplitude trimming */
0100     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_LANE_DRIVER1_0,
0101              SJA1110_TXDRV(0x5));
0102     if (ret < 0)
0103         return ret;
0104 
0105     val = SJA1110_TXDRVTRIM_LSB(0xffffffull);
0106 
0107     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_LANE_DRIVER2_0, val);
0108     if (ret < 0)
0109         return ret;
0110 
0111     val = SJA1110_TXDRVTRIM_MSB(0xffffffull) | SJA1110_LANE_DRIVER2_1_RSV;
0112 
0113     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_LANE_DRIVER2_1, val);
0114     if (ret < 0)
0115         return ret;
0116 
0117     /* Enable input and output resistor terminations for low BER. */
0118     val = SJA1110_ACCOUPLE_RXVCM_EN | SJA1110_CDR_GAIN |
0119           SJA1110_RXRTRIM(4) | SJA1110_RXTEN | SJA1110_TXPLL_BWSEL |
0120           SJA1110_TXRTRIM(3) | SJA1110_TXTEN;
0121 
0122     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_LANE_TRIM, val);
0123     if (ret < 0)
0124         return ret;
0125 
0126     /* Select PCS as transmitter data source. */
0127     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_LANE_DATAPATH_1, 0);
0128     if (ret < 0)
0129         return ret;
0130 
0131     /* Program RX PLL feedback divider and reference divider for correct
0132      * oscillation frequency.
0133      */
0134     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_RXPLL_CTRL0,
0135              SJA1110_RXPLL_FBDIV(rxpll_fbdiv));
0136     if (ret < 0)
0137         return ret;
0138 
0139     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_RXPLL_CTRL1,
0140              SJA1110_RXPLL_REFDIV(rxpll_refdiv));
0141     if (ret < 0)
0142         return ret;
0143 
0144     /* Program threshold for receiver signal detector.
0145      * Enable control of RXPLL by receiver signal detector to disable RXPLL
0146      * when an input signal is not present.
0147      */
0148     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_RX_DATA_DETECT, 0x0005);
0149     if (ret < 0)
0150         return ret;
0151 
0152     /* Enable TX and RX PLLs and circuits.
0153      * Release reset of PMA to enable data flow to/from PCS.
0154      */
0155     ret = xpcs_read(xpcs, MDIO_MMD_VEND2, SJA1110_POWERDOWN_ENABLE);
0156     if (ret < 0)
0157         return ret;
0158 
0159     val = ret & ~(SJA1110_TXPLL_PD | SJA1110_TXPD | SJA1110_RXCH_PD |
0160               SJA1110_RXBIAS_PD | SJA1110_RESET_SER_EN |
0161               SJA1110_RESET_SER | SJA1110_RESET_DES);
0162     val |= SJA1110_RXPKDETEN | SJA1110_RCVEN;
0163 
0164     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_POWERDOWN_ENABLE, val);
0165     if (ret < 0)
0166         return ret;
0167 
0168     /* Program continuous-time linear equalizer (CTLE) settings. */
0169     ret = xpcs_write(xpcs, MDIO_MMD_VEND2, SJA1110_RX_CDR_CTLE,
0170              rx_cdr_ctle);
0171     if (ret < 0)
0172         return ret;
0173 
0174     return 0;
0175 }
0176 
0177 int nxp_sja1110_sgmii_pma_config(struct dw_xpcs *xpcs)
0178 {
0179     return nxp_sja1110_pma_config(xpcs, 0x19, 0x1, 0x19, 0x1, 0x212a);
0180 }
0181 
0182 int nxp_sja1110_2500basex_pma_config(struct dw_xpcs *xpcs)
0183 {
0184     return nxp_sja1110_pma_config(xpcs, 0x7d, 0x2, 0x7d, 0x2, 0x732a);
0185 }