1 // SPDX-License-Identifier: GPL-2.0-only 2 /* 3 * dwmac-stm32.c - DWMAC Specific Glue layer for STM32 MCU 4 * 5 * Copyright (C) STMicroelectronics SA 2017 6 * Author: Alexandre Torgue <alexandre.torgue@st.com> for STMicroelectronics. 7 */ 8 9 #include <linux/clk.h> 10 #include <linux/kernel.h> 11 #include <linux/mfd/syscon.h> 12 #include <linux/module.h> 13 #include <linux/of.h> 14 #include <linux/of_net.h> 15 #include <linux/phy.h> 16 #include <linux/platform_device.h> 17 #include <linux/pm_wakeirq.h> 18 #include <linux/regmap.h> 19 #include <linux/slab.h> 20 #include <linux/stmmac.h> 21 22 #include "stmmac_platform.h" 23 24 #define SYSCFG_MCU_ETH_MASK BIT(23) 25 #define SYSCFG_MP1_ETH_MASK GENMASK(23, 16) 26 #define SYSCFG_PMCCLRR_OFFSET 0x40 27 28 #define SYSCFG_PMCR_ETH_CLK_SEL BIT(16) 29 #define SYSCFG_PMCR_ETH_REF_CLK_SEL BIT(17) 30 31 /* CLOCK feed to PHY*/ 32 #define ETH_CK_F_25M 25000000 33 #define ETH_CK_F_50M 50000000 34 #define ETH_CK_F_125M 125000000 35 36 /* Ethernet PHY interface selection in register SYSCFG Configuration 37 *------------------------------------------ 38 * src |BIT(23)| BIT(22)| BIT(21)|BIT(20)| 39 *------------------------------------------ 40 * MII | 0 | 0 | 0 | 1 | 41 *------------------------------------------ 42 * GMII | 0 | 0 | 0 | 0 | 43 *------------------------------------------ 44 * RGMII | 0 | 0 | 1 | n/a | 45 *------------------------------------------ 46 * RMII | 1 | 0 | 0 | n/a | 47 *------------------------------------------ 48 */ 49 #define SYSCFG_PMCR_ETH_SEL_MII BIT(20) 50 #define SYSCFG_PMCR_PHY_INTF_SEL_MASK GENMASK(23, 21) 51 #define SYSCFG_MCU_ETH_SEL_MII 0 52 #define SYSCFG_MCU_ETH_SEL_RMII 1 53 54 /* STM32MP2 register definitions */ 55 #define SYSCFG_MP2_ETH_MASK GENMASK(31, 0) 56 57 #define SYSCFG_ETHCR_ETH_SEL_MASK GENMASK(6, 4) 58 #define SYSCFG_ETHCR_ETH_PTP_CLK_SEL BIT(2) 59 #define SYSCFG_ETHCR_ETH_CLK_SEL BIT(1) 60 #define SYSCFG_ETHCR_ETH_REF_CLK_SEL BIT(0) 61 62 /* STM32MPx register definitions 63 * 64 * Below table summarizes the clock requirement and clock sources for 65 * supported phy interface modes. 66 * __________________________________________________________________________ 67 *|PHY_MODE | Normal | PHY wo crystal| PHY wo crystal |No 125MHz from PHY| 68 *| | | 25MHz | 50MHz | | 69 * --------------------------------------------------------------------------- 70 *| MII | - | eth-ck | n/a | n/a | 71 *| | | st,ext-phyclk | | | 72 * --------------------------------------------------------------------------- 73 *| GMII | - | eth-ck | n/a | n/a | 74 *| | | st,ext-phyclk | | | 75 * --------------------------------------------------------------------------- 76 *| RGMII | - | eth-ck | n/a | eth-ck | 77 *| | | st,ext-phyclk | | st,eth-clk-sel or| 78 *| | | | | st,ext-phyclk | 79 * --------------------------------------------------------------------------- 80 *| RMII | - | eth-ck | eth-ck | n/a | 81 *| | | st,ext-phyclk | st,eth-ref-clk-sel | | 82 *| | | | or st,ext-phyclk | | 83 * --------------------------------------------------------------------------- 84 * 85 */ 86 87 struct stm32_dwmac { 88 struct clk *clk_tx; 89 struct clk *clk_rx; 90 struct clk *clk_eth_ck; 91 struct clk *clk_ethstp; 92 struct clk *syscfg_clk; 93 int ext_phyclk; 94 int enable_eth_ck; 95 int eth_clk_sel_reg; 96 int eth_ref_clk_sel_reg; 97 int irq_pwr_wakeup; 98 u32 mode_reg; /* MAC glue-logic mode register */ 99 u32 mode_mask; 100 struct regmap *regmap; 101 u32 speed; 102 const struct stm32_ops *ops; 103 struct device *dev; 104 }; 105 106 struct stm32_ops { 107 int (*set_mode)(struct plat_stmmacenet_data *plat_dat); 108 int (*suspend)(struct stm32_dwmac *dwmac); 109 void (*resume)(struct stm32_dwmac *dwmac); 110 int (*parse_data)(struct stm32_dwmac *dwmac, 111 struct device *dev); 112 bool clk_rx_enable_in_suspend; 113 bool is_mp13, is_mp2; 114 u32 syscfg_clr_off; 115 }; 116 117 static int stm32_dwmac_clk_enable(struct stm32_dwmac *dwmac) 118 { 119 int ret; 120 121 ret = clk_prepare_enable(dwmac->clk_tx); 122 if (ret) 123 goto err_clk_tx; 124 125 ret = clk_prepare_enable(dwmac->clk_rx); 126 if (ret) 127 goto err_clk_rx; 128 129 ret = clk_prepare_enable(dwmac->syscfg_clk); 130 if (ret) 131 goto err_syscfg_clk; 132 133 if (dwmac->enable_eth_ck) { 134 ret = clk_prepare_enable(dwmac->clk_eth_ck); 135 if (ret) 136 goto err_clk_eth_ck; 137 } 138 139 return ret; 140 141 err_clk_eth_ck: 142 clk_disable_unprepare(dwmac->syscfg_clk); 143 err_syscfg_clk: 144 clk_disable_unprepare(dwmac->clk_rx); 145 err_clk_rx: 146 clk_disable_unprepare(dwmac->clk_tx); 147 err_clk_tx: 148 return ret; 149 } 150 151 static int stm32_dwmac_init(struct plat_stmmacenet_data *plat_dat) 152 { 153 struct stm32_dwmac *dwmac = plat_dat->bsp_priv; 154 int ret; 155 156 if (dwmac->ops->set_mode) { 157 ret = dwmac->ops->set_mode(plat_dat); 158 if (ret) 159 return ret; 160 } 161 162 return stm32_dwmac_clk_enable(dwmac); 163 } 164 165 static int stm32mp1_select_ethck_external(struct plat_stmmacenet_data *plat_dat) 166 { 167 struct stm32_dwmac *dwmac = plat_dat->bsp_priv; 168 169 switch (plat_dat->phy_interface) { 170 case PHY_INTERFACE_MODE_MII: 171 dwmac->enable_eth_ck = dwmac->ext_phyclk; 172 return 0; 173 case PHY_INTERFACE_MODE_GMII: 174 dwmac->enable_eth_ck = dwmac->eth_clk_sel_reg || 175 dwmac->ext_phyclk; 176 return 0; 177 case PHY_INTERFACE_MODE_RMII: 178 dwmac->enable_eth_ck = dwmac->eth_ref_clk_sel_reg || 179 dwmac->ext_phyclk; 180 return 0; 181 case PHY_INTERFACE_MODE_RGMII: 182 case PHY_INTERFACE_MODE_RGMII_ID: 183 case PHY_INTERFACE_MODE_RGMII_RXID: 184 case PHY_INTERFACE_MODE_RGMII_TXID: 185 dwmac->enable_eth_ck = dwmac->eth_clk_sel_reg || 186 dwmac->ext_phyclk; 187 return 0; 188 default: 189 dwmac->enable_eth_ck = false; 190 dev_err(dwmac->dev, "Mode %s not supported", 191 phy_modes(plat_dat->phy_interface)); 192 return -EINVAL; 193 } 194 } 195 196 static int stm32mp1_validate_ethck_rate(struct plat_stmmacenet_data *plat_dat) 197 { 198 struct stm32_dwmac *dwmac = plat_dat->bsp_priv; 199 const u32 clk_rate = clk_get_rate(dwmac->clk_eth_ck); 200 201 if (!dwmac->enable_eth_ck) 202 return 0; 203 204 switch (plat_dat->phy_interface) { 205 case PHY_INTERFACE_MODE_MII: 206 case PHY_INTERFACE_MODE_GMII: 207 if (clk_rate == ETH_CK_F_25M) 208 return 0; 209 break; 210 case PHY_INTERFACE_MODE_RMII: 211 if (clk_rate == ETH_CK_F_25M || clk_rate == ETH_CK_F_50M) 212 return 0; 213 break; 214 case PHY_INTERFACE_MODE_RGMII: 215 case PHY_INTERFACE_MODE_RGMII_ID: 216 case PHY_INTERFACE_MODE_RGMII_RXID: 217 case PHY_INTERFACE_MODE_RGMII_TXID: 218 if (clk_rate == ETH_CK_F_25M || clk_rate == ETH_CK_F_125M) 219 return 0; 220 break; 221 default: 222 break; 223 } 224 225 dev_err(dwmac->dev, "Mode %s does not match eth-ck frequency %d Hz", 226 phy_modes(plat_dat->phy_interface), clk_rate); 227 return -EINVAL; 228 } 229 230 static int stm32mp1_configure_pmcr(struct plat_stmmacenet_data *plat_dat, 231 u8 phy_intf_sel) 232 { 233 struct stm32_dwmac *dwmac = plat_dat->bsp_priv; 234 u32 reg = dwmac->mode_reg; 235 int val; 236 237 val = FIELD_PREP(SYSCFG_PMCR_PHY_INTF_SEL_MASK, phy_intf_sel); 238 239 switch (plat_dat->phy_interface) { 240 case PHY_INTERFACE_MODE_MII: 241 /* 242 * STM32MP15xx supports both MII and GMII, STM32MP13xx MII only. 243 * SYSCFG_PMCSETR ETH_SELMII is present only on STM32MP15xx and 244 * acts as a selector between 0:GMII and 1:MII. As STM32MP13xx 245 * supports only MII, ETH_SELMII is not present. 246 */ 247 if (!dwmac->ops->is_mp13) /* Select MII mode on STM32MP15xx */ 248 val |= SYSCFG_PMCR_ETH_SEL_MII; 249 break; 250 case PHY_INTERFACE_MODE_GMII: 251 if (dwmac->enable_eth_ck) 252 val |= SYSCFG_PMCR_ETH_CLK_SEL; 253 break; 254 case PHY_INTERFACE_MODE_RMII: 255 if (dwmac->enable_eth_ck) 256 val |= SYSCFG_PMCR_ETH_REF_CLK_SEL; 257 break; 258 case PHY_INTERFACE_MODE_RGMII: 259 case PHY_INTERFACE_MODE_RGMII_ID: 260 case PHY_INTERFACE_MODE_RGMII_RXID: 261 case PHY_INTERFACE_MODE_RGMII_TXID: 262 if (dwmac->enable_eth_ck) 263 val |= SYSCFG_PMCR_ETH_CLK_SEL; 264 break; 265 default: 266 dev_err(dwmac->dev, "Mode %s not supported", 267 phy_modes(plat_dat->phy_interface)); 268 /* Do not manage others interfaces */ 269 return -EINVAL; 270 } 271 272 dev_dbg(dwmac->dev, "Mode %s", phy_modes(plat_dat->phy_interface)); 273 274 /* Shift value at correct ethernet MAC offset in SYSCFG_PMCSETR */ 275 val <<= ffs(dwmac->mode_mask) - ffs(SYSCFG_MP1_ETH_MASK); 276 277 /* Need to update PMCCLRR (clear register) */ 278 regmap_write(dwmac->regmap, dwmac->ops->syscfg_clr_off, 279 dwmac->mode_mask); 280 281 /* Update PMCSETR (set register) */ 282 return regmap_update_bits(dwmac->regmap, reg, 283 dwmac->mode_mask, val); 284 } 285 286 static int stm32mp2_configure_syscfg(struct plat_stmmacenet_data *plat_dat, 287 u8 phy_intf_sel) 288 { 289 struct stm32_dwmac *dwmac = plat_dat->bsp_priv; 290 u32 reg = dwmac->mode_reg; 291 int val; 292 293 val = FIELD_PREP(SYSCFG_ETHCR_ETH_SEL_MASK, phy_intf_sel); 294 295 switch (plat_dat->phy_interface) { 296 case PHY_INTERFACE_MODE_MII: 297 /* ETH_REF_CLK_SEL bit in SYSCFG register is not applicable in MII mode */ 298 break; 299 case PHY_INTERFACE_MODE_RMII: 300 if (dwmac->enable_eth_ck) { 301 /* Internal clock ETH_CLK of 50MHz from RCC is used */ 302 val |= SYSCFG_ETHCR_ETH_REF_CLK_SEL; 303 } 304 break; 305 case PHY_INTERFACE_MODE_RGMII: 306 case PHY_INTERFACE_MODE_RGMII_ID: 307 case PHY_INTERFACE_MODE_RGMII_RXID: 308 case PHY_INTERFACE_MODE_RGMII_TXID: 309 case PHY_INTERFACE_MODE_GMII: 310 if (dwmac->enable_eth_ck) { 311 /* Internal clock ETH_CLK of 125MHz from RCC is used */ 312 val |= SYSCFG_ETHCR_ETH_CLK_SEL; 313 } 314 break; 315 default: 316 dev_err(dwmac->dev, "Mode %s not supported", 317 phy_modes(plat_dat->phy_interface)); 318 /* Do not manage others interfaces */ 319 return -EINVAL; 320 } 321 322 dev_dbg(dwmac->dev, "Mode %s", phy_modes(plat_dat->phy_interface)); 323 324 /* Select PTP (IEEE1588) clock selection from RCC (ck_ker_ethxptp) */ 325 val |= SYSCFG_ETHCR_ETH_PTP_CLK_SEL; 326 327 /* Update ETHCR (set register) */ 328 return regmap_update_bits(dwmac->regmap, reg, 329 SYSCFG_MP2_ETH_MASK, val); 330 } 331 332 static int stm32mp1_set_mode(struct plat_stmmacenet_data *plat_dat) 333 { 334 struct stm32_dwmac *dwmac = plat_dat->bsp_priv; 335 int phy_intf_sel, ret; 336 337 ret = stm32mp1_select_ethck_external(plat_dat); 338 if (ret) 339 return ret; 340 341 ret = stm32mp1_validate_ethck_rate(plat_dat); 342 if (ret) 343 return ret; 344 345 phy_intf_sel = stmmac_get_phy_intf_sel(plat_dat->phy_interface); 346 if (phy_intf_sel != PHY_INTF_SEL_GMII_MII && 347 phy_intf_sel != PHY_INTF_SEL_RGMII && 348 phy_intf_sel != PHY_INTF_SEL_RMII) { 349 dev_err(dwmac->dev, "Mode %s not supported\n", 350 phy_modes(plat_dat->phy_interface)); 351 return phy_intf_sel < 0 ? phy_intf_sel : -EINVAL; 352 } 353 354 if (!dwmac->ops->is_mp2) 355 return stm32mp1_configure_pmcr(plat_dat, phy_intf_sel); 356 else 357 return stm32mp2_configure_syscfg(plat_dat, phy_intf_sel); 358 } 359 360 static int stm32mcu_set_mode(struct plat_stmmacenet_data *plat_dat) 361 { 362 struct stm32_dwmac *dwmac = plat_dat->bsp_priv; 363 u32 reg = dwmac->mode_reg; 364 int val; 365 366 switch (plat_dat->phy_interface) { 367 case PHY_INTERFACE_MODE_MII: 368 val = SYSCFG_MCU_ETH_SEL_MII; 369 break; 370 case PHY_INTERFACE_MODE_RMII: 371 val = SYSCFG_MCU_ETH_SEL_RMII; 372 break; 373 default: 374 dev_err(dwmac->dev, "Mode %s not supported", 375 phy_modes(plat_dat->phy_interface)); 376 /* Do not manage others interfaces */ 377 return -EINVAL; 378 } 379 380 dev_dbg(dwmac->dev, "Mode %s", phy_modes(plat_dat->phy_interface)); 381 382 return regmap_update_bits(dwmac->regmap, reg, 383 SYSCFG_MCU_ETH_MASK, val << 23); 384 } 385 386 static void stm32_dwmac_clk_disable(struct stm32_dwmac *dwmac) 387 { 388 clk_disable_unprepare(dwmac->clk_tx); 389 clk_disable_unprepare(dwmac->clk_rx); 390 clk_disable_unprepare(dwmac->syscfg_clk); 391 if (dwmac->enable_eth_ck) 392 clk_disable_unprepare(dwmac->clk_eth_ck); 393 } 394 395 static int stm32_dwmac_parse_data(struct stm32_dwmac *dwmac, 396 struct device *dev) 397 { 398 struct device_node *np = dev->of_node; 399 int err; 400 401 /* Get TX/RX clocks */ 402 dwmac->clk_tx = devm_clk_get(dev, "mac-clk-tx"); 403 if (IS_ERR(dwmac->clk_tx)) { 404 dev_err(dev, "No ETH Tx clock provided...\n"); 405 return PTR_ERR(dwmac->clk_tx); 406 } 407 408 dwmac->clk_rx = devm_clk_get(dev, "mac-clk-rx"); 409 if (IS_ERR(dwmac->clk_rx)) { 410 dev_err(dev, "No ETH Rx clock provided...\n"); 411 return PTR_ERR(dwmac->clk_rx); 412 } 413 414 if (dwmac->ops->parse_data) { 415 err = dwmac->ops->parse_data(dwmac, dev); 416 if (err) 417 return err; 418 } 419 420 /* Get mode register */ 421 dwmac->regmap = syscon_regmap_lookup_by_phandle_args(np, "st,syscon", 422 1, &dwmac->mode_reg); 423 if (IS_ERR(dwmac->regmap)) 424 return PTR_ERR(dwmac->regmap); 425 426 if (dwmac->ops->is_mp2) 427 return 0; 428 429 dwmac->mode_mask = SYSCFG_MP1_ETH_MASK; 430 err = of_property_read_u32_index(np, "st,syscon", 2, &dwmac->mode_mask); 431 if (err) { 432 if (dwmac->ops->is_mp13) { 433 dev_err(dev, "Sysconfig register mask must be set (%d)\n", err); 434 } else { 435 dev_dbg(dev, "Warning sysconfig register mask not set\n"); 436 err = 0; 437 } 438 } 439 440 return err; 441 } 442 443 static int stm32mp1_parse_data(struct stm32_dwmac *dwmac, 444 struct device *dev) 445 { 446 struct platform_device *pdev = to_platform_device(dev); 447 struct device_node *np = dev->of_node; 448 int err = 0; 449 450 /* Ethernet PHY have no crystal */ 451 dwmac->ext_phyclk = of_property_read_bool(np, "st,ext-phyclk"); 452 453 /* Gigabit Ethernet 125MHz clock selection. */ 454 dwmac->eth_clk_sel_reg = of_property_read_bool(np, "st,eth-clk-sel"); 455 456 /* Ethernet 50MHz RMII clock selection */ 457 dwmac->eth_ref_clk_sel_reg = 458 of_property_read_bool(np, "st,eth-ref-clk-sel"); 459 460 /* Get ETH_CLK clocks */ 461 dwmac->clk_eth_ck = devm_clk_get(dev, "eth-ck"); 462 if (IS_ERR(dwmac->clk_eth_ck)) { 463 dev_info(dev, "No phy clock provided...\n"); 464 dwmac->clk_eth_ck = NULL; 465 } 466 467 /* Clock used for low power mode */ 468 dwmac->clk_ethstp = devm_clk_get(dev, "ethstp"); 469 if (IS_ERR(dwmac->clk_ethstp)) { 470 dev_err(dev, 471 "No ETH peripheral clock provided for CStop mode ...\n"); 472 return PTR_ERR(dwmac->clk_ethstp); 473 } 474 475 /* Optional Clock for sysconfig */ 476 dwmac->syscfg_clk = devm_clk_get(dev, "syscfg-clk"); 477 if (IS_ERR(dwmac->syscfg_clk)) 478 dwmac->syscfg_clk = NULL; 479 480 /* Get IRQ information early to have an ability to ask for deferred 481 * probe if needed before we went too far with resource allocation. 482 */ 483 dwmac->irq_pwr_wakeup = platform_get_irq_byname_optional(pdev, 484 "stm32_pwr_wakeup"); 485 if (dwmac->irq_pwr_wakeup == -EPROBE_DEFER) 486 return -EPROBE_DEFER; 487 488 if (!dwmac->clk_eth_ck && dwmac->irq_pwr_wakeup >= 0) { 489 err = device_init_wakeup(&pdev->dev, true); 490 if (err) { 491 dev_err(&pdev->dev, "Failed to init wake up irq\n"); 492 return err; 493 } 494 err = dev_pm_set_dedicated_wake_irq(&pdev->dev, 495 dwmac->irq_pwr_wakeup); 496 if (err) { 497 dev_err(&pdev->dev, "Failed to set wake up irq\n"); 498 device_init_wakeup(&pdev->dev, false); 499 } 500 device_set_wakeup_enable(&pdev->dev, false); 501 } 502 return err; 503 } 504 505 static int stm32_dwmac_suspend(struct device *dev, void *bsp_priv) 506 { 507 struct stm32_dwmac *dwmac = bsp_priv; 508 509 stm32_dwmac_clk_disable(dwmac); 510 511 return dwmac->ops->suspend ? dwmac->ops->suspend(dwmac) : 0; 512 } 513 514 static int stm32_dwmac_resume(struct device *dev, void *bsp_priv) 515 { 516 struct stmmac_priv *priv = netdev_priv(dev_get_drvdata(dev)); 517 struct stm32_dwmac *dwmac = bsp_priv; 518 519 if (dwmac->ops->resume) 520 dwmac->ops->resume(dwmac); 521 522 return stm32_dwmac_init(priv->plat); 523 } 524 525 static int stm32_dwmac_probe(struct platform_device *pdev) 526 { 527 struct plat_stmmacenet_data *plat_dat; 528 struct stmmac_resources stmmac_res; 529 struct stm32_dwmac *dwmac; 530 const struct stm32_ops *data; 531 int ret; 532 533 ret = stmmac_get_platform_resources(pdev, &stmmac_res); 534 if (ret) 535 return ret; 536 537 plat_dat = devm_stmmac_probe_config_dt(pdev, stmmac_res.mac); 538 if (IS_ERR(plat_dat)) 539 return PTR_ERR(plat_dat); 540 541 dwmac = devm_kzalloc(&pdev->dev, sizeof(*dwmac), GFP_KERNEL); 542 if (!dwmac) 543 return -ENOMEM; 544 545 data = of_device_get_match_data(&pdev->dev); 546 if (!data) { 547 dev_err(&pdev->dev, "no of match data provided\n"); 548 return -EINVAL; 549 } 550 551 dwmac->ops = data; 552 dwmac->dev = &pdev->dev; 553 554 ret = stm32_dwmac_parse_data(dwmac, &pdev->dev); 555 if (ret) { 556 dev_err(&pdev->dev, "Unable to parse OF data\n"); 557 return ret; 558 } 559 560 plat_dat->flags |= STMMAC_FLAG_EN_TX_LPI_CLK_PHY_CAP; 561 plat_dat->bsp_priv = dwmac; 562 plat_dat->suspend = stm32_dwmac_suspend; 563 plat_dat->resume = stm32_dwmac_resume; 564 565 ret = stm32_dwmac_init(plat_dat); 566 if (ret) 567 return ret; 568 569 /* If this platform requires the clock to be running in suspend, 570 * prepare and enable the receive clock an additional time to keep 571 * it running. 572 */ 573 if (dwmac->ops->clk_rx_enable_in_suspend) { 574 ret = clk_prepare_enable(dwmac->clk_rx); 575 if (ret) 576 goto err_clk_disable; 577 } 578 579 ret = stmmac_dvr_probe(&pdev->dev, plat_dat, &stmmac_res); 580 if (ret) 581 goto err_clk_disable_suspend; 582 583 return 0; 584 585 err_clk_disable_suspend: 586 if (dwmac->ops->clk_rx_enable_in_suspend) 587 clk_disable_unprepare(dwmac->clk_rx); 588 589 err_clk_disable: 590 stm32_dwmac_clk_disable(dwmac); 591 592 return ret; 593 } 594 595 static void stm32_dwmac_remove(struct platform_device *pdev) 596 { 597 struct net_device *ndev = platform_get_drvdata(pdev); 598 struct stmmac_priv *priv = netdev_priv(ndev); 599 struct stm32_dwmac *dwmac = priv->plat->bsp_priv; 600 601 stmmac_dvr_remove(&pdev->dev); 602 603 /* If this platform requires the clock to be running in suspend, 604 * we need to disable and unprepare the receive clock an additional 605 * time to balance the extra clk_prepare_enable() in the probe 606 * function. 607 */ 608 if (dwmac->ops->clk_rx_enable_in_suspend) 609 clk_disable_unprepare(dwmac->clk_rx); 610 611 stm32_dwmac_clk_disable(dwmac); 612 613 if (dwmac->irq_pwr_wakeup >= 0) { 614 dev_pm_clear_wake_irq(&pdev->dev); 615 device_init_wakeup(&pdev->dev, false); 616 } 617 } 618 619 static int stm32mp1_suspend(struct stm32_dwmac *dwmac) 620 { 621 return clk_prepare_enable(dwmac->clk_ethstp); 622 } 623 624 static void stm32mp1_resume(struct stm32_dwmac *dwmac) 625 { 626 clk_disable_unprepare(dwmac->clk_ethstp); 627 } 628 629 static struct stm32_ops stm32mcu_dwmac_data = { 630 .set_mode = stm32mcu_set_mode 631 }; 632 633 static struct stm32_ops stm32mp1_dwmac_data = { 634 .set_mode = stm32mp1_set_mode, 635 .suspend = stm32mp1_suspend, 636 .resume = stm32mp1_resume, 637 .parse_data = stm32mp1_parse_data, 638 .syscfg_clr_off = 0x44, 639 .is_mp13 = false, 640 .clk_rx_enable_in_suspend = true 641 }; 642 643 static struct stm32_ops stm32mp13_dwmac_data = { 644 .set_mode = stm32mp1_set_mode, 645 .suspend = stm32mp1_suspend, 646 .resume = stm32mp1_resume, 647 .parse_data = stm32mp1_parse_data, 648 .syscfg_clr_off = 0x08, 649 .is_mp13 = true, 650 .clk_rx_enable_in_suspend = true 651 }; 652 653 static struct stm32_ops stm32mp25_dwmac_data = { 654 .set_mode = stm32mp1_set_mode, 655 .suspend = stm32mp1_suspend, 656 .resume = stm32mp1_resume, 657 .parse_data = stm32mp1_parse_data, 658 .is_mp2 = true, 659 .clk_rx_enable_in_suspend = true 660 }; 661 662 static const struct of_device_id stm32_dwmac_match[] = { 663 { .compatible = "st,stm32-dwmac", .data = &stm32mcu_dwmac_data}, 664 { .compatible = "st,stm32mp1-dwmac", .data = &stm32mp1_dwmac_data}, 665 { .compatible = "st,stm32mp13-dwmac", .data = &stm32mp13_dwmac_data}, 666 { .compatible = "st,stm32mp25-dwmac", .data = &stm32mp25_dwmac_data}, 667 { } 668 }; 669 MODULE_DEVICE_TABLE(of, stm32_dwmac_match); 670 671 static struct platform_driver stm32_dwmac_driver = { 672 .probe = stm32_dwmac_probe, 673 .remove = stm32_dwmac_remove, 674 .driver = { 675 .name = "stm32-dwmac", 676 .pm = &stmmac_simple_pm_ops, 677 .of_match_table = stm32_dwmac_match, 678 }, 679 }; 680 module_platform_driver(stm32_dwmac_driver); 681 682 MODULE_AUTHOR("Alexandre Torgue <alexandre.torgue@gmail.com>"); 683 MODULE_AUTHOR("Christophe Roullier <christophe.roullier@st.com>"); 684 MODULE_DESCRIPTION("STMicroelectronics STM32 DWMAC Specific Glue layer"); 685 MODULE_LICENSE("GPL v2"); 686