1 /* 2 * Amlogic Meson DWMAC glue layer 3 * 4 * Copyright (C) 2014 Beniamino Galvani <b.galvani@gmail.com> 5 * 6 * This program is free software; you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License version 2 as 8 * published by the Free Software Foundation. 9 * 10 * You should have received a copy of the GNU General Public License 11 * along with this program. If not, see <http://www.gnu.org/licenses/>. 12 */ 13 14 #include <linux/device.h> 15 #include <linux/ethtool.h> 16 #include <linux/io.h> 17 #include <linux/ioport.h> 18 #include <linux/module.h> 19 #include <linux/platform_device.h> 20 #include <linux/stmmac.h> 21 22 #include "stmmac_platform.h" 23 24 #define ETHMAC_SPEED_100 BIT(1) 25 26 struct meson_dwmac { 27 struct device *dev; 28 void __iomem *reg; 29 }; 30 31 static void meson6_dwmac_fix_mac_speed(void *priv, unsigned int speed) 32 { 33 struct meson_dwmac *dwmac = priv; 34 unsigned int val; 35 36 val = readl(dwmac->reg); 37 38 switch (speed) { 39 case SPEED_10: 40 val &= ~ETHMAC_SPEED_100; 41 break; 42 case SPEED_100: 43 val |= ETHMAC_SPEED_100; 44 break; 45 } 46 47 writel(val, dwmac->reg); 48 } 49 50 static int meson6_dwmac_probe(struct platform_device *pdev) 51 { 52 struct plat_stmmacenet_data *plat_dat; 53 struct stmmac_resources stmmac_res; 54 struct meson_dwmac *dwmac; 55 struct resource *res; 56 int ret; 57 58 ret = stmmac_get_platform_resources(pdev, &stmmac_res); 59 if (ret) 60 return ret; 61 62 plat_dat = stmmac_probe_config_dt(pdev, &stmmac_res.mac); 63 if (IS_ERR(plat_dat)) 64 return PTR_ERR(plat_dat); 65 66 dwmac = devm_kzalloc(&pdev->dev, sizeof(*dwmac), GFP_KERNEL); 67 if (!dwmac) 68 return -ENOMEM; 69 70 res = platform_get_resource(pdev, IORESOURCE_MEM, 1); 71 dwmac->reg = devm_ioremap_resource(&pdev->dev, res); 72 if (IS_ERR(dwmac->reg)) 73 return PTR_ERR(dwmac->reg); 74 75 plat_dat->bsp_priv = dwmac; 76 plat_dat->fix_mac_speed = meson6_dwmac_fix_mac_speed; 77 78 return stmmac_dvr_probe(&pdev->dev, plat_dat, &stmmac_res); 79 } 80 81 static const struct of_device_id meson6_dwmac_match[] = { 82 { .compatible = "amlogic,meson6-dwmac" }, 83 { } 84 }; 85 MODULE_DEVICE_TABLE(of, meson6_dwmac_match); 86 87 static struct platform_driver meson6_dwmac_driver = { 88 .probe = meson6_dwmac_probe, 89 .remove = stmmac_pltfr_remove, 90 .driver = { 91 .name = "meson6-dwmac", 92 .pm = &stmmac_pltfr_pm_ops, 93 .of_match_table = meson6_dwmac_match, 94 }, 95 }; 96 module_platform_driver(meson6_dwmac_driver); 97 98 MODULE_AUTHOR("Beniamino Galvani <b.galvani@gmail.com>"); 99 MODULE_DESCRIPTION("Amlogic Meson DWMAC glue layer"); 100 MODULE_LICENSE("GPL v2"); 101