SOCFPGA updates for 3.15 version 2:
*Update SOCFPGA DTS to include ethernet, sd/mmc, and clock fixes *Add stmmac ethernet glue layer *Update socfpga_defconfig to include sd/mmc, and micrel_phy -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.11 (GNU/Linux) iQIcBAABAgAGBQJTHUB/AAoJEBmUBAuBoyj0jvUQAJ2l8RYqyBdf4vOtr2+SWcr+ Oq7GovRYG0uIihzaYSQRzVh7gCRahP5iyMkxd0vd2NVqxmFSP7qRnErB/Oc+VZvn gK3LXzXXQZOBh9WSA6D/2NkxhJ/OjnSXhWMfIvYomOlwrpwZAzpQX/wWUGCPCUr/ /woJC5XFRWGudyr7/f6EDsy63H0DL58oATDXLRxXYy6UCme2gJlSjWJOVLJp1MDI vSJG5b1uqFtcg9cghgXkJXc/QCreyW0sWAla/Jyr8M8OfO8IZ0Mw94HVT8JaYjkJ iDDLie61IyYXJwC96KAWfnbhvL3+J71gfh8HKqqC5OW94PM/KvGOR1GaUr65rfqf jMivoKNJXb7NTN09z6YB+rjHxMv3F7UBOJKyfsNRACOJmQHaSBxjBEGQ//AQm9SZ Aq41OJx9cGjJRG7lG+M0k6N6LTcNP9QqTFe/ccno32aTscPY++bhKxPeLJRWgtQL YvuxB3p6BEkNfYZ/3c35UCyhkjcvRaXa4TvscRcdR8jrBNaHfveT7O8OvsZPz9BO hgt0c7HZehdiCmJYKa92ZFRgxEHmxL/ZS6CuD6PNO17/5SN2WcS7+wigaPlr/4Hr oVZD6tzzt/cxcjcZ2KirnPUcvFRPrpFiI1UM17xILuT4onlpBX3rxQQlCGF7fugD PdNLQg/XY3mvK54vlFn1 =0sQZ -----END PGP SIGNATURE----- Merge tag 'socfpga_updates_for_3.15_v2' of git://git.rocketboards.org/linux-socfpga-next into next/drivers Merge "SOCFPGA updates for 3.15 version 2" from Dinh Nguyen: *Update SOCFPGA DTS to include ethernet, sd/mmc, and clock fixes *Add stmmac ethernet glue layer *Update socfpga_defconfig to include sd/mmc, and micrel_phy * tag 'socfpga_updates_for_3.15_v2' of git://git.rocketboards.org/linux-socfpga-next: dts: socfpga: Add sysmgr node so the gmac can use to reference dts: socfpga: Add support for SD/MMC on the SOCFPGA platform dts: socfpga: Update clock entry to support multiple parents ARM: socfpga: Update socfpga_defconfig dts: socfpga: Add DTS entry for adding the stmmac glue layer for stmmac. net: stmmac: Add SOCFPGA glue driver Signed-off-by: Arnd Bergmann <arnd@arndb.de>
This commit is contained in:
Коммит
de65ded49e
|
@ -0,0 +1,23 @@
|
|||
* Altera SOCFPGA specific extensions to the Synopsys Designware Mobile
|
||||
Storage Host Controller
|
||||
|
||||
The Synopsys designware mobile storage host controller is used to interface
|
||||
a SoC with storage medium such as eMMC or SD/MMC cards. This file documents
|
||||
differences between the core Synopsys dw mshc controller properties described
|
||||
by synopsys-dw-mshc.txt and the properties used by the Altera SOCFPGA specific
|
||||
extensions to the Synopsys Designware Mobile Storage Host Controller.
|
||||
|
||||
Required Properties:
|
||||
|
||||
* compatible: should be
|
||||
- "altr,socfpga-dw-mshc": for Altera's SOCFPGA platform
|
||||
|
||||
Example:
|
||||
|
||||
mmc: dwmmc0@ff704000 {
|
||||
compatible = "altr,socfpga-dw-mshc";
|
||||
reg = <0xff704000 0x1000>;
|
||||
interrupts = <0 129 4>;
|
||||
#address-cells = <1>;
|
||||
#size-cells = <0>;
|
||||
};
|
|
@ -0,0 +1,35 @@
|
|||
Altera SOCFPGA SoC DWMAC controller
|
||||
|
||||
The device node has following properties.
|
||||
|
||||
Required properties:
|
||||
- compatible : Should contain "altr,socfpga-stmmac"
|
||||
- altr,sysmgr-syscon : Should be the phandle to the system manager node that
|
||||
encompasses the glue register, and the register offset.
|
||||
|
||||
Sub-nodes:
|
||||
The dwmac core should be added as subnode to SOCFPGA dwmac glue.
|
||||
- dwmac : The binding details of dwmac can be found in
|
||||
Documentation/devicetree/bindings/net/stmmac.txt
|
||||
|
||||
Example:
|
||||
|
||||
ethernet0: ethernet0 {
|
||||
#address-cells = <1>;
|
||||
#size-cells = <1>;
|
||||
|
||||
compatible = "altr,socfpga-stmmac";
|
||||
altr,sysmgr-syscon = <&sysmgr 0x60>;
|
||||
status = "disabled";
|
||||
ranges;
|
||||
|
||||
gmac0: gmac0@ff700000 {
|
||||
compatible = "snps,dwmac-3.70a", "snps,dwmac";
|
||||
reg = <0xff700000 0x2000>;
|
||||
interrupts = <0 115 4>;
|
||||
interrupt-names = "macirq";
|
||||
mac-address = [00 00 00 00 00 00];/* Filled in by U-Boot */
|
||||
clocks = <&emac0_clk>;
|
||||
clock-names = "stmmaceth";
|
||||
};
|
||||
};
|
|
@ -92,7 +92,12 @@
|
|||
#address-cells = <1>;
|
||||
#size-cells = <0>;
|
||||
|
||||
osc: osc1 {
|
||||
osc1: osc1 {
|
||||
#clock-cells = <0>;
|
||||
compatible = "fixed-clock";
|
||||
};
|
||||
|
||||
osc2: osc2 {
|
||||
#clock-cells = <0>;
|
||||
compatible = "fixed-clock";
|
||||
};
|
||||
|
@ -100,7 +105,11 @@
|
|||
f2s_periph_ref_clk: f2s_periph_ref_clk {
|
||||
#clock-cells = <0>;
|
||||
compatible = "fixed-clock";
|
||||
clock-frequency = <10000000>;
|
||||
};
|
||||
|
||||
f2s_sdram_ref_clk: f2s_sdram_ref_clk {
|
||||
#clock-cells = <0>;
|
||||
compatible = "fixed-clock";
|
||||
};
|
||||
|
||||
main_pll: main_pll {
|
||||
|
@ -108,7 +117,7 @@
|
|||
#size-cells = <0>;
|
||||
#clock-cells = <0>;
|
||||
compatible = "altr,socfpga-pll-clock";
|
||||
clocks = <&osc>;
|
||||
clocks = <&osc1>;
|
||||
reg = <0x40>;
|
||||
|
||||
mpuclk: mpuclk {
|
||||
|
@ -162,7 +171,7 @@
|
|||
#size-cells = <0>;
|
||||
#clock-cells = <0>;
|
||||
compatible = "altr,socfpga-pll-clock";
|
||||
clocks = <&osc>;
|
||||
clocks = <&osc1>, <&osc2>, <&f2s_periph_ref_clk>;
|
||||
reg = <0x80>;
|
||||
|
||||
emac0_clk: emac0_clk {
|
||||
|
@ -213,7 +222,7 @@
|
|||
#size-cells = <0>;
|
||||
#clock-cells = <0>;
|
||||
compatible = "altr,socfpga-pll-clock";
|
||||
clocks = <&osc>;
|
||||
clocks = <&osc1>, <&osc2>, <&f2s_sdram_ref_clk>;
|
||||
reg = <0xC0>;
|
||||
|
||||
ddr_dqs_clk: ddr_dqs_clk {
|
||||
|
@ -441,26 +450,43 @@
|
|||
};
|
||||
};
|
||||
|
||||
gmac0: ethernet@ff700000 {
|
||||
compatible = "altr,socfpga-stmmac", "snps,dwmac-3.70a", "snps,dwmac";
|
||||
reg = <0xff700000 0x2000>;
|
||||
interrupts = <0 115 4>;
|
||||
interrupt-names = "macirq";
|
||||
mac-address = [00 00 00 00 00 00];/* Filled in by U-Boot */
|
||||
clocks = <&emac0_clk>;
|
||||
clock-names = "stmmaceth";
|
||||
ethernet0: ethernet0 {
|
||||
#address-cells = <1>;
|
||||
#size-cells = <1>;
|
||||
compatible = "altr,socfpga-stmmac";
|
||||
altr,sysmgr-syscon = <&sysmgr 0x60>;
|
||||
status = "disabled";
|
||||
ranges;
|
||||
|
||||
gmac0: gmac0@ff700000 {
|
||||
compatible = "snps,dwmac-3.70a", "snps,dwmac";
|
||||
reg = <0xff700000 0x2000>;
|
||||
interrupts = <0 115 4>;
|
||||
interrupt-names = "macirq";
|
||||
mac-address = [00 00 00 00 00 00];/* Filled in by U-Boot */
|
||||
clocks = <&emac0_clk>;
|
||||
clock-names = "stmmaceth";
|
||||
};
|
||||
};
|
||||
|
||||
gmac1: ethernet@ff702000 {
|
||||
compatible = "altr,socfpga-stmmac", "snps,dwmac-3.70a", "snps,dwmac";
|
||||
reg = <0xff702000 0x2000>;
|
||||
interrupts = <0 120 4>;
|
||||
interrupt-names = "macirq";
|
||||
mac-address = [00 00 00 00 00 00];/* Filled in by U-Boot */
|
||||
clocks = <&emac1_clk>;
|
||||
clock-names = "stmmaceth";
|
||||
ethernet1: ethernet1 {
|
||||
#address-cells = <1>;
|
||||
#size-cells = <1>;
|
||||
compatible = "altr,socfpga-stmmac";
|
||||
altr,sysmgr-syscon = <&sysmgr 0x60>;
|
||||
status = "disabled";
|
||||
ranges;
|
||||
|
||||
gmac1: gmac1@ff702000 {
|
||||
device_type = "network";
|
||||
compatible = "snps,dwmac-3.70a", "snps,dwmac";
|
||||
reg = <0xff702000 0x2000>;
|
||||
interrupts = <0 120 4>;
|
||||
interrupt-names = "macirq";
|
||||
mac-address = [00 00 00 00 00 00];/* Filled in by U-Boot */
|
||||
clocks = <&emac1_clk>;
|
||||
clock-names = "stmmaceth";
|
||||
};
|
||||
};
|
||||
|
||||
L2: l2-cache@fffef000 {
|
||||
|
@ -473,6 +499,17 @@
|
|||
arm,data-latency = <2 1 1>;
|
||||
};
|
||||
|
||||
mmc: dwmmc0@ff704000 {
|
||||
compatible = "altr,socfpga-dw-mshc";
|
||||
reg = <0xff704000 0x1000>;
|
||||
interrupts = <0 139 4>;
|
||||
fifo-depth = <0x400>;
|
||||
#address-cells = <1>;
|
||||
#size-cells = <0>;
|
||||
clocks = <&l4_mp_clk>, <&sdmmc_clk>;
|
||||
clock-names = "biu", "ciu";
|
||||
};
|
||||
|
||||
/* Local timer */
|
||||
timer@fffec600 {
|
||||
compatible = "arm,cortex-a9-twd-timer";
|
||||
|
@ -526,9 +563,9 @@
|
|||
reg = <0xffd05000 0x1000>;
|
||||
};
|
||||
|
||||
sysmgr@ffd08000 {
|
||||
compatible = "altr,sys-mgr";
|
||||
reg = <0xffd08000 0x4000>;
|
||||
};
|
||||
sysmgr: sysmgr@ffd08000 {
|
||||
compatible = "altr,sys-mgr", "syscon";
|
||||
reg = <0xffd08000 0x4000>;
|
||||
};
|
||||
};
|
||||
};
|
||||
|
|
|
@ -27,6 +27,17 @@
|
|||
};
|
||||
};
|
||||
|
||||
dwmmc0@ff704000 {
|
||||
num-slots = <1>;
|
||||
supports-highspeed;
|
||||
broken-cd;
|
||||
|
||||
slot@0 {
|
||||
reg = <0>;
|
||||
bus-width = <4>;
|
||||
};
|
||||
};
|
||||
|
||||
serial0@ffc02000 {
|
||||
clock-frequency = <100000000>;
|
||||
};
|
||||
|
|
|
@ -37,4 +37,28 @@
|
|||
*/
|
||||
ethernet0 = &gmac1;
|
||||
};
|
||||
|
||||
aliases {
|
||||
/* this allow the ethaddr uboot environmnet variable contents
|
||||
* to be added to the gmac1 device tree blob.
|
||||
*/
|
||||
ethernet0 = &gmac1;
|
||||
};
|
||||
};
|
||||
|
||||
ðernet1 {
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
&gmac1 {
|
||||
phy-mode = "rgmii";
|
||||
|
||||
rxd0-skew-ps = <0>;
|
||||
rxd1-skew-ps = <0>;
|
||||
rxd2-skew-ps = <0>;
|
||||
rxd3-skew-ps = <0>;
|
||||
txen-skew-ps = <0>;
|
||||
txc-skew-ps = <2600>;
|
||||
rxdv-skew-ps = <0>;
|
||||
rxc-skew-ps = <2000>;
|
||||
};
|
||||
|
|
|
@ -28,6 +28,17 @@
|
|||
};
|
||||
};
|
||||
|
||||
dwmmc0@ff704000 {
|
||||
num-slots = <1>;
|
||||
supports-highspeed;
|
||||
broken-cd;
|
||||
|
||||
slot@0 {
|
||||
reg = <0>;
|
||||
bus-width = <4>;
|
||||
};
|
||||
};
|
||||
|
||||
ethernet@ff702000 {
|
||||
phy-mode = "rgmii";
|
||||
phy-addr = <0xffffffff>; /* probe for phy addr */
|
||||
|
|
|
@ -38,3 +38,20 @@
|
|||
ethernet0 = &gmac1;
|
||||
};
|
||||
};
|
||||
|
||||
ðernet1 {
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
&gmac1 {
|
||||
phy-mode = "rgmii";
|
||||
|
||||
rxd0-skew-ps = <0>;
|
||||
rxd1-skew-ps = <0>;
|
||||
rxd2-skew-ps = <0>;
|
||||
rxd3-skew-ps = <0>;
|
||||
txen-skew-ps = <0>;
|
||||
txc-skew-ps = <2600>;
|
||||
rxdv-skew-ps = <0>;
|
||||
rxc-skew-ps = <2000>;
|
||||
};
|
||||
|
|
|
@ -30,8 +30,28 @@
|
|||
device_type = "memory";
|
||||
reg = <0x0 0x40000000>; /* 1GB */
|
||||
};
|
||||
|
||||
aliases {
|
||||
/* this allow the ethaddr uboot environmnet variable contents
|
||||
* to be added to the gmac1 device tree blob.
|
||||
*/
|
||||
ethernet0 = &gmac1;
|
||||
};
|
||||
};
|
||||
|
||||
ðernet1 {
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
&gmac1 {
|
||||
status = "okay";
|
||||
phy-mode = "rgmii";
|
||||
|
||||
rxd0-skew-ps = <0>;
|
||||
rxd1-skew-ps = <0>;
|
||||
rxd2-skew-ps = <0>;
|
||||
rxd3-skew-ps = <0>;
|
||||
txen-skew-ps = <0>;
|
||||
txc-skew-ps = <2600>;
|
||||
rxdv-skew-ps = <0>;
|
||||
rxc-skew-ps = <2000>;
|
||||
};
|
||||
|
|
|
@ -41,6 +41,17 @@
|
|||
};
|
||||
};
|
||||
|
||||
dwmmc0@ff704000 {
|
||||
num-slots = <1>;
|
||||
supports-highspeed;
|
||||
broken-cd;
|
||||
|
||||
slot@0 {
|
||||
reg = <0>;
|
||||
bus-width = <4>;
|
||||
};
|
||||
};
|
||||
|
||||
ethernet@ff700000 {
|
||||
phy-mode = "gmii";
|
||||
status = "okay";
|
||||
|
@ -75,3 +86,11 @@
|
|||
};
|
||||
};
|
||||
};
|
||||
|
||||
ðernet0 {
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
&gmac0 {
|
||||
phy-mode = "gmii";
|
||||
};
|
||||
|
|
|
@ -52,6 +52,7 @@ CONFIG_BLK_DEV_SD=y
|
|||
# CONFIG_SCSI_LOWLEVEL is not set
|
||||
CONFIG_NETDEVICES=y
|
||||
CONFIG_STMMAC_ETH=y
|
||||
CONFIG_MICREL_PHY=y
|
||||
# CONFIG_STMMAC_PHY_ID_ZERO_WORKAROUND is not set
|
||||
CONFIG_INPUT_EVDEV=y
|
||||
# CONFIG_SERIO_SERPORT is not set
|
||||
|
@ -66,6 +67,9 @@ CONFIG_SERIAL_8250_DW=y
|
|||
CONFIG_EXT2_FS=y
|
||||
CONFIG_EXT2_FS_XATTR=y
|
||||
CONFIG_EXT2_FS_POSIX_ACL=y
|
||||
CONFIG_EXT3_FS=y
|
||||
CONFIG_NFS_FS=y
|
||||
CONFIG_ROOT_NFS=y
|
||||
# CONFIG_DNOTIFY is not set
|
||||
# CONFIG_INOTIFY_USER is not set
|
||||
CONFIG_VFAT_FS=y
|
||||
|
@ -82,3 +86,5 @@ CONFIG_DEBUG_INFO=y
|
|||
CONFIG_ENABLE_DEFAULT_TRACERS=y
|
||||
CONFIG_DEBUG_USER=y
|
||||
CONFIG_XZ_DEC=y
|
||||
CONFIG_MMC=y
|
||||
CONFIG_MMC_DW=y
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
obj-$(CONFIG_STMMAC_ETH) += stmmac.o
|
||||
stmmac-$(CONFIG_ARCH_SOCFPGA) += dwmac-socfpga.o
|
||||
stmmac-$(CONFIG_STMMAC_PLATFORM) += stmmac_platform.o
|
||||
stmmac-$(CONFIG_STMMAC_PCI) += stmmac_pci.o
|
||||
stmmac-$(CONFIG_DWMAC_SUNXI) += dwmac-sunxi.o
|
||||
|
|
|
@ -0,0 +1,183 @@
|
|||
/* Copyright (C) 2014 Altera Corporation
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* Adopted from dwmac-sti.c
|
||||
*/
|
||||
|
||||
#include <linux/clk.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/mfd/syscon.h>
|
||||
#include <linux/of.h>
|
||||
#include <linux/of_address.h>
|
||||
#include <linux/of_net.h>
|
||||
#include <linux/of_platform.h>
|
||||
#include <linux/phy.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/regmap.h>
|
||||
#include <linux/stmmac.h>
|
||||
|
||||
#define SYSMGR_EMACGRP_CTRL_PHYSEL_ENUM_GMII_MII 0x0
|
||||
#define SYSMGR_EMACGRP_CTRL_PHYSEL_ENUM_RGMII 0x1
|
||||
#define SYSMGR_EMACGRP_CTRL_PHYSEL_ENUM_RMII 0x2
|
||||
#define SYSMGR_EMACGRP_CTRL_PHYSEL_WIDTH 2
|
||||
#define SYSMGR_EMACGRP_CTRL_PHYSEL_MASK 0x00000003
|
||||
|
||||
struct socfpga_dwmac {
|
||||
int interface;
|
||||
u32 reg_offset;
|
||||
struct device *dev;
|
||||
struct regmap *sys_mgr_base_addr;
|
||||
struct device_node *dwmac_np;
|
||||
};
|
||||
|
||||
static int socfpga_dwmac_parse_data(struct socfpga_dwmac *dwmac, struct device *dev)
|
||||
{
|
||||
struct device_node *np = dev->of_node;
|
||||
struct device_node *stmmac_np;
|
||||
struct regmap *sys_mgr_base_addr;
|
||||
u32 reg_offset;
|
||||
int ret;
|
||||
|
||||
stmmac_np = of_get_next_available_child(np, NULL);
|
||||
if (!stmmac_np) {
|
||||
dev_info(dev, "No dwmac node found\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (!of_device_is_compatible(stmmac_np, "snps,dwmac")) {
|
||||
dev_info(dev, "dwmac node isn't compatible with snps,dwmac\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
dwmac->interface = of_get_phy_mode(stmmac_np);
|
||||
of_node_put(stmmac_np);
|
||||
|
||||
sys_mgr_base_addr = syscon_regmap_lookup_by_phandle(np, "altr,sysmgr-syscon");
|
||||
if (IS_ERR(sys_mgr_base_addr)) {
|
||||
dev_info(dev, "No sysmgr-syscon node found\n");
|
||||
return PTR_ERR(sys_mgr_base_addr);
|
||||
}
|
||||
|
||||
ret = of_property_read_u32_index(np, "altr,sysmgr-syscon", 1, ®_offset);
|
||||
if (ret) {
|
||||
dev_info(dev, "Could not reg_offset into sysmgr-syscon!\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
dwmac->reg_offset = reg_offset;
|
||||
dwmac->sys_mgr_base_addr = sys_mgr_base_addr;
|
||||
dwmac->dwmac_np = stmmac_np;
|
||||
dwmac->dev = dev;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int socfpga_dwmac_setup(struct socfpga_dwmac *dwmac)
|
||||
{
|
||||
struct regmap *sys_mgr_base_addr = dwmac->sys_mgr_base_addr;
|
||||
int phymode = dwmac->interface;
|
||||
u32 reg_offset = dwmac->reg_offset;
|
||||
u32 ctrl, val, shift = 0;
|
||||
|
||||
if (of_machine_is_compatible("altr,socfpga-vt"))
|
||||
return 0;
|
||||
|
||||
switch (phymode) {
|
||||
case PHY_INTERFACE_MODE_RGMII:
|
||||
val = SYSMGR_EMACGRP_CTRL_PHYSEL_ENUM_RGMII;
|
||||
break;
|
||||
case PHY_INTERFACE_MODE_MII:
|
||||
case PHY_INTERFACE_MODE_GMII:
|
||||
val = SYSMGR_EMACGRP_CTRL_PHYSEL_ENUM_GMII_MII;
|
||||
break;
|
||||
default:
|
||||
dev_err(dwmac->dev, "bad phy mode %d\n", phymode);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
regmap_read(sys_mgr_base_addr, reg_offset, &ctrl);
|
||||
ctrl &= ~(SYSMGR_EMACGRP_CTRL_PHYSEL_MASK << shift);
|
||||
ctrl |= val << shift;
|
||||
|
||||
regmap_write(sys_mgr_base_addr, reg_offset, ctrl);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int socfpga_dwmac_probe(struct platform_device *pdev)
|
||||
{
|
||||
struct device *dev = &pdev->dev;
|
||||
struct device_node *node = dev->of_node;
|
||||
int ret = -ENOMEM;
|
||||
struct socfpga_dwmac *dwmac;
|
||||
|
||||
dwmac = devm_kzalloc(dev, sizeof(*dwmac), GFP_KERNEL);
|
||||
if (!dwmac)
|
||||
return -ENOMEM;
|
||||
|
||||
ret = socfpga_dwmac_parse_data(dwmac, dev);
|
||||
if (ret) {
|
||||
dev_err(dev, "Unable to parse OF data\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = socfpga_dwmac_setup(dwmac);
|
||||
if (ret) {
|
||||
dev_err(dev, "couldn't setup SoC glue (%d)\n", ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (node) {
|
||||
ret = of_platform_populate(node, NULL, NULL, dev);
|
||||
if (ret) {
|
||||
dev_err(dev, "failed to add dwmac core\n");
|
||||
return ret;
|
||||
}
|
||||
} else {
|
||||
dev_err(dev, "no device node, failed to add dwmac core\n");
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
platform_set_drvdata(pdev, dwmac);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int socfpga_dwmac_remove(struct platform_device *pdev)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const struct of_device_id socfpga_dwmac_match[] = {
|
||||
{ .compatible = "altr,socfpga-stmmac" },
|
||||
{},
|
||||
};
|
||||
MODULE_DEVICE_TABLE(of, socfpga_dwmac_match);
|
||||
|
||||
static struct platform_driver socfpga_dwmac_driver = {
|
||||
.probe = socfpga_dwmac_probe,
|
||||
.remove = socfpga_dwmac_remove,
|
||||
.driver = {
|
||||
.name = "socfpga-dwmac",
|
||||
.of_match_table = of_match_ptr(socfpga_dwmac_match),
|
||||
},
|
||||
};
|
||||
|
||||
module_platform_driver(socfpga_dwmac_driver);
|
||||
|
||||
MODULE_ALIAS("platform:socfpga-dwmac");
|
||||
MODULE_AUTHOR("Dinh Nguyen <dinguyen@altera.com>");
|
||||
MODULE_LICENSE("GPL v2");
|
||||
MODULE_DESCRIPTION("Altera SOCFPGA DWMAC Glue Layer");
|
Загрузка…
Ссылка в новой задаче