1c942fddfSThomas Gleixner // SPDX-License-Identifier: GPL-2.0-or-later 27ad269eaSRoger Chen /** 3d0ea5cbdSJesse Brandeburg * DOC: dwmac-rk.c - Rockchip RK3288 DWMAC specific glue layer 47ad269eaSRoger Chen * 57ad269eaSRoger Chen * Copyright (C) 2014 Chen-Zhi (Roger Chen) 67ad269eaSRoger Chen * 77ad269eaSRoger Chen * Chen-Zhi (Roger Chen) <roger.chen@rock-chips.com> 87ad269eaSRoger Chen */ 97ad269eaSRoger Chen 107ad269eaSRoger Chen #include <linux/stmmac.h> 117ad269eaSRoger Chen #include <linux/bitops.h> 127ad269eaSRoger Chen #include <linux/clk.h> 137ad269eaSRoger Chen #include <linux/phy.h> 147ad269eaSRoger Chen #include <linux/of_net.h> 157ad269eaSRoger Chen #include <linux/gpio.h> 16e0fb4013SJoachim Eastwood #include <linux/module.h> 177ad269eaSRoger Chen #include <linux/of_gpio.h> 187ad269eaSRoger Chen #include <linux/of_device.h> 19e0fb4013SJoachim Eastwood #include <linux/platform_device.h> 207ad269eaSRoger Chen #include <linux/regulator/consumer.h> 217ad269eaSRoger Chen #include <linux/delay.h> 227ad269eaSRoger Chen #include <linux/mfd/syscon.h> 237ad269eaSRoger Chen #include <linux/regmap.h> 24aec3f415SPunit Agrawal #include <linux/pm_runtime.h> 257ad269eaSRoger Chen 26e0fb4013SJoachim Eastwood #include "stmmac_platform.h" 27e0fb4013SJoachim Eastwood 280fb98db1SHeiko Stübner struct rk_priv_data; 290fb98db1SHeiko Stübner struct rk_gmac_ops { 300fb98db1SHeiko Stübner void (*set_to_rgmii)(struct rk_priv_data *bsp_priv, 310fb98db1SHeiko Stübner int tx_delay, int rx_delay); 320fb98db1SHeiko Stübner void (*set_to_rmii)(struct rk_priv_data *bsp_priv); 330fb98db1SHeiko Stübner void (*set_rgmii_speed)(struct rk_priv_data *bsp_priv, int speed); 340fb98db1SHeiko Stübner void (*set_rmii_speed)(struct rk_priv_data *bsp_priv, int speed); 352f2b60a0SDavid Wu void (*set_clock_selection)(struct rk_priv_data *bsp_priv, bool input, 362f2b60a0SDavid Wu bool enable); 37fecd4d7eSDavid Wu void (*integrated_phy_powerup)(struct rk_priv_data *bsp_priv); 380546b224SJohn Keeping bool regs_valid; 393bb3d6b1SDavid Wu u32 regs[]; 400fb98db1SHeiko Stübner }; 410fb98db1SHeiko Stübner 42ea449f7fSSebastian Reichel static const char * const rk_clocks[] = { 43ea449f7fSSebastian Reichel "aclk_mac", "pclk_mac", "mac_clk_tx", "clk_mac_speed", 44ea449f7fSSebastian Reichel }; 45ea449f7fSSebastian Reichel 46ea449f7fSSebastian Reichel static const char * const rk_rmii_clocks[] = { 47ea449f7fSSebastian Reichel "mac_clk_rx", "clk_mac_ref", "clk_mac_refout", 48ea449f7fSSebastian Reichel }; 49ea449f7fSSebastian Reichel 50ea449f7fSSebastian Reichel enum rk_clocks_index { 51ea449f7fSSebastian Reichel RK_ACLK_MAC = 0, 52ea449f7fSSebastian Reichel RK_PCLK_MAC, 53ea449f7fSSebastian Reichel RK_MAC_CLK_TX, 54ea449f7fSSebastian Reichel RK_CLK_MAC_SPEED, 55ea449f7fSSebastian Reichel RK_MAC_CLK_RX, 56ea449f7fSSebastian Reichel RK_CLK_MAC_REF, 57ea449f7fSSebastian Reichel RK_CLK_MAC_REFOUT, 58ea449f7fSSebastian Reichel }; 59ea449f7fSSebastian Reichel 607ad269eaSRoger Chen struct rk_priv_data { 617ad269eaSRoger Chen struct platform_device *pdev; 620c65b2b9SAndrew Lunn phy_interface_t phy_iface; 633bb3d6b1SDavid Wu int id; 642e12f536SRomain Perier struct regulator *regulator; 65229666c1SVincent Palatin bool suspended; 6692c2588fSJoachim Eastwood const struct rk_gmac_ops *ops; 677ad269eaSRoger Chen 687ad269eaSRoger Chen bool clk_enabled; 697ad269eaSRoger Chen bool clock_input; 70fecd4d7eSDavid Wu bool integrated_phy; 717ad269eaSRoger Chen 72ea449f7fSSebastian Reichel struct clk_bulk_data *clks; 73ea449f7fSSebastian Reichel int num_clks; 747ad269eaSRoger Chen struct clk *clk_mac; 75fecd4d7eSDavid Wu struct clk *clk_phy; 76fecd4d7eSDavid Wu 77fecd4d7eSDavid Wu struct reset_control *phy_reset; 787ad269eaSRoger Chen 797ad269eaSRoger Chen int tx_delay; 807ad269eaSRoger Chen int rx_delay; 817ad269eaSRoger Chen 827ad269eaSRoger Chen struct regmap *grf; 832f2b60a0SDavid Wu struct regmap *php_grf; 847ad269eaSRoger Chen }; 857ad269eaSRoger Chen 867ad269eaSRoger Chen #define HIWORD_UPDATE(val, mask, shift) \ 877ad269eaSRoger Chen ((val) << (shift) | (mask) << ((shift) + 16)) 887ad269eaSRoger Chen 897ad269eaSRoger Chen #define GRF_BIT(nr) (BIT(nr) | BIT(nr+16)) 907ad269eaSRoger Chen #define GRF_CLR_BIT(nr) (BIT(nr+16)) 917ad269eaSRoger Chen 92eaf70ad1SWadim Egorov #define DELAY_ENABLE(soc, tx, rx) \ 93eaf70ad1SWadim Egorov (((tx) ? soc##_GMAC_TXCLK_DLY_ENABLE : soc##_GMAC_TXCLK_DLY_DISABLE) | \ 94eaf70ad1SWadim Egorov ((rx) ? soc##_GMAC_RXCLK_DLY_ENABLE : soc##_GMAC_RXCLK_DLY_DISABLE)) 95eaf70ad1SWadim Egorov 9623c94d63SDavid Wu #define PX30_GRF_GMAC_CON1 0x0904 9723c94d63SDavid Wu 9823c94d63SDavid Wu /* PX30_GRF_GMAC_CON1 */ 9923c94d63SDavid Wu #define PX30_GMAC_PHY_INTF_SEL_RMII (GRF_CLR_BIT(4) | GRF_CLR_BIT(5) | \ 10023c94d63SDavid Wu GRF_BIT(6)) 10123c94d63SDavid Wu #define PX30_GMAC_SPEED_10M GRF_CLR_BIT(2) 10223c94d63SDavid Wu #define PX30_GMAC_SPEED_100M GRF_BIT(2) 10323c94d63SDavid Wu 10423c94d63SDavid Wu static void px30_set_to_rmii(struct rk_priv_data *bsp_priv) 10523c94d63SDavid Wu { 10623c94d63SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 10723c94d63SDavid Wu 10823c94d63SDavid Wu if (IS_ERR(bsp_priv->grf)) { 10923c94d63SDavid Wu dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 11023c94d63SDavid Wu return; 11123c94d63SDavid Wu } 11223c94d63SDavid Wu 11323c94d63SDavid Wu regmap_write(bsp_priv->grf, PX30_GRF_GMAC_CON1, 11423c94d63SDavid Wu PX30_GMAC_PHY_INTF_SEL_RMII); 11523c94d63SDavid Wu } 11623c94d63SDavid Wu 11723c94d63SDavid Wu static void px30_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 11823c94d63SDavid Wu { 119ea449f7fSSebastian Reichel struct clk *clk_mac_speed = bsp_priv->clks[RK_CLK_MAC_SPEED].clk; 12023c94d63SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 12123c94d63SDavid Wu int ret; 12223c94d63SDavid Wu 123ea449f7fSSebastian Reichel if (!clk_mac_speed) { 12423c94d63SDavid Wu dev_err(dev, "%s: Missing clk_mac_speed clock\n", __func__); 12523c94d63SDavid Wu return; 12623c94d63SDavid Wu } 12723c94d63SDavid Wu 12823c94d63SDavid Wu if (speed == 10) { 12923c94d63SDavid Wu regmap_write(bsp_priv->grf, PX30_GRF_GMAC_CON1, 13023c94d63SDavid Wu PX30_GMAC_SPEED_10M); 13123c94d63SDavid Wu 132ea449f7fSSebastian Reichel ret = clk_set_rate(clk_mac_speed, 2500000); 13323c94d63SDavid Wu if (ret) 13423c94d63SDavid Wu dev_err(dev, "%s: set clk_mac_speed rate 2500000 failed: %d\n", 13523c94d63SDavid Wu __func__, ret); 13623c94d63SDavid Wu } else if (speed == 100) { 13723c94d63SDavid Wu regmap_write(bsp_priv->grf, PX30_GRF_GMAC_CON1, 13823c94d63SDavid Wu PX30_GMAC_SPEED_100M); 13923c94d63SDavid Wu 140ea449f7fSSebastian Reichel ret = clk_set_rate(clk_mac_speed, 25000000); 14123c94d63SDavid Wu if (ret) 14223c94d63SDavid Wu dev_err(dev, "%s: set clk_mac_speed rate 25000000 failed: %d\n", 14323c94d63SDavid Wu __func__, ret); 14423c94d63SDavid Wu 14523c94d63SDavid Wu } else { 14623c94d63SDavid Wu dev_err(dev, "unknown speed value for RMII! speed=%d", speed); 14723c94d63SDavid Wu } 14823c94d63SDavid Wu } 14923c94d63SDavid Wu 15023c94d63SDavid Wu static const struct rk_gmac_ops px30_ops = { 15123c94d63SDavid Wu .set_to_rmii = px30_set_to_rmii, 15223c94d63SDavid Wu .set_rmii_speed = px30_set_rmii_speed, 15323c94d63SDavid Wu }; 15423c94d63SDavid Wu 15505946876SDavid Wu #define RK3128_GRF_MAC_CON0 0x0168 15605946876SDavid Wu #define RK3128_GRF_MAC_CON1 0x016c 15705946876SDavid Wu 15805946876SDavid Wu /* RK3128_GRF_MAC_CON0 */ 15905946876SDavid Wu #define RK3128_GMAC_TXCLK_DLY_ENABLE GRF_BIT(14) 16005946876SDavid Wu #define RK3128_GMAC_TXCLK_DLY_DISABLE GRF_CLR_BIT(14) 16105946876SDavid Wu #define RK3128_GMAC_RXCLK_DLY_ENABLE GRF_BIT(15) 16205946876SDavid Wu #define RK3128_GMAC_RXCLK_DLY_DISABLE GRF_CLR_BIT(15) 16305946876SDavid Wu #define RK3128_GMAC_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 7) 16405946876SDavid Wu #define RK3128_GMAC_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 0) 16505946876SDavid Wu 16605946876SDavid Wu /* RK3128_GRF_MAC_CON1 */ 16705946876SDavid Wu #define RK3128_GMAC_PHY_INTF_SEL_RGMII \ 16805946876SDavid Wu (GRF_BIT(6) | GRF_CLR_BIT(7) | GRF_CLR_BIT(8)) 16905946876SDavid Wu #define RK3128_GMAC_PHY_INTF_SEL_RMII \ 17005946876SDavid Wu (GRF_CLR_BIT(6) | GRF_CLR_BIT(7) | GRF_BIT(8)) 17105946876SDavid Wu #define RK3128_GMAC_FLOW_CTRL GRF_BIT(9) 17205946876SDavid Wu #define RK3128_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(9) 17305946876SDavid Wu #define RK3128_GMAC_SPEED_10M GRF_CLR_BIT(10) 17405946876SDavid Wu #define RK3128_GMAC_SPEED_100M GRF_BIT(10) 17505946876SDavid Wu #define RK3128_GMAC_RMII_CLK_25M GRF_BIT(11) 17605946876SDavid Wu #define RK3128_GMAC_RMII_CLK_2_5M GRF_CLR_BIT(11) 17705946876SDavid Wu #define RK3128_GMAC_CLK_125M (GRF_CLR_BIT(12) | GRF_CLR_BIT(13)) 17805946876SDavid Wu #define RK3128_GMAC_CLK_25M (GRF_BIT(12) | GRF_BIT(13)) 17905946876SDavid Wu #define RK3128_GMAC_CLK_2_5M (GRF_CLR_BIT(12) | GRF_BIT(13)) 18005946876SDavid Wu #define RK3128_GMAC_RMII_MODE GRF_BIT(14) 18105946876SDavid Wu #define RK3128_GMAC_RMII_MODE_CLR GRF_CLR_BIT(14) 18205946876SDavid Wu 18305946876SDavid Wu static void rk3128_set_to_rgmii(struct rk_priv_data *bsp_priv, 18405946876SDavid Wu int tx_delay, int rx_delay) 18505946876SDavid Wu { 18605946876SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 18705946876SDavid Wu 18805946876SDavid Wu if (IS_ERR(bsp_priv->grf)) { 18905946876SDavid Wu dev_err(dev, "Missing rockchip,grf property\n"); 19005946876SDavid Wu return; 19105946876SDavid Wu } 19205946876SDavid Wu 19305946876SDavid Wu regmap_write(bsp_priv->grf, RK3128_GRF_MAC_CON1, 19405946876SDavid Wu RK3128_GMAC_PHY_INTF_SEL_RGMII | 19505946876SDavid Wu RK3128_GMAC_RMII_MODE_CLR); 19605946876SDavid Wu regmap_write(bsp_priv->grf, RK3128_GRF_MAC_CON0, 19705946876SDavid Wu DELAY_ENABLE(RK3128, tx_delay, rx_delay) | 19805946876SDavid Wu RK3128_GMAC_CLK_RX_DL_CFG(rx_delay) | 19905946876SDavid Wu RK3128_GMAC_CLK_TX_DL_CFG(tx_delay)); 20005946876SDavid Wu } 20105946876SDavid Wu 20205946876SDavid Wu static void rk3128_set_to_rmii(struct rk_priv_data *bsp_priv) 20305946876SDavid Wu { 20405946876SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 20505946876SDavid Wu 20605946876SDavid Wu if (IS_ERR(bsp_priv->grf)) { 20705946876SDavid Wu dev_err(dev, "Missing rockchip,grf property\n"); 20805946876SDavid Wu return; 20905946876SDavid Wu } 21005946876SDavid Wu 21105946876SDavid Wu regmap_write(bsp_priv->grf, RK3128_GRF_MAC_CON1, 21205946876SDavid Wu RK3128_GMAC_PHY_INTF_SEL_RMII | RK3128_GMAC_RMII_MODE); 21305946876SDavid Wu } 21405946876SDavid Wu 21505946876SDavid Wu static void rk3128_set_rgmii_speed(struct rk_priv_data *bsp_priv, int speed) 21605946876SDavid Wu { 21705946876SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 21805946876SDavid Wu 21905946876SDavid Wu if (IS_ERR(bsp_priv->grf)) { 22005946876SDavid Wu dev_err(dev, "Missing rockchip,grf property\n"); 22105946876SDavid Wu return; 22205946876SDavid Wu } 22305946876SDavid Wu 22405946876SDavid Wu if (speed == 10) 22505946876SDavid Wu regmap_write(bsp_priv->grf, RK3128_GRF_MAC_CON1, 22605946876SDavid Wu RK3128_GMAC_CLK_2_5M); 22705946876SDavid Wu else if (speed == 100) 22805946876SDavid Wu regmap_write(bsp_priv->grf, RK3128_GRF_MAC_CON1, 22905946876SDavid Wu RK3128_GMAC_CLK_25M); 23005946876SDavid Wu else if (speed == 1000) 23105946876SDavid Wu regmap_write(bsp_priv->grf, RK3128_GRF_MAC_CON1, 23205946876SDavid Wu RK3128_GMAC_CLK_125M); 23305946876SDavid Wu else 23405946876SDavid Wu dev_err(dev, "unknown speed value for RGMII! speed=%d", speed); 23505946876SDavid Wu } 23605946876SDavid Wu 23705946876SDavid Wu static void rk3128_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 23805946876SDavid Wu { 23905946876SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 24005946876SDavid Wu 24105946876SDavid Wu if (IS_ERR(bsp_priv->grf)) { 24205946876SDavid Wu dev_err(dev, "Missing rockchip,grf property\n"); 24305946876SDavid Wu return; 24405946876SDavid Wu } 24505946876SDavid Wu 24605946876SDavid Wu if (speed == 10) { 24705946876SDavid Wu regmap_write(bsp_priv->grf, RK3128_GRF_MAC_CON1, 24805946876SDavid Wu RK3128_GMAC_RMII_CLK_2_5M | 24905946876SDavid Wu RK3128_GMAC_SPEED_10M); 25005946876SDavid Wu } else if (speed == 100) { 25105946876SDavid Wu regmap_write(bsp_priv->grf, RK3128_GRF_MAC_CON1, 25205946876SDavid Wu RK3128_GMAC_RMII_CLK_25M | 25305946876SDavid Wu RK3128_GMAC_SPEED_100M); 25405946876SDavid Wu } else { 25505946876SDavid Wu dev_err(dev, "unknown speed value for RMII! speed=%d", speed); 25605946876SDavid Wu } 25705946876SDavid Wu } 25805946876SDavid Wu 25905946876SDavid Wu static const struct rk_gmac_ops rk3128_ops = { 26005946876SDavid Wu .set_to_rgmii = rk3128_set_to_rgmii, 26105946876SDavid Wu .set_to_rmii = rk3128_set_to_rmii, 26205946876SDavid Wu .set_rgmii_speed = rk3128_set_rgmii_speed, 26305946876SDavid Wu .set_rmii_speed = rk3128_set_rmii_speed, 26405946876SDavid Wu }; 26505946876SDavid Wu 266e7ffd812SXing Zheng #define RK3228_GRF_MAC_CON0 0x0900 267e7ffd812SXing Zheng #define RK3228_GRF_MAC_CON1 0x0904 268e7ffd812SXing Zheng 2696fa12c78SDavid Wu #define RK3228_GRF_CON_MUX 0x50 2706fa12c78SDavid Wu 271e7ffd812SXing Zheng /* RK3228_GRF_MAC_CON0 */ 272e7ffd812SXing Zheng #define RK3228_GMAC_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 7) 273e7ffd812SXing Zheng #define RK3228_GMAC_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 0) 274e7ffd812SXing Zheng 275e7ffd812SXing Zheng /* RK3228_GRF_MAC_CON1 */ 276e7ffd812SXing Zheng #define RK3228_GMAC_PHY_INTF_SEL_RGMII \ 277e7ffd812SXing Zheng (GRF_BIT(4) | GRF_CLR_BIT(5) | GRF_CLR_BIT(6)) 278e7ffd812SXing Zheng #define RK3228_GMAC_PHY_INTF_SEL_RMII \ 279e7ffd812SXing Zheng (GRF_CLR_BIT(4) | GRF_CLR_BIT(5) | GRF_BIT(6)) 280e7ffd812SXing Zheng #define RK3228_GMAC_FLOW_CTRL GRF_BIT(3) 281e7ffd812SXing Zheng #define RK3228_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(3) 282e7ffd812SXing Zheng #define RK3228_GMAC_SPEED_10M GRF_CLR_BIT(2) 283e7ffd812SXing Zheng #define RK3228_GMAC_SPEED_100M GRF_BIT(2) 284e7ffd812SXing Zheng #define RK3228_GMAC_RMII_CLK_25M GRF_BIT(7) 285e7ffd812SXing Zheng #define RK3228_GMAC_RMII_CLK_2_5M GRF_CLR_BIT(7) 286e7ffd812SXing Zheng #define RK3228_GMAC_CLK_125M (GRF_CLR_BIT(8) | GRF_CLR_BIT(9)) 287e7ffd812SXing Zheng #define RK3228_GMAC_CLK_25M (GRF_BIT(8) | GRF_BIT(9)) 288e7ffd812SXing Zheng #define RK3228_GMAC_CLK_2_5M (GRF_CLR_BIT(8) | GRF_BIT(9)) 289e7ffd812SXing Zheng #define RK3228_GMAC_RMII_MODE GRF_BIT(10) 290e7ffd812SXing Zheng #define RK3228_GMAC_RMII_MODE_CLR GRF_CLR_BIT(10) 291e7ffd812SXing Zheng #define RK3228_GMAC_TXCLK_DLY_ENABLE GRF_BIT(0) 292e7ffd812SXing Zheng #define RK3228_GMAC_TXCLK_DLY_DISABLE GRF_CLR_BIT(0) 293e7ffd812SXing Zheng #define RK3228_GMAC_RXCLK_DLY_ENABLE GRF_BIT(1) 294e7ffd812SXing Zheng #define RK3228_GMAC_RXCLK_DLY_DISABLE GRF_CLR_BIT(1) 295e7ffd812SXing Zheng 2966fa12c78SDavid Wu /* RK3228_GRF_COM_MUX */ 2976fa12c78SDavid Wu #define RK3228_GRF_CON_MUX_GMAC_INTEGRATED_PHY GRF_BIT(15) 2986fa12c78SDavid Wu 299e7ffd812SXing Zheng static void rk3228_set_to_rgmii(struct rk_priv_data *bsp_priv, 300e7ffd812SXing Zheng int tx_delay, int rx_delay) 301e7ffd812SXing Zheng { 302e7ffd812SXing Zheng struct device *dev = &bsp_priv->pdev->dev; 303e7ffd812SXing Zheng 304e7ffd812SXing Zheng if (IS_ERR(bsp_priv->grf)) { 305e7ffd812SXing Zheng dev_err(dev, "Missing rockchip,grf property\n"); 306e7ffd812SXing Zheng return; 307e7ffd812SXing Zheng } 308e7ffd812SXing Zheng 309e7ffd812SXing Zheng regmap_write(bsp_priv->grf, RK3228_GRF_MAC_CON1, 310e7ffd812SXing Zheng RK3228_GMAC_PHY_INTF_SEL_RGMII | 311e7ffd812SXing Zheng RK3228_GMAC_RMII_MODE_CLR | 312eaf70ad1SWadim Egorov DELAY_ENABLE(RK3228, tx_delay, rx_delay)); 313e7ffd812SXing Zheng 314e7ffd812SXing Zheng regmap_write(bsp_priv->grf, RK3228_GRF_MAC_CON0, 315e7ffd812SXing Zheng RK3228_GMAC_CLK_RX_DL_CFG(rx_delay) | 316e7ffd812SXing Zheng RK3228_GMAC_CLK_TX_DL_CFG(tx_delay)); 317e7ffd812SXing Zheng } 318e7ffd812SXing Zheng 319e7ffd812SXing Zheng static void rk3228_set_to_rmii(struct rk_priv_data *bsp_priv) 320e7ffd812SXing Zheng { 321e7ffd812SXing Zheng struct device *dev = &bsp_priv->pdev->dev; 322e7ffd812SXing Zheng 323e7ffd812SXing Zheng if (IS_ERR(bsp_priv->grf)) { 324e7ffd812SXing Zheng dev_err(dev, "Missing rockchip,grf property\n"); 325e7ffd812SXing Zheng return; 326e7ffd812SXing Zheng } 327e7ffd812SXing Zheng 328e7ffd812SXing Zheng regmap_write(bsp_priv->grf, RK3228_GRF_MAC_CON1, 329e7ffd812SXing Zheng RK3228_GMAC_PHY_INTF_SEL_RMII | 330e7ffd812SXing Zheng RK3228_GMAC_RMII_MODE); 331e7ffd812SXing Zheng 332e7ffd812SXing Zheng /* set MAC to RMII mode */ 333e7ffd812SXing Zheng regmap_write(bsp_priv->grf, RK3228_GRF_MAC_CON1, GRF_BIT(11)); 334e7ffd812SXing Zheng } 335e7ffd812SXing Zheng 336e7ffd812SXing Zheng static void rk3228_set_rgmii_speed(struct rk_priv_data *bsp_priv, int speed) 337e7ffd812SXing Zheng { 338e7ffd812SXing Zheng struct device *dev = &bsp_priv->pdev->dev; 339e7ffd812SXing Zheng 340e7ffd812SXing Zheng if (IS_ERR(bsp_priv->grf)) { 341e7ffd812SXing Zheng dev_err(dev, "Missing rockchip,grf property\n"); 342e7ffd812SXing Zheng return; 343e7ffd812SXing Zheng } 344e7ffd812SXing Zheng 345e7ffd812SXing Zheng if (speed == 10) 346e7ffd812SXing Zheng regmap_write(bsp_priv->grf, RK3228_GRF_MAC_CON1, 347e7ffd812SXing Zheng RK3228_GMAC_CLK_2_5M); 348e7ffd812SXing Zheng else if (speed == 100) 349e7ffd812SXing Zheng regmap_write(bsp_priv->grf, RK3228_GRF_MAC_CON1, 350e7ffd812SXing Zheng RK3228_GMAC_CLK_25M); 351e7ffd812SXing Zheng else if (speed == 1000) 352e7ffd812SXing Zheng regmap_write(bsp_priv->grf, RK3228_GRF_MAC_CON1, 353e7ffd812SXing Zheng RK3228_GMAC_CLK_125M); 354e7ffd812SXing Zheng else 355e7ffd812SXing Zheng dev_err(dev, "unknown speed value for RGMII! speed=%d", speed); 356e7ffd812SXing Zheng } 357e7ffd812SXing Zheng 358e7ffd812SXing Zheng static void rk3228_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 359e7ffd812SXing Zheng { 360e7ffd812SXing Zheng struct device *dev = &bsp_priv->pdev->dev; 361e7ffd812SXing Zheng 362e7ffd812SXing Zheng if (IS_ERR(bsp_priv->grf)) { 363e7ffd812SXing Zheng dev_err(dev, "Missing rockchip,grf property\n"); 364e7ffd812SXing Zheng return; 365e7ffd812SXing Zheng } 366e7ffd812SXing Zheng 367e7ffd812SXing Zheng if (speed == 10) 368e7ffd812SXing Zheng regmap_write(bsp_priv->grf, RK3228_GRF_MAC_CON1, 369e7ffd812SXing Zheng RK3228_GMAC_RMII_CLK_2_5M | 370e7ffd812SXing Zheng RK3228_GMAC_SPEED_10M); 371e7ffd812SXing Zheng else if (speed == 100) 372e7ffd812SXing Zheng regmap_write(bsp_priv->grf, RK3228_GRF_MAC_CON1, 373e7ffd812SXing Zheng RK3228_GMAC_RMII_CLK_25M | 374e7ffd812SXing Zheng RK3228_GMAC_SPEED_100M); 375e7ffd812SXing Zheng else 376e7ffd812SXing Zheng dev_err(dev, "unknown speed value for RMII! speed=%d", speed); 377e7ffd812SXing Zheng } 378e7ffd812SXing Zheng 3796fa12c78SDavid Wu static void rk3228_integrated_phy_powerup(struct rk_priv_data *priv) 3806fa12c78SDavid Wu { 3816fa12c78SDavid Wu regmap_write(priv->grf, RK3228_GRF_CON_MUX, 3826fa12c78SDavid Wu RK3228_GRF_CON_MUX_GMAC_INTEGRATED_PHY); 3836fa12c78SDavid Wu } 3846fa12c78SDavid Wu 385e7ffd812SXing Zheng static const struct rk_gmac_ops rk3228_ops = { 386e7ffd812SXing Zheng .set_to_rgmii = rk3228_set_to_rgmii, 387e7ffd812SXing Zheng .set_to_rmii = rk3228_set_to_rmii, 388e7ffd812SXing Zheng .set_rgmii_speed = rk3228_set_rgmii_speed, 389e7ffd812SXing Zheng .set_rmii_speed = rk3228_set_rmii_speed, 3906fa12c78SDavid Wu .integrated_phy_powerup = rk3228_integrated_phy_powerup, 391e7ffd812SXing Zheng }; 392e7ffd812SXing Zheng 3937ad269eaSRoger Chen #define RK3288_GRF_SOC_CON1 0x0248 3947ad269eaSRoger Chen #define RK3288_GRF_SOC_CON3 0x0250 3957ad269eaSRoger Chen 3967ad269eaSRoger Chen /*RK3288_GRF_SOC_CON1*/ 3970fb98db1SHeiko Stübner #define RK3288_GMAC_PHY_INTF_SEL_RGMII (GRF_BIT(6) | GRF_CLR_BIT(7) | \ 3980fb98db1SHeiko Stübner GRF_CLR_BIT(8)) 3990fb98db1SHeiko Stübner #define RK3288_GMAC_PHY_INTF_SEL_RMII (GRF_CLR_BIT(6) | GRF_CLR_BIT(7) | \ 4000fb98db1SHeiko Stübner GRF_BIT(8)) 4010fb98db1SHeiko Stübner #define RK3288_GMAC_FLOW_CTRL GRF_BIT(9) 4020fb98db1SHeiko Stübner #define RK3288_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(9) 4030fb98db1SHeiko Stübner #define RK3288_GMAC_SPEED_10M GRF_CLR_BIT(10) 4040fb98db1SHeiko Stübner #define RK3288_GMAC_SPEED_100M GRF_BIT(10) 4050fb98db1SHeiko Stübner #define RK3288_GMAC_RMII_CLK_25M GRF_BIT(11) 4060fb98db1SHeiko Stübner #define RK3288_GMAC_RMII_CLK_2_5M GRF_CLR_BIT(11) 4070fb98db1SHeiko Stübner #define RK3288_GMAC_CLK_125M (GRF_CLR_BIT(12) | GRF_CLR_BIT(13)) 4080fb98db1SHeiko Stübner #define RK3288_GMAC_CLK_25M (GRF_BIT(12) | GRF_BIT(13)) 4090fb98db1SHeiko Stübner #define RK3288_GMAC_CLK_2_5M (GRF_CLR_BIT(12) | GRF_BIT(13)) 4100fb98db1SHeiko Stübner #define RK3288_GMAC_RMII_MODE GRF_BIT(14) 4110fb98db1SHeiko Stübner #define RK3288_GMAC_RMII_MODE_CLR GRF_CLR_BIT(14) 4127ad269eaSRoger Chen 4137ad269eaSRoger Chen /*RK3288_GRF_SOC_CON3*/ 4140fb98db1SHeiko Stübner #define RK3288_GMAC_TXCLK_DLY_ENABLE GRF_BIT(14) 4150fb98db1SHeiko Stübner #define RK3288_GMAC_TXCLK_DLY_DISABLE GRF_CLR_BIT(14) 4160fb98db1SHeiko Stübner #define RK3288_GMAC_RXCLK_DLY_ENABLE GRF_BIT(15) 4170fb98db1SHeiko Stübner #define RK3288_GMAC_RXCLK_DLY_DISABLE GRF_CLR_BIT(15) 4180fb98db1SHeiko Stübner #define RK3288_GMAC_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 7) 4190fb98db1SHeiko Stübner #define RK3288_GMAC_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 0) 4207ad269eaSRoger Chen 4210fb98db1SHeiko Stübner static void rk3288_set_to_rgmii(struct rk_priv_data *bsp_priv, 4227ad269eaSRoger Chen int tx_delay, int rx_delay) 4237ad269eaSRoger Chen { 4247ad269eaSRoger Chen struct device *dev = &bsp_priv->pdev->dev; 4257ad269eaSRoger Chen 4267ad269eaSRoger Chen if (IS_ERR(bsp_priv->grf)) { 427d42202dcSRomain Perier dev_err(dev, "Missing rockchip,grf property\n"); 4287ad269eaSRoger Chen return; 4297ad269eaSRoger Chen } 4307ad269eaSRoger Chen 4317ad269eaSRoger Chen regmap_write(bsp_priv->grf, RK3288_GRF_SOC_CON1, 4320fb98db1SHeiko Stübner RK3288_GMAC_PHY_INTF_SEL_RGMII | 4330fb98db1SHeiko Stübner RK3288_GMAC_RMII_MODE_CLR); 4347ad269eaSRoger Chen regmap_write(bsp_priv->grf, RK3288_GRF_SOC_CON3, 435eaf70ad1SWadim Egorov DELAY_ENABLE(RK3288, tx_delay, rx_delay) | 4360fb98db1SHeiko Stübner RK3288_GMAC_CLK_RX_DL_CFG(rx_delay) | 4370fb98db1SHeiko Stübner RK3288_GMAC_CLK_TX_DL_CFG(tx_delay)); 4387ad269eaSRoger Chen } 4397ad269eaSRoger Chen 4400fb98db1SHeiko Stübner static void rk3288_set_to_rmii(struct rk_priv_data *bsp_priv) 4417ad269eaSRoger Chen { 4427ad269eaSRoger Chen struct device *dev = &bsp_priv->pdev->dev; 4437ad269eaSRoger Chen 4447ad269eaSRoger Chen if (IS_ERR(bsp_priv->grf)) { 445d42202dcSRomain Perier dev_err(dev, "Missing rockchip,grf property\n"); 4467ad269eaSRoger Chen return; 4477ad269eaSRoger Chen } 4487ad269eaSRoger Chen 4497ad269eaSRoger Chen regmap_write(bsp_priv->grf, RK3288_GRF_SOC_CON1, 4500fb98db1SHeiko Stübner RK3288_GMAC_PHY_INTF_SEL_RMII | RK3288_GMAC_RMII_MODE); 4517ad269eaSRoger Chen } 4527ad269eaSRoger Chen 4530fb98db1SHeiko Stübner static void rk3288_set_rgmii_speed(struct rk_priv_data *bsp_priv, int speed) 4547ad269eaSRoger Chen { 4557ad269eaSRoger Chen struct device *dev = &bsp_priv->pdev->dev; 4567ad269eaSRoger Chen 4577ad269eaSRoger Chen if (IS_ERR(bsp_priv->grf)) { 458d42202dcSRomain Perier dev_err(dev, "Missing rockchip,grf property\n"); 4597ad269eaSRoger Chen return; 4607ad269eaSRoger Chen } 4617ad269eaSRoger Chen 4627ad269eaSRoger Chen if (speed == 10) 4630fb98db1SHeiko Stübner regmap_write(bsp_priv->grf, RK3288_GRF_SOC_CON1, 4640fb98db1SHeiko Stübner RK3288_GMAC_CLK_2_5M); 4657ad269eaSRoger Chen else if (speed == 100) 4660fb98db1SHeiko Stübner regmap_write(bsp_priv->grf, RK3288_GRF_SOC_CON1, 4670fb98db1SHeiko Stübner RK3288_GMAC_CLK_25M); 4687ad269eaSRoger Chen else if (speed == 1000) 4690fb98db1SHeiko Stübner regmap_write(bsp_priv->grf, RK3288_GRF_SOC_CON1, 4700fb98db1SHeiko Stübner RK3288_GMAC_CLK_125M); 4717ad269eaSRoger Chen else 4727ad269eaSRoger Chen dev_err(dev, "unknown speed value for RGMII! speed=%d", speed); 4737ad269eaSRoger Chen } 4747ad269eaSRoger Chen 4750fb98db1SHeiko Stübner static void rk3288_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 4767ad269eaSRoger Chen { 4777ad269eaSRoger Chen struct device *dev = &bsp_priv->pdev->dev; 4787ad269eaSRoger Chen 4797ad269eaSRoger Chen if (IS_ERR(bsp_priv->grf)) { 480d42202dcSRomain Perier dev_err(dev, "Missing rockchip,grf property\n"); 4817ad269eaSRoger Chen return; 4827ad269eaSRoger Chen } 4837ad269eaSRoger Chen 4847ad269eaSRoger Chen if (speed == 10) { 4857ad269eaSRoger Chen regmap_write(bsp_priv->grf, RK3288_GRF_SOC_CON1, 4860fb98db1SHeiko Stübner RK3288_GMAC_RMII_CLK_2_5M | 4870fb98db1SHeiko Stübner RK3288_GMAC_SPEED_10M); 4887ad269eaSRoger Chen } else if (speed == 100) { 4897ad269eaSRoger Chen regmap_write(bsp_priv->grf, RK3288_GRF_SOC_CON1, 4900fb98db1SHeiko Stübner RK3288_GMAC_RMII_CLK_25M | 4910fb98db1SHeiko Stübner RK3288_GMAC_SPEED_100M); 4927ad269eaSRoger Chen } else { 4937ad269eaSRoger Chen dev_err(dev, "unknown speed value for RMII! speed=%d", speed); 4947ad269eaSRoger Chen } 4957ad269eaSRoger Chen } 4967ad269eaSRoger Chen 49792c2588fSJoachim Eastwood static const struct rk_gmac_ops rk3288_ops = { 4980fb98db1SHeiko Stübner .set_to_rgmii = rk3288_set_to_rgmii, 4990fb98db1SHeiko Stübner .set_to_rmii = rk3288_set_to_rmii, 5000fb98db1SHeiko Stübner .set_rgmii_speed = rk3288_set_rgmii_speed, 5010fb98db1SHeiko Stübner .set_rmii_speed = rk3288_set_rmii_speed, 5020fb98db1SHeiko Stübner }; 5030fb98db1SHeiko Stübner 504b4ac9456STobias Schramm #define RK3308_GRF_MAC_CON0 0x04a0 505b4ac9456STobias Schramm 506b4ac9456STobias Schramm /* RK3308_GRF_MAC_CON0 */ 507b4ac9456STobias Schramm #define RK3308_GMAC_PHY_INTF_SEL_RMII (GRF_CLR_BIT(2) | GRF_CLR_BIT(3) | \ 508b4ac9456STobias Schramm GRF_BIT(4)) 509b4ac9456STobias Schramm #define RK3308_GMAC_FLOW_CTRL GRF_BIT(3) 510b4ac9456STobias Schramm #define RK3308_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(3) 511b4ac9456STobias Schramm #define RK3308_GMAC_SPEED_10M GRF_CLR_BIT(0) 512b4ac9456STobias Schramm #define RK3308_GMAC_SPEED_100M GRF_BIT(0) 513b4ac9456STobias Schramm 514b4ac9456STobias Schramm static void rk3308_set_to_rmii(struct rk_priv_data *bsp_priv) 515b4ac9456STobias Schramm { 516b4ac9456STobias Schramm struct device *dev = &bsp_priv->pdev->dev; 517b4ac9456STobias Schramm 518b4ac9456STobias Schramm if (IS_ERR(bsp_priv->grf)) { 519b4ac9456STobias Schramm dev_err(dev, "Missing rockchip,grf property\n"); 520b4ac9456STobias Schramm return; 521b4ac9456STobias Schramm } 522b4ac9456STobias Schramm 523b4ac9456STobias Schramm regmap_write(bsp_priv->grf, RK3308_GRF_MAC_CON0, 524b4ac9456STobias Schramm RK3308_GMAC_PHY_INTF_SEL_RMII); 525b4ac9456STobias Schramm } 526b4ac9456STobias Schramm 527b4ac9456STobias Schramm static void rk3308_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 528b4ac9456STobias Schramm { 529b4ac9456STobias Schramm struct device *dev = &bsp_priv->pdev->dev; 530b4ac9456STobias Schramm 531b4ac9456STobias Schramm if (IS_ERR(bsp_priv->grf)) { 532b4ac9456STobias Schramm dev_err(dev, "Missing rockchip,grf property\n"); 533b4ac9456STobias Schramm return; 534b4ac9456STobias Schramm } 535b4ac9456STobias Schramm 536b4ac9456STobias Schramm if (speed == 10) { 537b4ac9456STobias Schramm regmap_write(bsp_priv->grf, RK3308_GRF_MAC_CON0, 538b4ac9456STobias Schramm RK3308_GMAC_SPEED_10M); 539b4ac9456STobias Schramm } else if (speed == 100) { 540b4ac9456STobias Schramm regmap_write(bsp_priv->grf, RK3308_GRF_MAC_CON0, 541b4ac9456STobias Schramm RK3308_GMAC_SPEED_100M); 542b4ac9456STobias Schramm } else { 543b4ac9456STobias Schramm dev_err(dev, "unknown speed value for RMII! speed=%d", speed); 544b4ac9456STobias Schramm } 545b4ac9456STobias Schramm } 546b4ac9456STobias Schramm 547b4ac9456STobias Schramm static const struct rk_gmac_ops rk3308_ops = { 548b4ac9456STobias Schramm .set_to_rmii = rk3308_set_to_rmii, 549b4ac9456STobias Schramm .set_rmii_speed = rk3308_set_rmii_speed, 550b4ac9456STobias Schramm }; 551b4ac9456STobias Schramm 552d4ff816eSdavid.wu #define RK3328_GRF_MAC_CON0 0x0900 553d4ff816eSdavid.wu #define RK3328_GRF_MAC_CON1 0x0904 5548bdf63bdSDavid Wu #define RK3328_GRF_MAC_CON2 0x0908 5558bdf63bdSDavid Wu #define RK3328_GRF_MACPHY_CON1 0xb04 556d4ff816eSdavid.wu 557d4ff816eSdavid.wu /* RK3328_GRF_MAC_CON0 */ 558d4ff816eSdavid.wu #define RK3328_GMAC_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 7) 559d4ff816eSdavid.wu #define RK3328_GMAC_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 0) 560d4ff816eSdavid.wu 561d4ff816eSdavid.wu /* RK3328_GRF_MAC_CON1 */ 562d4ff816eSdavid.wu #define RK3328_GMAC_PHY_INTF_SEL_RGMII \ 563d4ff816eSdavid.wu (GRF_BIT(4) | GRF_CLR_BIT(5) | GRF_CLR_BIT(6)) 564d4ff816eSdavid.wu #define RK3328_GMAC_PHY_INTF_SEL_RMII \ 565d4ff816eSdavid.wu (GRF_CLR_BIT(4) | GRF_CLR_BIT(5) | GRF_BIT(6)) 566d4ff816eSdavid.wu #define RK3328_GMAC_FLOW_CTRL GRF_BIT(3) 567d4ff816eSdavid.wu #define RK3328_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(3) 568d4ff816eSdavid.wu #define RK3328_GMAC_SPEED_10M GRF_CLR_BIT(2) 569d4ff816eSdavid.wu #define RK3328_GMAC_SPEED_100M GRF_BIT(2) 570d4ff816eSdavid.wu #define RK3328_GMAC_RMII_CLK_25M GRF_BIT(7) 571d4ff816eSdavid.wu #define RK3328_GMAC_RMII_CLK_2_5M GRF_CLR_BIT(7) 572d4ff816eSdavid.wu #define RK3328_GMAC_CLK_125M (GRF_CLR_BIT(11) | GRF_CLR_BIT(12)) 573d4ff816eSdavid.wu #define RK3328_GMAC_CLK_25M (GRF_BIT(11) | GRF_BIT(12)) 574d4ff816eSdavid.wu #define RK3328_GMAC_CLK_2_5M (GRF_CLR_BIT(11) | GRF_BIT(12)) 575d4ff816eSdavid.wu #define RK3328_GMAC_RMII_MODE GRF_BIT(9) 576d4ff816eSdavid.wu #define RK3328_GMAC_RMII_MODE_CLR GRF_CLR_BIT(9) 577d4ff816eSdavid.wu #define RK3328_GMAC_TXCLK_DLY_ENABLE GRF_BIT(0) 578d4ff816eSdavid.wu #define RK3328_GMAC_TXCLK_DLY_DISABLE GRF_CLR_BIT(0) 579d4ff816eSdavid.wu #define RK3328_GMAC_RXCLK_DLY_ENABLE GRF_BIT(1) 580d4ff816eSdavid.wu #define RK3328_GMAC_RXCLK_DLY_DISABLE GRF_CLR_BIT(0) 581d4ff816eSdavid.wu 5828bdf63bdSDavid Wu /* RK3328_GRF_MACPHY_CON1 */ 5838bdf63bdSDavid Wu #define RK3328_MACPHY_RMII_MODE GRF_BIT(9) 5848bdf63bdSDavid Wu 585d4ff816eSdavid.wu static void rk3328_set_to_rgmii(struct rk_priv_data *bsp_priv, 586d4ff816eSdavid.wu int tx_delay, int rx_delay) 587d4ff816eSdavid.wu { 588d4ff816eSdavid.wu struct device *dev = &bsp_priv->pdev->dev; 589d4ff816eSdavid.wu 590d4ff816eSdavid.wu if (IS_ERR(bsp_priv->grf)) { 591d4ff816eSdavid.wu dev_err(dev, "Missing rockchip,grf property\n"); 592d4ff816eSdavid.wu return; 593d4ff816eSdavid.wu } 594d4ff816eSdavid.wu 595d4ff816eSdavid.wu regmap_write(bsp_priv->grf, RK3328_GRF_MAC_CON1, 596d4ff816eSdavid.wu RK3328_GMAC_PHY_INTF_SEL_RGMII | 597d4ff816eSdavid.wu RK3328_GMAC_RMII_MODE_CLR | 598d4ff816eSdavid.wu RK3328_GMAC_RXCLK_DLY_ENABLE | 599d4ff816eSdavid.wu RK3328_GMAC_TXCLK_DLY_ENABLE); 600d4ff816eSdavid.wu 601d4ff816eSdavid.wu regmap_write(bsp_priv->grf, RK3328_GRF_MAC_CON0, 602d4ff816eSdavid.wu RK3328_GMAC_CLK_RX_DL_CFG(rx_delay) | 603d4ff816eSdavid.wu RK3328_GMAC_CLK_TX_DL_CFG(tx_delay)); 604d4ff816eSdavid.wu } 605d4ff816eSdavid.wu 606d4ff816eSdavid.wu static void rk3328_set_to_rmii(struct rk_priv_data *bsp_priv) 607d4ff816eSdavid.wu { 608d4ff816eSdavid.wu struct device *dev = &bsp_priv->pdev->dev; 6098bdf63bdSDavid Wu unsigned int reg; 610d4ff816eSdavid.wu 611d4ff816eSdavid.wu if (IS_ERR(bsp_priv->grf)) { 612d4ff816eSdavid.wu dev_err(dev, "Missing rockchip,grf property\n"); 613d4ff816eSdavid.wu return; 614d4ff816eSdavid.wu } 615d4ff816eSdavid.wu 6168bdf63bdSDavid Wu reg = bsp_priv->integrated_phy ? RK3328_GRF_MAC_CON2 : 6178bdf63bdSDavid Wu RK3328_GRF_MAC_CON1; 6188bdf63bdSDavid Wu 6198bdf63bdSDavid Wu regmap_write(bsp_priv->grf, reg, 620d4ff816eSdavid.wu RK3328_GMAC_PHY_INTF_SEL_RMII | 621d4ff816eSdavid.wu RK3328_GMAC_RMII_MODE); 622d4ff816eSdavid.wu } 623d4ff816eSdavid.wu 624d4ff816eSdavid.wu static void rk3328_set_rgmii_speed(struct rk_priv_data *bsp_priv, int speed) 625d4ff816eSdavid.wu { 626d4ff816eSdavid.wu struct device *dev = &bsp_priv->pdev->dev; 627d4ff816eSdavid.wu 628d4ff816eSdavid.wu if (IS_ERR(bsp_priv->grf)) { 629d4ff816eSdavid.wu dev_err(dev, "Missing rockchip,grf property\n"); 630d4ff816eSdavid.wu return; 631d4ff816eSdavid.wu } 632d4ff816eSdavid.wu 633d4ff816eSdavid.wu if (speed == 10) 634d4ff816eSdavid.wu regmap_write(bsp_priv->grf, RK3328_GRF_MAC_CON1, 635d4ff816eSdavid.wu RK3328_GMAC_CLK_2_5M); 636d4ff816eSdavid.wu else if (speed == 100) 637d4ff816eSdavid.wu regmap_write(bsp_priv->grf, RK3328_GRF_MAC_CON1, 638d4ff816eSdavid.wu RK3328_GMAC_CLK_25M); 639d4ff816eSdavid.wu else if (speed == 1000) 640d4ff816eSdavid.wu regmap_write(bsp_priv->grf, RK3328_GRF_MAC_CON1, 641d4ff816eSdavid.wu RK3328_GMAC_CLK_125M); 642d4ff816eSdavid.wu else 643d4ff816eSdavid.wu dev_err(dev, "unknown speed value for RGMII! speed=%d", speed); 644d4ff816eSdavid.wu } 645d4ff816eSdavid.wu 646d4ff816eSdavid.wu static void rk3328_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 647d4ff816eSdavid.wu { 648d4ff816eSdavid.wu struct device *dev = &bsp_priv->pdev->dev; 6498bdf63bdSDavid Wu unsigned int reg; 650d4ff816eSdavid.wu 651d4ff816eSdavid.wu if (IS_ERR(bsp_priv->grf)) { 652d4ff816eSdavid.wu dev_err(dev, "Missing rockchip,grf property\n"); 653d4ff816eSdavid.wu return; 654d4ff816eSdavid.wu } 655d4ff816eSdavid.wu 6568bdf63bdSDavid Wu reg = bsp_priv->integrated_phy ? RK3328_GRF_MAC_CON2 : 6578bdf63bdSDavid Wu RK3328_GRF_MAC_CON1; 6588bdf63bdSDavid Wu 659d4ff816eSdavid.wu if (speed == 10) 6608bdf63bdSDavid Wu regmap_write(bsp_priv->grf, reg, 661d4ff816eSdavid.wu RK3328_GMAC_RMII_CLK_2_5M | 662d4ff816eSdavid.wu RK3328_GMAC_SPEED_10M); 663d4ff816eSdavid.wu else if (speed == 100) 6648bdf63bdSDavid Wu regmap_write(bsp_priv->grf, reg, 665d4ff816eSdavid.wu RK3328_GMAC_RMII_CLK_25M | 666d4ff816eSdavid.wu RK3328_GMAC_SPEED_100M); 667d4ff816eSdavid.wu else 668d4ff816eSdavid.wu dev_err(dev, "unknown speed value for RMII! speed=%d", speed); 669d4ff816eSdavid.wu } 670d4ff816eSdavid.wu 6718bdf63bdSDavid Wu static void rk3328_integrated_phy_powerup(struct rk_priv_data *priv) 6728bdf63bdSDavid Wu { 6738bdf63bdSDavid Wu regmap_write(priv->grf, RK3328_GRF_MACPHY_CON1, 6748bdf63bdSDavid Wu RK3328_MACPHY_RMII_MODE); 6758bdf63bdSDavid Wu } 6768bdf63bdSDavid Wu 677d4ff816eSdavid.wu static const struct rk_gmac_ops rk3328_ops = { 678d4ff816eSdavid.wu .set_to_rgmii = rk3328_set_to_rgmii, 679d4ff816eSdavid.wu .set_to_rmii = rk3328_set_to_rmii, 680d4ff816eSdavid.wu .set_rgmii_speed = rk3328_set_rgmii_speed, 681d4ff816eSdavid.wu .set_rmii_speed = rk3328_set_rmii_speed, 6828bdf63bdSDavid Wu .integrated_phy_powerup = rk3328_integrated_phy_powerup, 683d4ff816eSdavid.wu }; 684d4ff816eSdavid.wu 685ba289af8SRoger Chen #define RK3366_GRF_SOC_CON6 0x0418 686ba289af8SRoger Chen #define RK3366_GRF_SOC_CON7 0x041c 687ba289af8SRoger Chen 688ba289af8SRoger Chen /* RK3366_GRF_SOC_CON6 */ 689ba289af8SRoger Chen #define RK3366_GMAC_PHY_INTF_SEL_RGMII (GRF_BIT(9) | GRF_CLR_BIT(10) | \ 690ba289af8SRoger Chen GRF_CLR_BIT(11)) 691ba289af8SRoger Chen #define RK3366_GMAC_PHY_INTF_SEL_RMII (GRF_CLR_BIT(9) | GRF_CLR_BIT(10) | \ 692ba289af8SRoger Chen GRF_BIT(11)) 693ba289af8SRoger Chen #define RK3366_GMAC_FLOW_CTRL GRF_BIT(8) 694ba289af8SRoger Chen #define RK3366_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(8) 695ba289af8SRoger Chen #define RK3366_GMAC_SPEED_10M GRF_CLR_BIT(7) 696ba289af8SRoger Chen #define RK3366_GMAC_SPEED_100M GRF_BIT(7) 697ba289af8SRoger Chen #define RK3366_GMAC_RMII_CLK_25M GRF_BIT(3) 698ba289af8SRoger Chen #define RK3366_GMAC_RMII_CLK_2_5M GRF_CLR_BIT(3) 699ba289af8SRoger Chen #define RK3366_GMAC_CLK_125M (GRF_CLR_BIT(4) | GRF_CLR_BIT(5)) 700ba289af8SRoger Chen #define RK3366_GMAC_CLK_25M (GRF_BIT(4) | GRF_BIT(5)) 701ba289af8SRoger Chen #define RK3366_GMAC_CLK_2_5M (GRF_CLR_BIT(4) | GRF_BIT(5)) 702ba289af8SRoger Chen #define RK3366_GMAC_RMII_MODE GRF_BIT(6) 703ba289af8SRoger Chen #define RK3366_GMAC_RMII_MODE_CLR GRF_CLR_BIT(6) 704ba289af8SRoger Chen 705ba289af8SRoger Chen /* RK3366_GRF_SOC_CON7 */ 706ba289af8SRoger Chen #define RK3366_GMAC_TXCLK_DLY_ENABLE GRF_BIT(7) 707ba289af8SRoger Chen #define RK3366_GMAC_TXCLK_DLY_DISABLE GRF_CLR_BIT(7) 708ba289af8SRoger Chen #define RK3366_GMAC_RXCLK_DLY_ENABLE GRF_BIT(15) 709ba289af8SRoger Chen #define RK3366_GMAC_RXCLK_DLY_DISABLE GRF_CLR_BIT(15) 710ba289af8SRoger Chen #define RK3366_GMAC_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 8) 711ba289af8SRoger Chen #define RK3366_GMAC_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 0) 712ba289af8SRoger Chen 713ba289af8SRoger Chen static void rk3366_set_to_rgmii(struct rk_priv_data *bsp_priv, 714ba289af8SRoger Chen int tx_delay, int rx_delay) 715ba289af8SRoger Chen { 716ba289af8SRoger Chen struct device *dev = &bsp_priv->pdev->dev; 717ba289af8SRoger Chen 718ba289af8SRoger Chen if (IS_ERR(bsp_priv->grf)) { 719ba289af8SRoger Chen dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 720ba289af8SRoger Chen return; 721ba289af8SRoger Chen } 722ba289af8SRoger Chen 723ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3366_GRF_SOC_CON6, 724ba289af8SRoger Chen RK3366_GMAC_PHY_INTF_SEL_RGMII | 725ba289af8SRoger Chen RK3366_GMAC_RMII_MODE_CLR); 726ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3366_GRF_SOC_CON7, 727eaf70ad1SWadim Egorov DELAY_ENABLE(RK3366, tx_delay, rx_delay) | 728ba289af8SRoger Chen RK3366_GMAC_CLK_RX_DL_CFG(rx_delay) | 729ba289af8SRoger Chen RK3366_GMAC_CLK_TX_DL_CFG(tx_delay)); 730ba289af8SRoger Chen } 731ba289af8SRoger Chen 732ba289af8SRoger Chen static void rk3366_set_to_rmii(struct rk_priv_data *bsp_priv) 733ba289af8SRoger Chen { 734ba289af8SRoger Chen struct device *dev = &bsp_priv->pdev->dev; 735ba289af8SRoger Chen 736ba289af8SRoger Chen if (IS_ERR(bsp_priv->grf)) { 737ba289af8SRoger Chen dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 738ba289af8SRoger Chen return; 739ba289af8SRoger Chen } 740ba289af8SRoger Chen 741ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3366_GRF_SOC_CON6, 742ba289af8SRoger Chen RK3366_GMAC_PHY_INTF_SEL_RMII | RK3366_GMAC_RMII_MODE); 743ba289af8SRoger Chen } 744ba289af8SRoger Chen 745ba289af8SRoger Chen static void rk3366_set_rgmii_speed(struct rk_priv_data *bsp_priv, int speed) 746ba289af8SRoger Chen { 747ba289af8SRoger Chen struct device *dev = &bsp_priv->pdev->dev; 748ba289af8SRoger Chen 749ba289af8SRoger Chen if (IS_ERR(bsp_priv->grf)) { 750ba289af8SRoger Chen dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 751ba289af8SRoger Chen return; 752ba289af8SRoger Chen } 753ba289af8SRoger Chen 754ba289af8SRoger Chen if (speed == 10) 755ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3366_GRF_SOC_CON6, 756ba289af8SRoger Chen RK3366_GMAC_CLK_2_5M); 757ba289af8SRoger Chen else if (speed == 100) 758ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3366_GRF_SOC_CON6, 759ba289af8SRoger Chen RK3366_GMAC_CLK_25M); 760ba289af8SRoger Chen else if (speed == 1000) 761ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3366_GRF_SOC_CON6, 762ba289af8SRoger Chen RK3366_GMAC_CLK_125M); 763ba289af8SRoger Chen else 764ba289af8SRoger Chen dev_err(dev, "unknown speed value for RGMII! speed=%d", speed); 765ba289af8SRoger Chen } 766ba289af8SRoger Chen 767ba289af8SRoger Chen static void rk3366_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 768ba289af8SRoger Chen { 769ba289af8SRoger Chen struct device *dev = &bsp_priv->pdev->dev; 770ba289af8SRoger Chen 771ba289af8SRoger Chen if (IS_ERR(bsp_priv->grf)) { 772ba289af8SRoger Chen dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 773ba289af8SRoger Chen return; 774ba289af8SRoger Chen } 775ba289af8SRoger Chen 776ba289af8SRoger Chen if (speed == 10) { 777ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3366_GRF_SOC_CON6, 778ba289af8SRoger Chen RK3366_GMAC_RMII_CLK_2_5M | 779ba289af8SRoger Chen RK3366_GMAC_SPEED_10M); 780ba289af8SRoger Chen } else if (speed == 100) { 781ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3366_GRF_SOC_CON6, 782ba289af8SRoger Chen RK3366_GMAC_RMII_CLK_25M | 783ba289af8SRoger Chen RK3366_GMAC_SPEED_100M); 784ba289af8SRoger Chen } else { 785ba289af8SRoger Chen dev_err(dev, "unknown speed value for RMII! speed=%d", speed); 786ba289af8SRoger Chen } 787ba289af8SRoger Chen } 788ba289af8SRoger Chen 789ba289af8SRoger Chen static const struct rk_gmac_ops rk3366_ops = { 790ba289af8SRoger Chen .set_to_rgmii = rk3366_set_to_rgmii, 791ba289af8SRoger Chen .set_to_rmii = rk3366_set_to_rmii, 792ba289af8SRoger Chen .set_rgmii_speed = rk3366_set_rgmii_speed, 793ba289af8SRoger Chen .set_rmii_speed = rk3366_set_rmii_speed, 794ba289af8SRoger Chen }; 795ba289af8SRoger Chen 796df558854SHeiko Stübner #define RK3368_GRF_SOC_CON15 0x043c 797df558854SHeiko Stübner #define RK3368_GRF_SOC_CON16 0x0440 798df558854SHeiko Stübner 799df558854SHeiko Stübner /* RK3368_GRF_SOC_CON15 */ 800df558854SHeiko Stübner #define RK3368_GMAC_PHY_INTF_SEL_RGMII (GRF_BIT(9) | GRF_CLR_BIT(10) | \ 801df558854SHeiko Stübner GRF_CLR_BIT(11)) 802df558854SHeiko Stübner #define RK3368_GMAC_PHY_INTF_SEL_RMII (GRF_CLR_BIT(9) | GRF_CLR_BIT(10) | \ 803df558854SHeiko Stübner GRF_BIT(11)) 804df558854SHeiko Stübner #define RK3368_GMAC_FLOW_CTRL GRF_BIT(8) 805df558854SHeiko Stübner #define RK3368_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(8) 806df558854SHeiko Stübner #define RK3368_GMAC_SPEED_10M GRF_CLR_BIT(7) 807df558854SHeiko Stübner #define RK3368_GMAC_SPEED_100M GRF_BIT(7) 808df558854SHeiko Stübner #define RK3368_GMAC_RMII_CLK_25M GRF_BIT(3) 809df558854SHeiko Stübner #define RK3368_GMAC_RMII_CLK_2_5M GRF_CLR_BIT(3) 810df558854SHeiko Stübner #define RK3368_GMAC_CLK_125M (GRF_CLR_BIT(4) | GRF_CLR_BIT(5)) 811df558854SHeiko Stübner #define RK3368_GMAC_CLK_25M (GRF_BIT(4) | GRF_BIT(5)) 812df558854SHeiko Stübner #define RK3368_GMAC_CLK_2_5M (GRF_CLR_BIT(4) | GRF_BIT(5)) 813df558854SHeiko Stübner #define RK3368_GMAC_RMII_MODE GRF_BIT(6) 814df558854SHeiko Stübner #define RK3368_GMAC_RMII_MODE_CLR GRF_CLR_BIT(6) 815df558854SHeiko Stübner 816df558854SHeiko Stübner /* RK3368_GRF_SOC_CON16 */ 817df558854SHeiko Stübner #define RK3368_GMAC_TXCLK_DLY_ENABLE GRF_BIT(7) 818df558854SHeiko Stübner #define RK3368_GMAC_TXCLK_DLY_DISABLE GRF_CLR_BIT(7) 819df558854SHeiko Stübner #define RK3368_GMAC_RXCLK_DLY_ENABLE GRF_BIT(15) 820df558854SHeiko Stübner #define RK3368_GMAC_RXCLK_DLY_DISABLE GRF_CLR_BIT(15) 821df558854SHeiko Stübner #define RK3368_GMAC_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 8) 822df558854SHeiko Stübner #define RK3368_GMAC_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 0) 823df558854SHeiko Stübner 824df558854SHeiko Stübner static void rk3368_set_to_rgmii(struct rk_priv_data *bsp_priv, 825df558854SHeiko Stübner int tx_delay, int rx_delay) 826df558854SHeiko Stübner { 827df558854SHeiko Stübner struct device *dev = &bsp_priv->pdev->dev; 828df558854SHeiko Stübner 829df558854SHeiko Stübner if (IS_ERR(bsp_priv->grf)) { 830df558854SHeiko Stübner dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 831df558854SHeiko Stübner return; 832df558854SHeiko Stübner } 833df558854SHeiko Stübner 834df558854SHeiko Stübner regmap_write(bsp_priv->grf, RK3368_GRF_SOC_CON15, 835df558854SHeiko Stübner RK3368_GMAC_PHY_INTF_SEL_RGMII | 836df558854SHeiko Stübner RK3368_GMAC_RMII_MODE_CLR); 837df558854SHeiko Stübner regmap_write(bsp_priv->grf, RK3368_GRF_SOC_CON16, 838eaf70ad1SWadim Egorov DELAY_ENABLE(RK3368, tx_delay, rx_delay) | 839df558854SHeiko Stübner RK3368_GMAC_CLK_RX_DL_CFG(rx_delay) | 840df558854SHeiko Stübner RK3368_GMAC_CLK_TX_DL_CFG(tx_delay)); 841df558854SHeiko Stübner } 842df558854SHeiko Stübner 843df558854SHeiko Stübner static void rk3368_set_to_rmii(struct rk_priv_data *bsp_priv) 844df558854SHeiko Stübner { 845df558854SHeiko Stübner struct device *dev = &bsp_priv->pdev->dev; 846df558854SHeiko Stübner 847df558854SHeiko Stübner if (IS_ERR(bsp_priv->grf)) { 848df558854SHeiko Stübner dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 849df558854SHeiko Stübner return; 850df558854SHeiko Stübner } 851df558854SHeiko Stübner 852df558854SHeiko Stübner regmap_write(bsp_priv->grf, RK3368_GRF_SOC_CON15, 853df558854SHeiko Stübner RK3368_GMAC_PHY_INTF_SEL_RMII | RK3368_GMAC_RMII_MODE); 854df558854SHeiko Stübner } 855df558854SHeiko Stübner 856df558854SHeiko Stübner static void rk3368_set_rgmii_speed(struct rk_priv_data *bsp_priv, int speed) 857df558854SHeiko Stübner { 858df558854SHeiko Stübner struct device *dev = &bsp_priv->pdev->dev; 859df558854SHeiko Stübner 860df558854SHeiko Stübner if (IS_ERR(bsp_priv->grf)) { 861df558854SHeiko Stübner dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 862df558854SHeiko Stübner return; 863df558854SHeiko Stübner } 864df558854SHeiko Stübner 865df558854SHeiko Stübner if (speed == 10) 866df558854SHeiko Stübner regmap_write(bsp_priv->grf, RK3368_GRF_SOC_CON15, 867df558854SHeiko Stübner RK3368_GMAC_CLK_2_5M); 868df558854SHeiko Stübner else if (speed == 100) 869df558854SHeiko Stübner regmap_write(bsp_priv->grf, RK3368_GRF_SOC_CON15, 870df558854SHeiko Stübner RK3368_GMAC_CLK_25M); 871df558854SHeiko Stübner else if (speed == 1000) 872df558854SHeiko Stübner regmap_write(bsp_priv->grf, RK3368_GRF_SOC_CON15, 873df558854SHeiko Stübner RK3368_GMAC_CLK_125M); 874df558854SHeiko Stübner else 875df558854SHeiko Stübner dev_err(dev, "unknown speed value for RGMII! speed=%d", speed); 876df558854SHeiko Stübner } 877df558854SHeiko Stübner 878df558854SHeiko Stübner static void rk3368_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 879df558854SHeiko Stübner { 880df558854SHeiko Stübner struct device *dev = &bsp_priv->pdev->dev; 881df558854SHeiko Stübner 882df558854SHeiko Stübner if (IS_ERR(bsp_priv->grf)) { 883df558854SHeiko Stübner dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 884df558854SHeiko Stübner return; 885df558854SHeiko Stübner } 886df558854SHeiko Stübner 887df558854SHeiko Stübner if (speed == 10) { 888df558854SHeiko Stübner regmap_write(bsp_priv->grf, RK3368_GRF_SOC_CON15, 889df558854SHeiko Stübner RK3368_GMAC_RMII_CLK_2_5M | 890df558854SHeiko Stübner RK3368_GMAC_SPEED_10M); 891df558854SHeiko Stübner } else if (speed == 100) { 892df558854SHeiko Stübner regmap_write(bsp_priv->grf, RK3368_GRF_SOC_CON15, 893df558854SHeiko Stübner RK3368_GMAC_RMII_CLK_25M | 894df558854SHeiko Stübner RK3368_GMAC_SPEED_100M); 895df558854SHeiko Stübner } else { 896df558854SHeiko Stübner dev_err(dev, "unknown speed value for RMII! speed=%d", speed); 897df558854SHeiko Stübner } 898df558854SHeiko Stübner } 899df558854SHeiko Stübner 90092c2588fSJoachim Eastwood static const struct rk_gmac_ops rk3368_ops = { 901df558854SHeiko Stübner .set_to_rgmii = rk3368_set_to_rgmii, 902df558854SHeiko Stübner .set_to_rmii = rk3368_set_to_rmii, 903df558854SHeiko Stübner .set_rgmii_speed = rk3368_set_rgmii_speed, 904df558854SHeiko Stübner .set_rmii_speed = rk3368_set_rmii_speed, 905df558854SHeiko Stübner }; 906df558854SHeiko Stübner 907ba289af8SRoger Chen #define RK3399_GRF_SOC_CON5 0xc214 908ba289af8SRoger Chen #define RK3399_GRF_SOC_CON6 0xc218 909ba289af8SRoger Chen 910ba289af8SRoger Chen /* RK3399_GRF_SOC_CON5 */ 911ba289af8SRoger Chen #define RK3399_GMAC_PHY_INTF_SEL_RGMII (GRF_BIT(9) | GRF_CLR_BIT(10) | \ 912ba289af8SRoger Chen GRF_CLR_BIT(11)) 913ba289af8SRoger Chen #define RK3399_GMAC_PHY_INTF_SEL_RMII (GRF_CLR_BIT(9) | GRF_CLR_BIT(10) | \ 914ba289af8SRoger Chen GRF_BIT(11)) 915ba289af8SRoger Chen #define RK3399_GMAC_FLOW_CTRL GRF_BIT(8) 916ba289af8SRoger Chen #define RK3399_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(8) 917ba289af8SRoger Chen #define RK3399_GMAC_SPEED_10M GRF_CLR_BIT(7) 918ba289af8SRoger Chen #define RK3399_GMAC_SPEED_100M GRF_BIT(7) 919ba289af8SRoger Chen #define RK3399_GMAC_RMII_CLK_25M GRF_BIT(3) 920ba289af8SRoger Chen #define RK3399_GMAC_RMII_CLK_2_5M GRF_CLR_BIT(3) 921ba289af8SRoger Chen #define RK3399_GMAC_CLK_125M (GRF_CLR_BIT(4) | GRF_CLR_BIT(5)) 922ba289af8SRoger Chen #define RK3399_GMAC_CLK_25M (GRF_BIT(4) | GRF_BIT(5)) 923ba289af8SRoger Chen #define RK3399_GMAC_CLK_2_5M (GRF_CLR_BIT(4) | GRF_BIT(5)) 924ba289af8SRoger Chen #define RK3399_GMAC_RMII_MODE GRF_BIT(6) 925ba289af8SRoger Chen #define RK3399_GMAC_RMII_MODE_CLR GRF_CLR_BIT(6) 926ba289af8SRoger Chen 927ba289af8SRoger Chen /* RK3399_GRF_SOC_CON6 */ 928ba289af8SRoger Chen #define RK3399_GMAC_TXCLK_DLY_ENABLE GRF_BIT(7) 929ba289af8SRoger Chen #define RK3399_GMAC_TXCLK_DLY_DISABLE GRF_CLR_BIT(7) 930ba289af8SRoger Chen #define RK3399_GMAC_RXCLK_DLY_ENABLE GRF_BIT(15) 931ba289af8SRoger Chen #define RK3399_GMAC_RXCLK_DLY_DISABLE GRF_CLR_BIT(15) 932ba289af8SRoger Chen #define RK3399_GMAC_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 8) 933ba289af8SRoger Chen #define RK3399_GMAC_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 0) 934ba289af8SRoger Chen 935ba289af8SRoger Chen static void rk3399_set_to_rgmii(struct rk_priv_data *bsp_priv, 936ba289af8SRoger Chen int tx_delay, int rx_delay) 937ba289af8SRoger Chen { 938ba289af8SRoger Chen struct device *dev = &bsp_priv->pdev->dev; 939ba289af8SRoger Chen 940ba289af8SRoger Chen if (IS_ERR(bsp_priv->grf)) { 941ba289af8SRoger Chen dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 942ba289af8SRoger Chen return; 943ba289af8SRoger Chen } 944ba289af8SRoger Chen 945ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3399_GRF_SOC_CON5, 946ba289af8SRoger Chen RK3399_GMAC_PHY_INTF_SEL_RGMII | 947ba289af8SRoger Chen RK3399_GMAC_RMII_MODE_CLR); 948ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3399_GRF_SOC_CON6, 949eaf70ad1SWadim Egorov DELAY_ENABLE(RK3399, tx_delay, rx_delay) | 950ba289af8SRoger Chen RK3399_GMAC_CLK_RX_DL_CFG(rx_delay) | 951ba289af8SRoger Chen RK3399_GMAC_CLK_TX_DL_CFG(tx_delay)); 952ba289af8SRoger Chen } 953ba289af8SRoger Chen 954ba289af8SRoger Chen static void rk3399_set_to_rmii(struct rk_priv_data *bsp_priv) 955ba289af8SRoger Chen { 956ba289af8SRoger Chen struct device *dev = &bsp_priv->pdev->dev; 957ba289af8SRoger Chen 958ba289af8SRoger Chen if (IS_ERR(bsp_priv->grf)) { 959ba289af8SRoger Chen dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 960ba289af8SRoger Chen return; 961ba289af8SRoger Chen } 962ba289af8SRoger Chen 963ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3399_GRF_SOC_CON5, 964ba289af8SRoger Chen RK3399_GMAC_PHY_INTF_SEL_RMII | RK3399_GMAC_RMII_MODE); 965ba289af8SRoger Chen } 966ba289af8SRoger Chen 967ba289af8SRoger Chen static void rk3399_set_rgmii_speed(struct rk_priv_data *bsp_priv, int speed) 968ba289af8SRoger Chen { 969ba289af8SRoger Chen struct device *dev = &bsp_priv->pdev->dev; 970ba289af8SRoger Chen 971ba289af8SRoger Chen if (IS_ERR(bsp_priv->grf)) { 972ba289af8SRoger Chen dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 973ba289af8SRoger Chen return; 974ba289af8SRoger Chen } 975ba289af8SRoger Chen 976ba289af8SRoger Chen if (speed == 10) 977ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3399_GRF_SOC_CON5, 978ba289af8SRoger Chen RK3399_GMAC_CLK_2_5M); 979ba289af8SRoger Chen else if (speed == 100) 980ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3399_GRF_SOC_CON5, 981ba289af8SRoger Chen RK3399_GMAC_CLK_25M); 982ba289af8SRoger Chen else if (speed == 1000) 983ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3399_GRF_SOC_CON5, 984ba289af8SRoger Chen RK3399_GMAC_CLK_125M); 985ba289af8SRoger Chen else 986ba289af8SRoger Chen dev_err(dev, "unknown speed value for RGMII! speed=%d", speed); 987ba289af8SRoger Chen } 988ba289af8SRoger Chen 989ba289af8SRoger Chen static void rk3399_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 990ba289af8SRoger Chen { 991ba289af8SRoger Chen struct device *dev = &bsp_priv->pdev->dev; 992ba289af8SRoger Chen 993ba289af8SRoger Chen if (IS_ERR(bsp_priv->grf)) { 994ba289af8SRoger Chen dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 995ba289af8SRoger Chen return; 996ba289af8SRoger Chen } 997ba289af8SRoger Chen 998ba289af8SRoger Chen if (speed == 10) { 999ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3399_GRF_SOC_CON5, 1000ba289af8SRoger Chen RK3399_GMAC_RMII_CLK_2_5M | 1001ba289af8SRoger Chen RK3399_GMAC_SPEED_10M); 1002ba289af8SRoger Chen } else if (speed == 100) { 1003ba289af8SRoger Chen regmap_write(bsp_priv->grf, RK3399_GRF_SOC_CON5, 1004ba289af8SRoger Chen RK3399_GMAC_RMII_CLK_25M | 1005ba289af8SRoger Chen RK3399_GMAC_SPEED_100M); 1006ba289af8SRoger Chen } else { 1007ba289af8SRoger Chen dev_err(dev, "unknown speed value for RMII! speed=%d", speed); 1008ba289af8SRoger Chen } 1009ba289af8SRoger Chen } 1010ba289af8SRoger Chen 1011ba289af8SRoger Chen static const struct rk_gmac_ops rk3399_ops = { 1012ba289af8SRoger Chen .set_to_rgmii = rk3399_set_to_rgmii, 1013ba289af8SRoger Chen .set_to_rmii = rk3399_set_to_rmii, 1014ba289af8SRoger Chen .set_rgmii_speed = rk3399_set_rgmii_speed, 1015ba289af8SRoger Chen .set_rmii_speed = rk3399_set_rmii_speed, 1016ba289af8SRoger Chen }; 1017ba289af8SRoger Chen 10183bb3d6b1SDavid Wu #define RK3568_GRF_GMAC0_CON0 0x0380 10193bb3d6b1SDavid Wu #define RK3568_GRF_GMAC0_CON1 0x0384 10203bb3d6b1SDavid Wu #define RK3568_GRF_GMAC1_CON0 0x0388 10213bb3d6b1SDavid Wu #define RK3568_GRF_GMAC1_CON1 0x038c 10223bb3d6b1SDavid Wu 10233bb3d6b1SDavid Wu /* RK3568_GRF_GMAC0_CON1 && RK3568_GRF_GMAC1_CON1 */ 10243bb3d6b1SDavid Wu #define RK3568_GMAC_PHY_INTF_SEL_RGMII \ 10253bb3d6b1SDavid Wu (GRF_BIT(4) | GRF_CLR_BIT(5) | GRF_CLR_BIT(6)) 10263bb3d6b1SDavid Wu #define RK3568_GMAC_PHY_INTF_SEL_RMII \ 10273bb3d6b1SDavid Wu (GRF_CLR_BIT(4) | GRF_CLR_BIT(5) | GRF_BIT(6)) 10283bb3d6b1SDavid Wu #define RK3568_GMAC_FLOW_CTRL GRF_BIT(3) 10293bb3d6b1SDavid Wu #define RK3568_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(3) 10303bb3d6b1SDavid Wu #define RK3568_GMAC_RXCLK_DLY_ENABLE GRF_BIT(1) 10313bb3d6b1SDavid Wu #define RK3568_GMAC_RXCLK_DLY_DISABLE GRF_CLR_BIT(1) 10323bb3d6b1SDavid Wu #define RK3568_GMAC_TXCLK_DLY_ENABLE GRF_BIT(0) 10333bb3d6b1SDavid Wu #define RK3568_GMAC_TXCLK_DLY_DISABLE GRF_CLR_BIT(0) 10343bb3d6b1SDavid Wu 10353bb3d6b1SDavid Wu /* RK3568_GRF_GMAC0_CON0 && RK3568_GRF_GMAC1_CON0 */ 10363bb3d6b1SDavid Wu #define RK3568_GMAC_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 8) 10373bb3d6b1SDavid Wu #define RK3568_GMAC_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 0) 10383bb3d6b1SDavid Wu 10393bb3d6b1SDavid Wu static void rk3568_set_to_rgmii(struct rk_priv_data *bsp_priv, 10403bb3d6b1SDavid Wu int tx_delay, int rx_delay) 10413bb3d6b1SDavid Wu { 10423bb3d6b1SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 10433bb3d6b1SDavid Wu u32 con0, con1; 10443bb3d6b1SDavid Wu 10453bb3d6b1SDavid Wu if (IS_ERR(bsp_priv->grf)) { 10463bb3d6b1SDavid Wu dev_err(dev, "Missing rockchip,grf property\n"); 10473bb3d6b1SDavid Wu return; 10483bb3d6b1SDavid Wu } 10493bb3d6b1SDavid Wu 10503bb3d6b1SDavid Wu con0 = (bsp_priv->id == 1) ? RK3568_GRF_GMAC1_CON0 : 10513bb3d6b1SDavid Wu RK3568_GRF_GMAC0_CON0; 10523bb3d6b1SDavid Wu con1 = (bsp_priv->id == 1) ? RK3568_GRF_GMAC1_CON1 : 10533bb3d6b1SDavid Wu RK3568_GRF_GMAC0_CON1; 10543bb3d6b1SDavid Wu 10553bb3d6b1SDavid Wu regmap_write(bsp_priv->grf, con0, 10563bb3d6b1SDavid Wu RK3568_GMAC_CLK_RX_DL_CFG(rx_delay) | 10573bb3d6b1SDavid Wu RK3568_GMAC_CLK_TX_DL_CFG(tx_delay)); 10583bb3d6b1SDavid Wu 10593bb3d6b1SDavid Wu regmap_write(bsp_priv->grf, con1, 10603bb3d6b1SDavid Wu RK3568_GMAC_PHY_INTF_SEL_RGMII | 10613bb3d6b1SDavid Wu RK3568_GMAC_RXCLK_DLY_ENABLE | 10623bb3d6b1SDavid Wu RK3568_GMAC_TXCLK_DLY_ENABLE); 10633bb3d6b1SDavid Wu } 10643bb3d6b1SDavid Wu 10653bb3d6b1SDavid Wu static void rk3568_set_to_rmii(struct rk_priv_data *bsp_priv) 10663bb3d6b1SDavid Wu { 10673bb3d6b1SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 10683bb3d6b1SDavid Wu u32 con1; 10693bb3d6b1SDavid Wu 10703bb3d6b1SDavid Wu if (IS_ERR(bsp_priv->grf)) { 10713bb3d6b1SDavid Wu dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 10723bb3d6b1SDavid Wu return; 10733bb3d6b1SDavid Wu } 10743bb3d6b1SDavid Wu 10753bb3d6b1SDavid Wu con1 = (bsp_priv->id == 1) ? RK3568_GRF_GMAC1_CON1 : 10763bb3d6b1SDavid Wu RK3568_GRF_GMAC0_CON1; 10773bb3d6b1SDavid Wu regmap_write(bsp_priv->grf, con1, RK3568_GMAC_PHY_INTF_SEL_RMII); 10783bb3d6b1SDavid Wu } 10793bb3d6b1SDavid Wu 10803bb3d6b1SDavid Wu static void rk3568_set_gmac_speed(struct rk_priv_data *bsp_priv, int speed) 10813bb3d6b1SDavid Wu { 1082ea449f7fSSebastian Reichel struct clk *clk_mac_speed = bsp_priv->clks[RK_CLK_MAC_SPEED].clk; 10833bb3d6b1SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 10843bb3d6b1SDavid Wu unsigned long rate; 10853bb3d6b1SDavid Wu int ret; 10863bb3d6b1SDavid Wu 10873bb3d6b1SDavid Wu switch (speed) { 10883bb3d6b1SDavid Wu case 10: 10893bb3d6b1SDavid Wu rate = 2500000; 10903bb3d6b1SDavid Wu break; 10913bb3d6b1SDavid Wu case 100: 10923bb3d6b1SDavid Wu rate = 25000000; 10933bb3d6b1SDavid Wu break; 10943bb3d6b1SDavid Wu case 1000: 10953bb3d6b1SDavid Wu rate = 125000000; 10963bb3d6b1SDavid Wu break; 10973bb3d6b1SDavid Wu default: 10983bb3d6b1SDavid Wu dev_err(dev, "unknown speed value for GMAC speed=%d", speed); 10993bb3d6b1SDavid Wu return; 11003bb3d6b1SDavid Wu } 11013bb3d6b1SDavid Wu 1102ea449f7fSSebastian Reichel ret = clk_set_rate(clk_mac_speed, rate); 11033bb3d6b1SDavid Wu if (ret) 11043bb3d6b1SDavid Wu dev_err(dev, "%s: set clk_mac_speed rate %ld failed %d\n", 11053bb3d6b1SDavid Wu __func__, rate, ret); 11063bb3d6b1SDavid Wu } 11073bb3d6b1SDavid Wu 11083bb3d6b1SDavid Wu static const struct rk_gmac_ops rk3568_ops = { 11093bb3d6b1SDavid Wu .set_to_rgmii = rk3568_set_to_rgmii, 11103bb3d6b1SDavid Wu .set_to_rmii = rk3568_set_to_rmii, 11113bb3d6b1SDavid Wu .set_rgmii_speed = rk3568_set_gmac_speed, 11123bb3d6b1SDavid Wu .set_rmii_speed = rk3568_set_gmac_speed, 11130546b224SJohn Keeping .regs_valid = true, 11143bb3d6b1SDavid Wu .regs = { 11153bb3d6b1SDavid Wu 0xfe2a0000, /* gmac0 */ 11163bb3d6b1SDavid Wu 0xfe010000, /* gmac1 */ 11173bb3d6b1SDavid Wu 0x0, /* sentinel */ 11183bb3d6b1SDavid Wu }, 11193bb3d6b1SDavid Wu }; 11203bb3d6b1SDavid Wu 11212f2b60a0SDavid Wu /* sys_grf */ 11222f2b60a0SDavid Wu #define RK3588_GRF_GMAC_CON7 0X031c 11232f2b60a0SDavid Wu #define RK3588_GRF_GMAC_CON8 0X0320 11242f2b60a0SDavid Wu #define RK3588_GRF_GMAC_CON9 0X0324 11252f2b60a0SDavid Wu 11262f2b60a0SDavid Wu #define RK3588_GMAC_RXCLK_DLY_ENABLE(id) GRF_BIT(2 * (id) + 3) 11272f2b60a0SDavid Wu #define RK3588_GMAC_RXCLK_DLY_DISABLE(id) GRF_CLR_BIT(2 * (id) + 3) 11282f2b60a0SDavid Wu #define RK3588_GMAC_TXCLK_DLY_ENABLE(id) GRF_BIT(2 * (id) + 2) 11292f2b60a0SDavid Wu #define RK3588_GMAC_TXCLK_DLY_DISABLE(id) GRF_CLR_BIT(2 * (id) + 2) 11302f2b60a0SDavid Wu 11312f2b60a0SDavid Wu #define RK3588_GMAC_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0xFF, 8) 11322f2b60a0SDavid Wu #define RK3588_GMAC_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0xFF, 0) 11332f2b60a0SDavid Wu 11342f2b60a0SDavid Wu /* php_grf */ 11352f2b60a0SDavid Wu #define RK3588_GRF_GMAC_CON0 0X0008 11362f2b60a0SDavid Wu #define RK3588_GRF_CLK_CON1 0X0070 11372f2b60a0SDavid Wu 11382f2b60a0SDavid Wu #define RK3588_GMAC_PHY_INTF_SEL_RGMII(id) \ 11392f2b60a0SDavid Wu (GRF_BIT(3 + (id) * 6) | GRF_CLR_BIT(4 + (id) * 6) | GRF_CLR_BIT(5 + (id) * 6)) 11402f2b60a0SDavid Wu #define RK3588_GMAC_PHY_INTF_SEL_RMII(id) \ 11412f2b60a0SDavid Wu (GRF_CLR_BIT(3 + (id) * 6) | GRF_CLR_BIT(4 + (id) * 6) | GRF_BIT(5 + (id) * 6)) 11422f2b60a0SDavid Wu 11432f2b60a0SDavid Wu #define RK3588_GMAC_CLK_RMII_MODE(id) GRF_BIT(5 * (id)) 11442f2b60a0SDavid Wu #define RK3588_GMAC_CLK_RGMII_MODE(id) GRF_CLR_BIT(5 * (id)) 11452f2b60a0SDavid Wu 11462f2b60a0SDavid Wu #define RK3588_GMAC_CLK_SELET_CRU(id) GRF_BIT(5 * (id) + 4) 11472f2b60a0SDavid Wu #define RK3588_GMAC_CLK_SELET_IO(id) GRF_CLR_BIT(5 * (id) + 4) 11482f2b60a0SDavid Wu 11492f2b60a0SDavid Wu #define RK3588_GMA_CLK_RMII_DIV2(id) GRF_BIT(5 * (id) + 2) 11502f2b60a0SDavid Wu #define RK3588_GMA_CLK_RMII_DIV20(id) GRF_CLR_BIT(5 * (id) + 2) 11512f2b60a0SDavid Wu 11522f2b60a0SDavid Wu #define RK3588_GMAC_CLK_RGMII_DIV1(id) \ 11532f2b60a0SDavid Wu (GRF_CLR_BIT(5 * (id) + 2) | GRF_CLR_BIT(5 * (id) + 3)) 11542f2b60a0SDavid Wu #define RK3588_GMAC_CLK_RGMII_DIV5(id) \ 11552f2b60a0SDavid Wu (GRF_BIT(5 * (id) + 2) | GRF_BIT(5 * (id) + 3)) 11562f2b60a0SDavid Wu #define RK3588_GMAC_CLK_RGMII_DIV50(id) \ 11572f2b60a0SDavid Wu (GRF_CLR_BIT(5 * (id) + 2) | GRF_BIT(5 * (id) + 3)) 11582f2b60a0SDavid Wu 11592f2b60a0SDavid Wu #define RK3588_GMAC_CLK_RMII_GATE(id) GRF_BIT(5 * (id) + 1) 11602f2b60a0SDavid Wu #define RK3588_GMAC_CLK_RMII_NOGATE(id) GRF_CLR_BIT(5 * (id) + 1) 11612f2b60a0SDavid Wu 11622f2b60a0SDavid Wu static void rk3588_set_to_rgmii(struct rk_priv_data *bsp_priv, 11632f2b60a0SDavid Wu int tx_delay, int rx_delay) 11642f2b60a0SDavid Wu { 11652f2b60a0SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 11662f2b60a0SDavid Wu u32 offset_con, id = bsp_priv->id; 11672f2b60a0SDavid Wu 11682f2b60a0SDavid Wu if (IS_ERR(bsp_priv->grf) || IS_ERR(bsp_priv->php_grf)) { 11692f2b60a0SDavid Wu dev_err(dev, "Missing rockchip,grf or rockchip,php_grf property\n"); 11702f2b60a0SDavid Wu return; 11712f2b60a0SDavid Wu } 11722f2b60a0SDavid Wu 11732f2b60a0SDavid Wu offset_con = bsp_priv->id == 1 ? RK3588_GRF_GMAC_CON9 : 11742f2b60a0SDavid Wu RK3588_GRF_GMAC_CON8; 11752f2b60a0SDavid Wu 11762f2b60a0SDavid Wu regmap_write(bsp_priv->php_grf, RK3588_GRF_GMAC_CON0, 11772f2b60a0SDavid Wu RK3588_GMAC_PHY_INTF_SEL_RGMII(id)); 11782f2b60a0SDavid Wu 11792f2b60a0SDavid Wu regmap_write(bsp_priv->php_grf, RK3588_GRF_CLK_CON1, 11802f2b60a0SDavid Wu RK3588_GMAC_CLK_RGMII_MODE(id)); 11812f2b60a0SDavid Wu 11822f2b60a0SDavid Wu regmap_write(bsp_priv->grf, RK3588_GRF_GMAC_CON7, 11832f2b60a0SDavid Wu RK3588_GMAC_RXCLK_DLY_ENABLE(id) | 11842f2b60a0SDavid Wu RK3588_GMAC_TXCLK_DLY_ENABLE(id)); 11852f2b60a0SDavid Wu 11862f2b60a0SDavid Wu regmap_write(bsp_priv->grf, offset_con, 11872f2b60a0SDavid Wu RK3588_GMAC_CLK_RX_DL_CFG(rx_delay) | 11882f2b60a0SDavid Wu RK3588_GMAC_CLK_TX_DL_CFG(tx_delay)); 11892f2b60a0SDavid Wu } 11902f2b60a0SDavid Wu 11912f2b60a0SDavid Wu static void rk3588_set_to_rmii(struct rk_priv_data *bsp_priv) 11922f2b60a0SDavid Wu { 11932f2b60a0SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 11942f2b60a0SDavid Wu 11952f2b60a0SDavid Wu if (IS_ERR(bsp_priv->php_grf)) { 11962f2b60a0SDavid Wu dev_err(dev, "%s: Missing rockchip,php_grf property\n", __func__); 11972f2b60a0SDavid Wu return; 11982f2b60a0SDavid Wu } 11992f2b60a0SDavid Wu 12002f2b60a0SDavid Wu regmap_write(bsp_priv->php_grf, RK3588_GRF_GMAC_CON0, 12012f2b60a0SDavid Wu RK3588_GMAC_PHY_INTF_SEL_RMII(bsp_priv->id)); 12022f2b60a0SDavid Wu 12032f2b60a0SDavid Wu regmap_write(bsp_priv->php_grf, RK3588_GRF_CLK_CON1, 12042f2b60a0SDavid Wu RK3588_GMAC_CLK_RMII_MODE(bsp_priv->id)); 12052f2b60a0SDavid Wu } 12062f2b60a0SDavid Wu 12072f2b60a0SDavid Wu static void rk3588_set_gmac_speed(struct rk_priv_data *bsp_priv, int speed) 12082f2b60a0SDavid Wu { 12092f2b60a0SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 12102f2b60a0SDavid Wu unsigned int val = 0, id = bsp_priv->id; 12112f2b60a0SDavid Wu 12122f2b60a0SDavid Wu switch (speed) { 12132f2b60a0SDavid Wu case 10: 12142f2b60a0SDavid Wu if (bsp_priv->phy_iface == PHY_INTERFACE_MODE_RMII) 12152f2b60a0SDavid Wu val = RK3588_GMA_CLK_RMII_DIV20(id); 12162f2b60a0SDavid Wu else 12172f2b60a0SDavid Wu val = RK3588_GMAC_CLK_RGMII_DIV50(id); 12182f2b60a0SDavid Wu break; 12192f2b60a0SDavid Wu case 100: 12202f2b60a0SDavid Wu if (bsp_priv->phy_iface == PHY_INTERFACE_MODE_RMII) 12212f2b60a0SDavid Wu val = RK3588_GMA_CLK_RMII_DIV2(id); 12222f2b60a0SDavid Wu else 12232f2b60a0SDavid Wu val = RK3588_GMAC_CLK_RGMII_DIV5(id); 12242f2b60a0SDavid Wu break; 12252f2b60a0SDavid Wu case 1000: 12262f2b60a0SDavid Wu if (bsp_priv->phy_iface != PHY_INTERFACE_MODE_RMII) 12272f2b60a0SDavid Wu val = RK3588_GMAC_CLK_RGMII_DIV1(id); 12282f2b60a0SDavid Wu else 12292f2b60a0SDavid Wu goto err; 12302f2b60a0SDavid Wu break; 12312f2b60a0SDavid Wu default: 12322f2b60a0SDavid Wu goto err; 12332f2b60a0SDavid Wu } 12342f2b60a0SDavid Wu 12352f2b60a0SDavid Wu regmap_write(bsp_priv->php_grf, RK3588_GRF_CLK_CON1, val); 12362f2b60a0SDavid Wu 12372f2b60a0SDavid Wu return; 12382f2b60a0SDavid Wu err: 12392f2b60a0SDavid Wu dev_err(dev, "unknown speed value for GMAC speed=%d", speed); 12402f2b60a0SDavid Wu } 12412f2b60a0SDavid Wu 12422f2b60a0SDavid Wu static void rk3588_set_clock_selection(struct rk_priv_data *bsp_priv, bool input, 12432f2b60a0SDavid Wu bool enable) 12442f2b60a0SDavid Wu { 12452f2b60a0SDavid Wu unsigned int val = input ? RK3588_GMAC_CLK_SELET_IO(bsp_priv->id) : 12462f2b60a0SDavid Wu RK3588_GMAC_CLK_SELET_CRU(bsp_priv->id); 12472f2b60a0SDavid Wu 12482f2b60a0SDavid Wu val |= enable ? RK3588_GMAC_CLK_RMII_NOGATE(bsp_priv->id) : 12492f2b60a0SDavid Wu RK3588_GMAC_CLK_RMII_GATE(bsp_priv->id); 12502f2b60a0SDavid Wu 12512f2b60a0SDavid Wu regmap_write(bsp_priv->php_grf, RK3588_GRF_CLK_CON1, val); 12522f2b60a0SDavid Wu } 12532f2b60a0SDavid Wu 12542f2b60a0SDavid Wu static const struct rk_gmac_ops rk3588_ops = { 12552f2b60a0SDavid Wu .set_to_rgmii = rk3588_set_to_rgmii, 12562f2b60a0SDavid Wu .set_to_rmii = rk3588_set_to_rmii, 12572f2b60a0SDavid Wu .set_rgmii_speed = rk3588_set_gmac_speed, 12582f2b60a0SDavid Wu .set_rmii_speed = rk3588_set_gmac_speed, 12592f2b60a0SDavid Wu .set_clock_selection = rk3588_set_clock_selection, 126088619e77SBenjamin Gaignard .regs_valid = true, 126188619e77SBenjamin Gaignard .regs = { 126288619e77SBenjamin Gaignard 0xfe1b0000, /* gmac0 */ 126388619e77SBenjamin Gaignard 0xfe1c0000, /* gmac1 */ 126488619e77SBenjamin Gaignard 0x0, /* sentinel */ 126588619e77SBenjamin Gaignard }, 12662f2b60a0SDavid Wu }; 12672f2b60a0SDavid Wu 126889c9c163SDavid Wu #define RV1108_GRF_GMAC_CON0 0X0900 126989c9c163SDavid Wu 127089c9c163SDavid Wu /* RV1108_GRF_GMAC_CON0 */ 127189c9c163SDavid Wu #define RV1108_GMAC_PHY_INTF_SEL_RMII (GRF_CLR_BIT(4) | GRF_CLR_BIT(5) | \ 127289c9c163SDavid Wu GRF_BIT(6)) 127389c9c163SDavid Wu #define RV1108_GMAC_FLOW_CTRL GRF_BIT(3) 127489c9c163SDavid Wu #define RV1108_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(3) 127589c9c163SDavid Wu #define RV1108_GMAC_SPEED_10M GRF_CLR_BIT(2) 127689c9c163SDavid Wu #define RV1108_GMAC_SPEED_100M GRF_BIT(2) 127789c9c163SDavid Wu #define RV1108_GMAC_RMII_CLK_25M GRF_BIT(7) 127889c9c163SDavid Wu #define RV1108_GMAC_RMII_CLK_2_5M GRF_CLR_BIT(7) 127989c9c163SDavid Wu 128089c9c163SDavid Wu static void rv1108_set_to_rmii(struct rk_priv_data *bsp_priv) 128189c9c163SDavid Wu { 128289c9c163SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 128389c9c163SDavid Wu 128489c9c163SDavid Wu if (IS_ERR(bsp_priv->grf)) { 128589c9c163SDavid Wu dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 128689c9c163SDavid Wu return; 128789c9c163SDavid Wu } 128889c9c163SDavid Wu 128989c9c163SDavid Wu regmap_write(bsp_priv->grf, RV1108_GRF_GMAC_CON0, 129089c9c163SDavid Wu RV1108_GMAC_PHY_INTF_SEL_RMII); 129189c9c163SDavid Wu } 129289c9c163SDavid Wu 129389c9c163SDavid Wu static void rv1108_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 129489c9c163SDavid Wu { 129589c9c163SDavid Wu struct device *dev = &bsp_priv->pdev->dev; 129689c9c163SDavid Wu 129789c9c163SDavid Wu if (IS_ERR(bsp_priv->grf)) { 129889c9c163SDavid Wu dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 129989c9c163SDavid Wu return; 130089c9c163SDavid Wu } 130189c9c163SDavid Wu 130289c9c163SDavid Wu if (speed == 10) { 130389c9c163SDavid Wu regmap_write(bsp_priv->grf, RV1108_GRF_GMAC_CON0, 130489c9c163SDavid Wu RV1108_GMAC_RMII_CLK_2_5M | 130589c9c163SDavid Wu RV1108_GMAC_SPEED_10M); 130689c9c163SDavid Wu } else if (speed == 100) { 130789c9c163SDavid Wu regmap_write(bsp_priv->grf, RV1108_GRF_GMAC_CON0, 130889c9c163SDavid Wu RV1108_GMAC_RMII_CLK_25M | 130989c9c163SDavid Wu RV1108_GMAC_SPEED_100M); 131089c9c163SDavid Wu } else { 131189c9c163SDavid Wu dev_err(dev, "unknown speed value for RMII! speed=%d", speed); 131289c9c163SDavid Wu } 131389c9c163SDavid Wu } 131489c9c163SDavid Wu 131589c9c163SDavid Wu static const struct rk_gmac_ops rv1108_ops = { 131689c9c163SDavid Wu .set_to_rmii = rv1108_set_to_rmii, 131789c9c163SDavid Wu .set_rmii_speed = rv1108_set_rmii_speed, 131889c9c163SDavid Wu }; 131989c9c163SDavid Wu 1320c931b060SAnand Moon #define RV1126_GRF_GMAC_CON0 0X0070 1321c931b060SAnand Moon #define RV1126_GRF_GMAC_CON1 0X0074 1322c931b060SAnand Moon #define RV1126_GRF_GMAC_CON2 0X0078 1323c931b060SAnand Moon 1324c931b060SAnand Moon /* RV1126_GRF_GMAC_CON0 */ 1325c931b060SAnand Moon #define RV1126_GMAC_PHY_INTF_SEL_RGMII \ 1326c931b060SAnand Moon (GRF_BIT(4) | GRF_CLR_BIT(5) | GRF_CLR_BIT(6)) 1327c931b060SAnand Moon #define RV1126_GMAC_PHY_INTF_SEL_RMII \ 1328c931b060SAnand Moon (GRF_CLR_BIT(4) | GRF_CLR_BIT(5) | GRF_BIT(6)) 1329c931b060SAnand Moon #define RV1126_GMAC_FLOW_CTRL GRF_BIT(7) 1330c931b060SAnand Moon #define RV1126_GMAC_FLOW_CTRL_CLR GRF_CLR_BIT(7) 1331c931b060SAnand Moon #define RV1126_GMAC_M0_RXCLK_DLY_ENABLE GRF_BIT(1) 1332c931b060SAnand Moon #define RV1126_GMAC_M0_RXCLK_DLY_DISABLE GRF_CLR_BIT(1) 1333c931b060SAnand Moon #define RV1126_GMAC_M0_TXCLK_DLY_ENABLE GRF_BIT(0) 1334c931b060SAnand Moon #define RV1126_GMAC_M0_TXCLK_DLY_DISABLE GRF_CLR_BIT(0) 1335c931b060SAnand Moon #define RV1126_GMAC_M1_RXCLK_DLY_ENABLE GRF_BIT(3) 1336c931b060SAnand Moon #define RV1126_GMAC_M1_RXCLK_DLY_DISABLE GRF_CLR_BIT(3) 1337c931b060SAnand Moon #define RV1126_GMAC_M1_TXCLK_DLY_ENABLE GRF_BIT(2) 1338c931b060SAnand Moon #define RV1126_GMAC_M1_TXCLK_DLY_DISABLE GRF_CLR_BIT(2) 1339c931b060SAnand Moon 1340c931b060SAnand Moon /* RV1126_GRF_GMAC_CON1 */ 1341c931b060SAnand Moon #define RV1126_GMAC_M0_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 8) 1342c931b060SAnand Moon #define RV1126_GMAC_M0_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 0) 1343c931b060SAnand Moon /* RV1126_GRF_GMAC_CON2 */ 1344c931b060SAnand Moon #define RV1126_GMAC_M1_CLK_RX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 8) 1345c931b060SAnand Moon #define RV1126_GMAC_M1_CLK_TX_DL_CFG(val) HIWORD_UPDATE(val, 0x7F, 0) 1346c931b060SAnand Moon 1347c931b060SAnand Moon static void rv1126_set_to_rgmii(struct rk_priv_data *bsp_priv, 1348c931b060SAnand Moon int tx_delay, int rx_delay) 1349c931b060SAnand Moon { 1350c931b060SAnand Moon struct device *dev = &bsp_priv->pdev->dev; 1351c931b060SAnand Moon 1352c931b060SAnand Moon if (IS_ERR(bsp_priv->grf)) { 1353c931b060SAnand Moon dev_err(dev, "Missing rockchip,grf property\n"); 1354c931b060SAnand Moon return; 1355c931b060SAnand Moon } 1356c931b060SAnand Moon 1357c931b060SAnand Moon regmap_write(bsp_priv->grf, RV1126_GRF_GMAC_CON0, 1358c931b060SAnand Moon RV1126_GMAC_PHY_INTF_SEL_RGMII | 1359c931b060SAnand Moon RV1126_GMAC_M0_RXCLK_DLY_ENABLE | 1360c931b060SAnand Moon RV1126_GMAC_M0_TXCLK_DLY_ENABLE | 1361c931b060SAnand Moon RV1126_GMAC_M1_RXCLK_DLY_ENABLE | 1362c931b060SAnand Moon RV1126_GMAC_M1_TXCLK_DLY_ENABLE); 1363c931b060SAnand Moon 1364c931b060SAnand Moon regmap_write(bsp_priv->grf, RV1126_GRF_GMAC_CON1, 1365c931b060SAnand Moon RV1126_GMAC_M0_CLK_RX_DL_CFG(rx_delay) | 1366c931b060SAnand Moon RV1126_GMAC_M0_CLK_TX_DL_CFG(tx_delay)); 1367c931b060SAnand Moon 1368c931b060SAnand Moon regmap_write(bsp_priv->grf, RV1126_GRF_GMAC_CON2, 1369c931b060SAnand Moon RV1126_GMAC_M1_CLK_RX_DL_CFG(rx_delay) | 1370c931b060SAnand Moon RV1126_GMAC_M1_CLK_TX_DL_CFG(tx_delay)); 1371c931b060SAnand Moon } 1372c931b060SAnand Moon 1373c931b060SAnand Moon static void rv1126_set_to_rmii(struct rk_priv_data *bsp_priv) 1374c931b060SAnand Moon { 1375c931b060SAnand Moon struct device *dev = &bsp_priv->pdev->dev; 1376c931b060SAnand Moon 1377c931b060SAnand Moon if (IS_ERR(bsp_priv->grf)) { 1378c931b060SAnand Moon dev_err(dev, "%s: Missing rockchip,grf property\n", __func__); 1379c931b060SAnand Moon return; 1380c931b060SAnand Moon } 1381c931b060SAnand Moon 1382c931b060SAnand Moon regmap_write(bsp_priv->grf, RV1126_GRF_GMAC_CON0, 1383c931b060SAnand Moon RV1126_GMAC_PHY_INTF_SEL_RMII); 1384c931b060SAnand Moon } 1385c931b060SAnand Moon 1386c931b060SAnand Moon static void rv1126_set_rgmii_speed(struct rk_priv_data *bsp_priv, int speed) 1387c931b060SAnand Moon { 1388ea449f7fSSebastian Reichel struct clk *clk_mac_speed = bsp_priv->clks[RK_CLK_MAC_SPEED].clk; 1389c931b060SAnand Moon struct device *dev = &bsp_priv->pdev->dev; 1390c931b060SAnand Moon unsigned long rate; 1391c931b060SAnand Moon int ret; 1392c931b060SAnand Moon 1393c931b060SAnand Moon switch (speed) { 1394c931b060SAnand Moon case 10: 1395c931b060SAnand Moon rate = 2500000; 1396c931b060SAnand Moon break; 1397c931b060SAnand Moon case 100: 1398c931b060SAnand Moon rate = 25000000; 1399c931b060SAnand Moon break; 1400c931b060SAnand Moon case 1000: 1401c931b060SAnand Moon rate = 125000000; 1402c931b060SAnand Moon break; 1403c931b060SAnand Moon default: 1404c931b060SAnand Moon dev_err(dev, "unknown speed value for RGMII speed=%d", speed); 1405c931b060SAnand Moon return; 1406c931b060SAnand Moon } 1407c931b060SAnand Moon 1408ea449f7fSSebastian Reichel ret = clk_set_rate(clk_mac_speed, rate); 1409c931b060SAnand Moon if (ret) 1410c931b060SAnand Moon dev_err(dev, "%s: set clk_mac_speed rate %ld failed %d\n", 1411c931b060SAnand Moon __func__, rate, ret); 1412c931b060SAnand Moon } 1413c931b060SAnand Moon 1414c931b060SAnand Moon static void rv1126_set_rmii_speed(struct rk_priv_data *bsp_priv, int speed) 1415c931b060SAnand Moon { 1416ea449f7fSSebastian Reichel struct clk *clk_mac_speed = bsp_priv->clks[RK_CLK_MAC_SPEED].clk; 1417c931b060SAnand Moon struct device *dev = &bsp_priv->pdev->dev; 1418c931b060SAnand Moon unsigned long rate; 1419c931b060SAnand Moon int ret; 1420c931b060SAnand Moon 1421c931b060SAnand Moon switch (speed) { 1422c931b060SAnand Moon case 10: 1423c931b060SAnand Moon rate = 2500000; 1424c931b060SAnand Moon break; 1425c931b060SAnand Moon case 100: 1426c931b060SAnand Moon rate = 25000000; 1427c931b060SAnand Moon break; 1428c931b060SAnand Moon default: 1429c931b060SAnand Moon dev_err(dev, "unknown speed value for RGMII speed=%d", speed); 1430c931b060SAnand Moon return; 1431c931b060SAnand Moon } 1432c931b060SAnand Moon 1433ea449f7fSSebastian Reichel ret = clk_set_rate(clk_mac_speed, rate); 1434c931b060SAnand Moon if (ret) 1435c931b060SAnand Moon dev_err(dev, "%s: set clk_mac_speed rate %ld failed %d\n", 1436c931b060SAnand Moon __func__, rate, ret); 1437c931b060SAnand Moon } 1438c931b060SAnand Moon 1439c931b060SAnand Moon static const struct rk_gmac_ops rv1126_ops = { 1440c931b060SAnand Moon .set_to_rgmii = rv1126_set_to_rgmii, 1441c931b060SAnand Moon .set_to_rmii = rv1126_set_to_rmii, 1442c931b060SAnand Moon .set_rgmii_speed = rv1126_set_rgmii_speed, 1443c931b060SAnand Moon .set_rmii_speed = rv1126_set_rmii_speed, 1444c931b060SAnand Moon }; 1445c931b060SAnand Moon 1446fecd4d7eSDavid Wu #define RK_GRF_MACPHY_CON0 0xb00 1447fecd4d7eSDavid Wu #define RK_GRF_MACPHY_CON1 0xb04 1448fecd4d7eSDavid Wu #define RK_GRF_MACPHY_CON2 0xb08 1449fecd4d7eSDavid Wu #define RK_GRF_MACPHY_CON3 0xb0c 1450fecd4d7eSDavid Wu 1451fecd4d7eSDavid Wu #define RK_MACPHY_ENABLE GRF_BIT(0) 1452fecd4d7eSDavid Wu #define RK_MACPHY_DISABLE GRF_CLR_BIT(0) 1453fecd4d7eSDavid Wu #define RK_MACPHY_CFG_CLK_50M GRF_BIT(14) 1454fecd4d7eSDavid Wu #define RK_GMAC2PHY_RMII_MODE (GRF_BIT(6) | GRF_CLR_BIT(7)) 1455fecd4d7eSDavid Wu #define RK_GRF_CON2_MACPHY_ID HIWORD_UPDATE(0x1234, 0xffff, 0) 1456fecd4d7eSDavid Wu #define RK_GRF_CON3_MACPHY_ID HIWORD_UPDATE(0x35, 0x3f, 0) 1457fecd4d7eSDavid Wu 1458fecd4d7eSDavid Wu static void rk_gmac_integrated_phy_powerup(struct rk_priv_data *priv) 14597ad269eaSRoger Chen { 1460fecd4d7eSDavid Wu if (priv->ops->integrated_phy_powerup) 1461fecd4d7eSDavid Wu priv->ops->integrated_phy_powerup(priv); 1462fecd4d7eSDavid Wu 1463fecd4d7eSDavid Wu regmap_write(priv->grf, RK_GRF_MACPHY_CON0, RK_MACPHY_CFG_CLK_50M); 1464fecd4d7eSDavid Wu regmap_write(priv->grf, RK_GRF_MACPHY_CON0, RK_GMAC2PHY_RMII_MODE); 1465fecd4d7eSDavid Wu 1466fecd4d7eSDavid Wu regmap_write(priv->grf, RK_GRF_MACPHY_CON2, RK_GRF_CON2_MACPHY_ID); 1467fecd4d7eSDavid Wu regmap_write(priv->grf, RK_GRF_MACPHY_CON3, RK_GRF_CON3_MACPHY_ID); 1468fecd4d7eSDavid Wu 1469fecd4d7eSDavid Wu if (priv->phy_reset) { 1470fecd4d7eSDavid Wu /* PHY needs to be disabled before trying to reset it */ 1471fecd4d7eSDavid Wu regmap_write(priv->grf, RK_GRF_MACPHY_CON0, RK_MACPHY_DISABLE); 1472fecd4d7eSDavid Wu if (priv->phy_reset) 1473fecd4d7eSDavid Wu reset_control_assert(priv->phy_reset); 1474fecd4d7eSDavid Wu usleep_range(10, 20); 1475fecd4d7eSDavid Wu if (priv->phy_reset) 1476fecd4d7eSDavid Wu reset_control_deassert(priv->phy_reset); 1477fecd4d7eSDavid Wu usleep_range(10, 20); 1478fecd4d7eSDavid Wu regmap_write(priv->grf, RK_GRF_MACPHY_CON0, RK_MACPHY_ENABLE); 1479fecd4d7eSDavid Wu msleep(30); 1480fecd4d7eSDavid Wu } 1481fecd4d7eSDavid Wu } 1482fecd4d7eSDavid Wu 1483fecd4d7eSDavid Wu static void rk_gmac_integrated_phy_powerdown(struct rk_priv_data *priv) 1484fecd4d7eSDavid Wu { 1485fecd4d7eSDavid Wu regmap_write(priv->grf, RK_GRF_MACPHY_CON0, RK_MACPHY_DISABLE); 1486fecd4d7eSDavid Wu if (priv->phy_reset) 1487fecd4d7eSDavid Wu reset_control_assert(priv->phy_reset); 1488fecd4d7eSDavid Wu } 1489fecd4d7eSDavid Wu 1490fecd4d7eSDavid Wu static int rk_gmac_clk_init(struct plat_stmmacenet_data *plat) 1491fecd4d7eSDavid Wu { 1492fecd4d7eSDavid Wu struct rk_priv_data *bsp_priv = plat->bsp_priv; 14937ad269eaSRoger Chen struct device *dev = &bsp_priv->pdev->dev; 1494ea449f7fSSebastian Reichel int phy_iface = bsp_priv->phy_iface; 1495ea449f7fSSebastian Reichel int i, j, ret; 14967ad269eaSRoger Chen 14977ad269eaSRoger Chen bsp_priv->clk_enabled = false; 14987ad269eaSRoger Chen 1499ea449f7fSSebastian Reichel bsp_priv->num_clks = ARRAY_SIZE(rk_clocks); 1500ea449f7fSSebastian Reichel if (phy_iface == PHY_INTERFACE_MODE_RMII) 1501ea449f7fSSebastian Reichel bsp_priv->num_clks += ARRAY_SIZE(rk_rmii_clocks); 15027ad269eaSRoger Chen 1503ea449f7fSSebastian Reichel bsp_priv->clks = devm_kcalloc(dev, bsp_priv->num_clks, 1504ea449f7fSSebastian Reichel sizeof(*bsp_priv->clks), GFP_KERNEL); 1505ea449f7fSSebastian Reichel if (!bsp_priv->clks) 1506ea449f7fSSebastian Reichel return -ENOMEM; 15077ad269eaSRoger Chen 1508ea449f7fSSebastian Reichel for (i = 0; i < ARRAY_SIZE(rk_clocks); i++) 1509ea449f7fSSebastian Reichel bsp_priv->clks[i].id = rk_clocks[i]; 15107ad269eaSRoger Chen 1511ea449f7fSSebastian Reichel if (phy_iface == PHY_INTERFACE_MODE_RMII) { 1512ea449f7fSSebastian Reichel for (j = 0; j < ARRAY_SIZE(rk_rmii_clocks); j++) 1513ea449f7fSSebastian Reichel bsp_priv->clks[i++].id = rk_rmii_clocks[j]; 1514ea449f7fSSebastian Reichel } 15157ad269eaSRoger Chen 1516ea449f7fSSebastian Reichel ret = devm_clk_bulk_get_optional(dev, bsp_priv->num_clks, 1517ea449f7fSSebastian Reichel bsp_priv->clks); 1518ea449f7fSSebastian Reichel if (ret) 1519ea449f7fSSebastian Reichel return dev_err_probe(dev, ret, "Failed to get clocks\n"); 1520ea449f7fSSebastian Reichel 1521ea449f7fSSebastian Reichel /* "stmmaceth" will be enabled by the core */ 15227ad269eaSRoger Chen bsp_priv->clk_mac = devm_clk_get(dev, "stmmaceth"); 1523ea449f7fSSebastian Reichel ret = PTR_ERR_OR_ZERO(bsp_priv->clk_mac); 1524ea449f7fSSebastian Reichel if (ret) 1525ea449f7fSSebastian Reichel return dev_err_probe(dev, ret, "Cannot get stmmaceth clock\n"); 152623c94d63SDavid Wu 15277ad269eaSRoger Chen if (bsp_priv->clock_input) { 1528d42202dcSRomain Perier dev_info(dev, "clock input from PHY\n"); 1529ea449f7fSSebastian Reichel } else if (phy_iface == PHY_INTERFACE_MODE_RMII) { 1530c48fa33cSHeiko Stübner clk_set_rate(bsp_priv->clk_mac, 50000000); 15317ad269eaSRoger Chen } 15327ad269eaSRoger Chen 1533fecd4d7eSDavid Wu if (plat->phy_node && bsp_priv->integrated_phy) { 1534fecd4d7eSDavid Wu bsp_priv->clk_phy = of_clk_get(plat->phy_node, 0); 1535ea449f7fSSebastian Reichel ret = PTR_ERR_OR_ZERO(bsp_priv->clk_phy); 1536ea449f7fSSebastian Reichel if (ret) 1537ea449f7fSSebastian Reichel return dev_err_probe(dev, ret, "Cannot get PHY clock\n"); 1538fecd4d7eSDavid Wu clk_set_rate(bsp_priv->clk_phy, 50000000); 1539fecd4d7eSDavid Wu } 1540fecd4d7eSDavid Wu 15417ad269eaSRoger Chen return 0; 15427ad269eaSRoger Chen } 15437ad269eaSRoger Chen 15447ad269eaSRoger Chen static int gmac_clk_enable(struct rk_priv_data *bsp_priv, bool enable) 15457ad269eaSRoger Chen { 1546ea449f7fSSebastian Reichel int ret; 15477ad269eaSRoger Chen 15487ad269eaSRoger Chen if (enable) { 15497ad269eaSRoger Chen if (!bsp_priv->clk_enabled) { 1550ea449f7fSSebastian Reichel ret = clk_bulk_prepare_enable(bsp_priv->num_clks, 1551ea449f7fSSebastian Reichel bsp_priv->clks); 1552ea449f7fSSebastian Reichel if (ret) 1553ea449f7fSSebastian Reichel return ret; 15547ad269eaSRoger Chen 1555ea449f7fSSebastian Reichel ret = clk_prepare_enable(bsp_priv->clk_phy); 1556ea449f7fSSebastian Reichel if (ret) 1557ea449f7fSSebastian Reichel return ret; 155823c94d63SDavid Wu 15592f2b60a0SDavid Wu if (bsp_priv->ops && bsp_priv->ops->set_clock_selection) 15602f2b60a0SDavid Wu bsp_priv->ops->set_clock_selection(bsp_priv, 15612f2b60a0SDavid Wu bsp_priv->clock_input, true); 15622f2b60a0SDavid Wu 15637ad269eaSRoger Chen mdelay(5); 15647ad269eaSRoger Chen bsp_priv->clk_enabled = true; 15657ad269eaSRoger Chen } 15667ad269eaSRoger Chen } else { 15677ad269eaSRoger Chen if (bsp_priv->clk_enabled) { 1568ea449f7fSSebastian Reichel clk_bulk_disable_unprepare(bsp_priv->num_clks, 1569ea449f7fSSebastian Reichel bsp_priv->clks); 1570fecd4d7eSDavid Wu clk_disable_unprepare(bsp_priv->clk_phy); 1571fecd4d7eSDavid Wu 15722f2b60a0SDavid Wu if (bsp_priv->ops && bsp_priv->ops->set_clock_selection) 15732f2b60a0SDavid Wu bsp_priv->ops->set_clock_selection(bsp_priv, 15742f2b60a0SDavid Wu bsp_priv->clock_input, false); 1575ea449f7fSSebastian Reichel 15767ad269eaSRoger Chen bsp_priv->clk_enabled = false; 15777ad269eaSRoger Chen } 15787ad269eaSRoger Chen } 15797ad269eaSRoger Chen 15807ad269eaSRoger Chen return 0; 15817ad269eaSRoger Chen } 15827ad269eaSRoger Chen 15837ad269eaSRoger Chen static int phy_power_on(struct rk_priv_data *bsp_priv, bool enable) 15847ad269eaSRoger Chen { 15852e12f536SRomain Perier struct regulator *ldo = bsp_priv->regulator; 15867ad269eaSRoger Chen int ret; 15877ad269eaSRoger Chen struct device *dev = &bsp_priv->pdev->dev; 15887ad269eaSRoger Chen 15897ad269eaSRoger Chen if (enable) { 15907ad269eaSRoger Chen ret = regulator_enable(ldo); 15912e12f536SRomain Perier if (ret) 1592d42202dcSRomain Perier dev_err(dev, "fail to enable phy-supply\n"); 15937ad269eaSRoger Chen } else { 15947ad269eaSRoger Chen ret = regulator_disable(ldo); 15952e12f536SRomain Perier if (ret) 1596d42202dcSRomain Perier dev_err(dev, "fail to disable phy-supply\n"); 15977ad269eaSRoger Chen } 15987ad269eaSRoger Chen 15997ad269eaSRoger Chen return 0; 16007ad269eaSRoger Chen } 16017ad269eaSRoger Chen 16020fb98db1SHeiko Stübner static struct rk_priv_data *rk_gmac_setup(struct platform_device *pdev, 1603fecd4d7eSDavid Wu struct plat_stmmacenet_data *plat, 160492c2588fSJoachim Eastwood const struct rk_gmac_ops *ops) 16057ad269eaSRoger Chen { 16067ad269eaSRoger Chen struct rk_priv_data *bsp_priv; 16077ad269eaSRoger Chen struct device *dev = &pdev->dev; 16083bb3d6b1SDavid Wu struct resource *res; 16097ad269eaSRoger Chen int ret; 16107ad269eaSRoger Chen const char *strings = NULL; 16117ad269eaSRoger Chen int value; 16127ad269eaSRoger Chen 16137ad269eaSRoger Chen bsp_priv = devm_kzalloc(dev, sizeof(*bsp_priv), GFP_KERNEL); 16147ad269eaSRoger Chen if (!bsp_priv) 16157ad269eaSRoger Chen return ERR_PTR(-ENOMEM); 16167ad269eaSRoger Chen 16170c65b2b9SAndrew Lunn of_get_phy_mode(dev->of_node, &bsp_priv->phy_iface); 16180fb98db1SHeiko Stübner bsp_priv->ops = ops; 16197ad269eaSRoger Chen 16203bb3d6b1SDavid Wu /* Some SoCs have multiple MAC controllers, which need 16213bb3d6b1SDavid Wu * to be distinguished. 16223bb3d6b1SDavid Wu */ 16233bb3d6b1SDavid Wu res = platform_get_resource(pdev, IORESOURCE_MEM, 0); 16240546b224SJohn Keeping if (res && ops->regs_valid) { 16253bb3d6b1SDavid Wu int i = 0; 16263bb3d6b1SDavid Wu 16273bb3d6b1SDavid Wu while (ops->regs[i]) { 16283bb3d6b1SDavid Wu if (ops->regs[i] == res->start) { 16293bb3d6b1SDavid Wu bsp_priv->id = i; 16303bb3d6b1SDavid Wu break; 16313bb3d6b1SDavid Wu } 16323bb3d6b1SDavid Wu i++; 16333bb3d6b1SDavid Wu } 16343bb3d6b1SDavid Wu } 16353bb3d6b1SDavid Wu 1636db219732SSebastian Reichel bsp_priv->regulator = devm_regulator_get(dev, "phy"); 16372e12f536SRomain Perier if (IS_ERR(bsp_priv->regulator)) { 1638db219732SSebastian Reichel ret = PTR_ERR(bsp_priv->regulator); 1639db219732SSebastian Reichel dev_err_probe(dev, ret, "failed to get phy regulator\n"); 1640db219732SSebastian Reichel return ERR_PTR(ret); 16417ad269eaSRoger Chen } 16427ad269eaSRoger Chen 16437ad269eaSRoger Chen ret = of_property_read_string(dev->of_node, "clock_in_out", &strings); 16447ad269eaSRoger Chen if (ret) { 1645d42202dcSRomain Perier dev_err(dev, "Can not read property: clock_in_out.\n"); 16467ad269eaSRoger Chen bsp_priv->clock_input = true; 16477ad269eaSRoger Chen } else { 1648d42202dcSRomain Perier dev_info(dev, "clock input or output? (%s).\n", 1649d42202dcSRomain Perier strings); 16507ad269eaSRoger Chen if (!strcmp(strings, "input")) 16517ad269eaSRoger Chen bsp_priv->clock_input = true; 16527ad269eaSRoger Chen else 16537ad269eaSRoger Chen bsp_priv->clock_input = false; 16547ad269eaSRoger Chen } 16557ad269eaSRoger Chen 16567ad269eaSRoger Chen ret = of_property_read_u32(dev->of_node, "tx_delay", &value); 16577ad269eaSRoger Chen if (ret) { 16587ad269eaSRoger Chen bsp_priv->tx_delay = 0x30; 1659d42202dcSRomain Perier dev_err(dev, "Can not read property: tx_delay."); 1660d42202dcSRomain Perier dev_err(dev, "set tx_delay to 0x%x\n", 1661d42202dcSRomain Perier bsp_priv->tx_delay); 16627ad269eaSRoger Chen } else { 1663d42202dcSRomain Perier dev_info(dev, "TX delay(0x%x).\n", value); 16647ad269eaSRoger Chen bsp_priv->tx_delay = value; 16657ad269eaSRoger Chen } 16667ad269eaSRoger Chen 16677ad269eaSRoger Chen ret = of_property_read_u32(dev->of_node, "rx_delay", &value); 16687ad269eaSRoger Chen if (ret) { 16697ad269eaSRoger Chen bsp_priv->rx_delay = 0x10; 1670d42202dcSRomain Perier dev_err(dev, "Can not read property: rx_delay."); 1671d42202dcSRomain Perier dev_err(dev, "set rx_delay to 0x%x\n", 1672d42202dcSRomain Perier bsp_priv->rx_delay); 16737ad269eaSRoger Chen } else { 1674d42202dcSRomain Perier dev_info(dev, "RX delay(0x%x).\n", value); 16757ad269eaSRoger Chen bsp_priv->rx_delay = value; 16767ad269eaSRoger Chen } 16777ad269eaSRoger Chen 16787ad269eaSRoger Chen bsp_priv->grf = syscon_regmap_lookup_by_phandle(dev->of_node, 16797ad269eaSRoger Chen "rockchip,grf"); 16802f2b60a0SDavid Wu bsp_priv->php_grf = syscon_regmap_lookup_by_phandle(dev->of_node, 16812f2b60a0SDavid Wu "rockchip,php-grf"); 16827ad269eaSRoger Chen 1683fecd4d7eSDavid Wu if (plat->phy_node) { 1684fecd4d7eSDavid Wu bsp_priv->integrated_phy = of_property_read_bool(plat->phy_node, 1685fecd4d7eSDavid Wu "phy-is-integrated"); 1686fecd4d7eSDavid Wu if (bsp_priv->integrated_phy) { 1687fecd4d7eSDavid Wu bsp_priv->phy_reset = of_reset_control_get(plat->phy_node, NULL); 1688fecd4d7eSDavid Wu if (IS_ERR(bsp_priv->phy_reset)) { 1689fecd4d7eSDavid Wu dev_err(&pdev->dev, "No PHY reset control found.\n"); 1690fecd4d7eSDavid Wu bsp_priv->phy_reset = NULL; 1691fecd4d7eSDavid Wu } 1692fecd4d7eSDavid Wu } 1693fecd4d7eSDavid Wu } 1694fecd4d7eSDavid Wu dev_info(dev, "integrated PHY? (%s).\n", 1695fecd4d7eSDavid Wu bsp_priv->integrated_phy ? "yes" : "no"); 1696fecd4d7eSDavid Wu 1697fecd4d7eSDavid Wu bsp_priv->pdev = pdev; 169845383f52SRoger Chen 169945383f52SRoger Chen return bsp_priv; 170045383f52SRoger Chen } 170145383f52SRoger Chen 170237c80d15SDavid Wu static int rk_gmac_check_ops(struct rk_priv_data *bsp_priv) 170337c80d15SDavid Wu { 170437c80d15SDavid Wu switch (bsp_priv->phy_iface) { 170537c80d15SDavid Wu case PHY_INTERFACE_MODE_RGMII: 170637c80d15SDavid Wu case PHY_INTERFACE_MODE_RGMII_ID: 170737c80d15SDavid Wu case PHY_INTERFACE_MODE_RGMII_RXID: 170837c80d15SDavid Wu case PHY_INTERFACE_MODE_RGMII_TXID: 170937c80d15SDavid Wu if (!bsp_priv->ops->set_to_rgmii) 171037c80d15SDavid Wu return -EINVAL; 171137c80d15SDavid Wu break; 171237c80d15SDavid Wu case PHY_INTERFACE_MODE_RMII: 171337c80d15SDavid Wu if (!bsp_priv->ops->set_to_rmii) 171437c80d15SDavid Wu return -EINVAL; 171537c80d15SDavid Wu break; 171637c80d15SDavid Wu default: 171737c80d15SDavid Wu dev_err(&bsp_priv->pdev->dev, 171837c80d15SDavid Wu "unsupported interface %d", bsp_priv->phy_iface); 171937c80d15SDavid Wu } 172037c80d15SDavid Wu return 0; 172137c80d15SDavid Wu } 172237c80d15SDavid Wu 172345383f52SRoger Chen static int rk_gmac_powerup(struct rk_priv_data *bsp_priv) 172445383f52SRoger Chen { 172545383f52SRoger Chen int ret; 172645383f52SRoger Chen struct device *dev = &bsp_priv->pdev->dev; 172745383f52SRoger Chen 172837c80d15SDavid Wu ret = rk_gmac_check_ops(bsp_priv); 172937c80d15SDavid Wu if (ret) 173037c80d15SDavid Wu return ret; 173137c80d15SDavid Wu 1732f217bfdeSHeiko Stübner ret = gmac_clk_enable(bsp_priv, true); 1733f217bfdeSHeiko Stübner if (ret) 1734f217bfdeSHeiko Stübner return ret; 1735f217bfdeSHeiko Stübner 17367ad269eaSRoger Chen /*rmii or rgmii*/ 1737eaf70ad1SWadim Egorov switch (bsp_priv->phy_iface) { 1738eaf70ad1SWadim Egorov case PHY_INTERFACE_MODE_RGMII: 1739d42202dcSRomain Perier dev_info(dev, "init for RGMII\n"); 17400fb98db1SHeiko Stübner bsp_priv->ops->set_to_rgmii(bsp_priv, bsp_priv->tx_delay, 17410fb98db1SHeiko Stübner bsp_priv->rx_delay); 1742eaf70ad1SWadim Egorov break; 1743eaf70ad1SWadim Egorov case PHY_INTERFACE_MODE_RGMII_ID: 1744eaf70ad1SWadim Egorov dev_info(dev, "init for RGMII_ID\n"); 1745eaf70ad1SWadim Egorov bsp_priv->ops->set_to_rgmii(bsp_priv, 0, 0); 1746eaf70ad1SWadim Egorov break; 1747eaf70ad1SWadim Egorov case PHY_INTERFACE_MODE_RGMII_RXID: 1748eaf70ad1SWadim Egorov dev_info(dev, "init for RGMII_RXID\n"); 1749eaf70ad1SWadim Egorov bsp_priv->ops->set_to_rgmii(bsp_priv, bsp_priv->tx_delay, 0); 1750eaf70ad1SWadim Egorov break; 1751eaf70ad1SWadim Egorov case PHY_INTERFACE_MODE_RGMII_TXID: 1752eaf70ad1SWadim Egorov dev_info(dev, "init for RGMII_TXID\n"); 1753eaf70ad1SWadim Egorov bsp_priv->ops->set_to_rgmii(bsp_priv, 0, bsp_priv->rx_delay); 1754eaf70ad1SWadim Egorov break; 1755eaf70ad1SWadim Egorov case PHY_INTERFACE_MODE_RMII: 1756d42202dcSRomain Perier dev_info(dev, "init for RMII\n"); 17570fb98db1SHeiko Stübner bsp_priv->ops->set_to_rmii(bsp_priv); 1758eaf70ad1SWadim Egorov break; 1759eaf70ad1SWadim Egorov default: 1760d42202dcSRomain Perier dev_err(dev, "NO interface defined!\n"); 17617ad269eaSRoger Chen } 17627ad269eaSRoger Chen 17637ad269eaSRoger Chen ret = phy_power_on(bsp_priv, true); 1764c69c29a1SAlexey Khoroshilov if (ret) { 1765c69c29a1SAlexey Khoroshilov gmac_clk_enable(bsp_priv, false); 17667ad269eaSRoger Chen return ret; 1767c69c29a1SAlexey Khoroshilov } 17687ad269eaSRoger Chen 1769aec3f415SPunit Agrawal pm_runtime_get_sync(dev); 1770aec3f415SPunit Agrawal 1771fecd4d7eSDavid Wu if (bsp_priv->integrated_phy) 1772fecd4d7eSDavid Wu rk_gmac_integrated_phy_powerup(bsp_priv); 1773fecd4d7eSDavid Wu 17747ad269eaSRoger Chen return 0; 17757ad269eaSRoger Chen } 17767ad269eaSRoger Chen 1777229666c1SVincent Palatin static void rk_gmac_powerdown(struct rk_priv_data *gmac) 17787ad269eaSRoger Chen { 1779fecd4d7eSDavid Wu if (gmac->integrated_phy) 1780fecd4d7eSDavid Wu rk_gmac_integrated_phy_powerdown(gmac); 1781fecd4d7eSDavid Wu 1782aec3f415SPunit Agrawal pm_runtime_put_sync(&gmac->pdev->dev); 1783aec3f415SPunit Agrawal 17847ad269eaSRoger Chen phy_power_on(gmac, false); 17857ad269eaSRoger Chen gmac_clk_enable(gmac, false); 17867ad269eaSRoger Chen } 17877ad269eaSRoger Chen 17887ad269eaSRoger Chen static void rk_fix_speed(void *priv, unsigned int speed) 17897ad269eaSRoger Chen { 17907ad269eaSRoger Chen struct rk_priv_data *bsp_priv = priv; 17917ad269eaSRoger Chen struct device *dev = &bsp_priv->pdev->dev; 17927ad269eaSRoger Chen 1793eaf70ad1SWadim Egorov switch (bsp_priv->phy_iface) { 1794eaf70ad1SWadim Egorov case PHY_INTERFACE_MODE_RGMII: 1795eaf70ad1SWadim Egorov case PHY_INTERFACE_MODE_RGMII_ID: 1796eaf70ad1SWadim Egorov case PHY_INTERFACE_MODE_RGMII_RXID: 1797eaf70ad1SWadim Egorov case PHY_INTERFACE_MODE_RGMII_TXID: 179837c80d15SDavid Wu if (bsp_priv->ops->set_rgmii_speed) 17990fb98db1SHeiko Stübner bsp_priv->ops->set_rgmii_speed(bsp_priv, speed); 1800eaf70ad1SWadim Egorov break; 1801eaf70ad1SWadim Egorov case PHY_INTERFACE_MODE_RMII: 180237c80d15SDavid Wu if (bsp_priv->ops->set_rmii_speed) 18030fb98db1SHeiko Stübner bsp_priv->ops->set_rmii_speed(bsp_priv, speed); 1804eaf70ad1SWadim Egorov break; 1805eaf70ad1SWadim Egorov default: 18067ad269eaSRoger Chen dev_err(dev, "unsupported interface %d", bsp_priv->phy_iface); 18077ad269eaSRoger Chen } 1808eaf70ad1SWadim Egorov } 18097ad269eaSRoger Chen 181027ffefd2SJoachim Eastwood static int rk_gmac_probe(struct platform_device *pdev) 181127ffefd2SJoachim Eastwood { 181227ffefd2SJoachim Eastwood struct plat_stmmacenet_data *plat_dat; 181327ffefd2SJoachim Eastwood struct stmmac_resources stmmac_res; 1814f529f182SJoachim Eastwood const struct rk_gmac_ops *data; 181527ffefd2SJoachim Eastwood int ret; 181627ffefd2SJoachim Eastwood 1817149adeddSJoachim Eastwood data = of_device_get_match_data(&pdev->dev); 1818149adeddSJoachim Eastwood if (!data) { 1819149adeddSJoachim Eastwood dev_err(&pdev->dev, "no of match data provided\n"); 1820149adeddSJoachim Eastwood return -EINVAL; 1821149adeddSJoachim Eastwood } 1822149adeddSJoachim Eastwood 182327ffefd2SJoachim Eastwood ret = stmmac_get_platform_resources(pdev, &stmmac_res); 182427ffefd2SJoachim Eastwood if (ret) 182527ffefd2SJoachim Eastwood return ret; 182627ffefd2SJoachim Eastwood 182783216e39SMichael Walle plat_dat = stmmac_probe_config_dt(pdev, stmmac_res.mac); 182827ffefd2SJoachim Eastwood if (IS_ERR(plat_dat)) 182927ffefd2SJoachim Eastwood return PTR_ERR(plat_dat); 183027ffefd2SJoachim Eastwood 1831d6b06251SEzequiel Garcia /* If the stmmac is not already selected as gmac4, 1832d6b06251SEzequiel Garcia * then make sure we fallback to gmac. 1833d6b06251SEzequiel Garcia */ 1834d6b06251SEzequiel Garcia if (!plat_dat->has_gmac4) 183527ffefd2SJoachim Eastwood plat_dat->has_gmac = true; 183627ffefd2SJoachim Eastwood plat_dat->fix_mac_speed = rk_fix_speed; 183727ffefd2SJoachim Eastwood 1838fecd4d7eSDavid Wu plat_dat->bsp_priv = rk_gmac_setup(pdev, plat_dat, data); 1839d2ed0a77SJohan Hovold if (IS_ERR(plat_dat->bsp_priv)) { 1840d2ed0a77SJohan Hovold ret = PTR_ERR(plat_dat->bsp_priv); 1841d2ed0a77SJohan Hovold goto err_remove_config_dt; 1842d2ed0a77SJohan Hovold } 184327ffefd2SJoachim Eastwood 1844fecd4d7eSDavid Wu ret = rk_gmac_clk_init(plat_dat); 1845fecd4d7eSDavid Wu if (ret) 18469de9aa48SEmil Renner Berthing goto err_remove_config_dt; 1847fecd4d7eSDavid Wu 184807a5e769SJoachim Eastwood ret = rk_gmac_powerup(plat_dat->bsp_priv); 184927ffefd2SJoachim Eastwood if (ret) 1850d2ed0a77SJohan Hovold goto err_remove_config_dt; 185127ffefd2SJoachim Eastwood 18522d222656SJohan Hovold ret = stmmac_dvr_probe(&pdev->dev, plat_dat, &stmmac_res); 18532d222656SJohan Hovold if (ret) 18542745529aSDavid S. Miller goto err_gmac_powerdown; 18552d222656SJohan Hovold 18562d222656SJohan Hovold return 0; 18572d222656SJohan Hovold 18582745529aSDavid S. Miller err_gmac_powerdown: 18592745529aSDavid S. Miller rk_gmac_powerdown(plat_dat->bsp_priv); 1860d2ed0a77SJohan Hovold err_remove_config_dt: 1861d2ed0a77SJohan Hovold stmmac_remove_config_dt(pdev, plat_dat); 18622d222656SJohan Hovold 18632d222656SJohan Hovold return ret; 186427ffefd2SJoachim Eastwood } 186527ffefd2SJoachim Eastwood 1866*903cc461SUwe Kleine-König static void rk_gmac_remove(struct platform_device *pdev) 18670de8c4c9SJoachim Eastwood { 18680de8c4c9SJoachim Eastwood struct rk_priv_data *bsp_priv = get_stmmac_bsp_priv(&pdev->dev); 1869ff0011cfSUwe Kleine-König 1870ff0011cfSUwe Kleine-König stmmac_dvr_remove(&pdev->dev); 18710de8c4c9SJoachim Eastwood 18720de8c4c9SJoachim Eastwood rk_gmac_powerdown(bsp_priv); 18730de8c4c9SJoachim Eastwood } 18740de8c4c9SJoachim Eastwood 18755619468aSJoachim Eastwood #ifdef CONFIG_PM_SLEEP 18765619468aSJoachim Eastwood static int rk_gmac_suspend(struct device *dev) 18775619468aSJoachim Eastwood { 18785619468aSJoachim Eastwood struct rk_priv_data *bsp_priv = get_stmmac_bsp_priv(dev); 18795619468aSJoachim Eastwood int ret = stmmac_suspend(dev); 18805619468aSJoachim Eastwood 18815619468aSJoachim Eastwood /* Keep the PHY up if we use Wake-on-Lan. */ 18825619468aSJoachim Eastwood if (!device_may_wakeup(dev)) { 18835619468aSJoachim Eastwood rk_gmac_powerdown(bsp_priv); 18845619468aSJoachim Eastwood bsp_priv->suspended = true; 18855619468aSJoachim Eastwood } 18865619468aSJoachim Eastwood 18875619468aSJoachim Eastwood return ret; 18885619468aSJoachim Eastwood } 18895619468aSJoachim Eastwood 18905619468aSJoachim Eastwood static int rk_gmac_resume(struct device *dev) 18915619468aSJoachim Eastwood { 18925619468aSJoachim Eastwood struct rk_priv_data *bsp_priv = get_stmmac_bsp_priv(dev); 18935619468aSJoachim Eastwood 18945619468aSJoachim Eastwood /* The PHY was up for Wake-on-Lan. */ 18955619468aSJoachim Eastwood if (bsp_priv->suspended) { 18965619468aSJoachim Eastwood rk_gmac_powerup(bsp_priv); 18975619468aSJoachim Eastwood bsp_priv->suspended = false; 18985619468aSJoachim Eastwood } 18995619468aSJoachim Eastwood 19005619468aSJoachim Eastwood return stmmac_resume(dev); 19015619468aSJoachim Eastwood } 19025619468aSJoachim Eastwood #endif /* CONFIG_PM_SLEEP */ 19035619468aSJoachim Eastwood 19045619468aSJoachim Eastwood static SIMPLE_DEV_PM_OPS(rk_gmac_pm_ops, rk_gmac_suspend, rk_gmac_resume); 19055619468aSJoachim Eastwood 1906e0fb4013SJoachim Eastwood static const struct of_device_id rk_gmac_dwmac_match[] = { 190723c94d63SDavid Wu { .compatible = "rockchip,px30-gmac", .data = &px30_ops }, 190805946876SDavid Wu { .compatible = "rockchip,rk3128-gmac", .data = &rk3128_ops }, 1909e7ffd812SXing Zheng { .compatible = "rockchip,rk3228-gmac", .data = &rk3228_ops }, 1910f529f182SJoachim Eastwood { .compatible = "rockchip,rk3288-gmac", .data = &rk3288_ops }, 1911b4ac9456STobias Schramm { .compatible = "rockchip,rk3308-gmac", .data = &rk3308_ops }, 1912d4ff816eSdavid.wu { .compatible = "rockchip,rk3328-gmac", .data = &rk3328_ops }, 1913ba289af8SRoger Chen { .compatible = "rockchip,rk3366-gmac", .data = &rk3366_ops }, 1914f529f182SJoachim Eastwood { .compatible = "rockchip,rk3368-gmac", .data = &rk3368_ops }, 1915ba289af8SRoger Chen { .compatible = "rockchip,rk3399-gmac", .data = &rk3399_ops }, 19163bb3d6b1SDavid Wu { .compatible = "rockchip,rk3568-gmac", .data = &rk3568_ops }, 19172f2b60a0SDavid Wu { .compatible = "rockchip,rk3588-gmac", .data = &rk3588_ops }, 191889c9c163SDavid Wu { .compatible = "rockchip,rv1108-gmac", .data = &rv1108_ops }, 1919c931b060SAnand Moon { .compatible = "rockchip,rv1126-gmac", .data = &rv1126_ops }, 1920e0fb4013SJoachim Eastwood { } 1921e0fb4013SJoachim Eastwood }; 1922e0fb4013SJoachim Eastwood MODULE_DEVICE_TABLE(of, rk_gmac_dwmac_match); 1923e0fb4013SJoachim Eastwood 1924e0fb4013SJoachim Eastwood static struct platform_driver rk_gmac_dwmac_driver = { 192527ffefd2SJoachim Eastwood .probe = rk_gmac_probe, 1926*903cc461SUwe Kleine-König .remove_new = rk_gmac_remove, 1927e0fb4013SJoachim Eastwood .driver = { 1928e0fb4013SJoachim Eastwood .name = "rk_gmac-dwmac", 19295619468aSJoachim Eastwood .pm = &rk_gmac_pm_ops, 1930e0fb4013SJoachim Eastwood .of_match_table = rk_gmac_dwmac_match, 1931e0fb4013SJoachim Eastwood }, 1932e0fb4013SJoachim Eastwood }; 1933e0fb4013SJoachim Eastwood module_platform_driver(rk_gmac_dwmac_driver); 1934e0fb4013SJoachim Eastwood 1935e0fb4013SJoachim Eastwood MODULE_AUTHOR("Chen-Zhi (Roger Chen) <roger.chen@rock-chips.com>"); 1936e0fb4013SJoachim Eastwood MODULE_DESCRIPTION("Rockchip RK3288 DWMAC specific glue layer"); 1937e0fb4013SJoachim Eastwood MODULE_LICENSE("GPL"); 1938