• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2011 Ilya Yanok, Emcraft Systems
3  *
4  * Based on mach-omap2/board-am3517evm.c
5  * Copyright (C) 2009 Texas Instruments Incorporated
6  * Author: Ranjith Lohithakshan <ranjithl@ti.com>
7  *
8  * This program is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License version 2
10  * published by the Free Software Foundation.
11  *
12  * This program is distributed "as is" WITHOUT ANY WARRANTY of any kind,
13  * whether express or implied; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * General Public License for more details.
16  */
17 
18 #include <linux/clk.h>
19 #include <linux/davinci_emac.h>
20 #include <linux/platform_device.h>
21 #include <plat/irqs.h>
22 #include <mach/am35xx.h>
23 
24 #include "control.h"
25 
26 static struct mdio_platform_data am35xx_emac_mdio_pdata;
27 
28 static struct resource am35xx_emac_mdio_resources[] = {
29 	DEFINE_RES_MEM(AM35XX_IPSS_EMAC_BASE + AM35XX_EMAC_MDIO_OFFSET, SZ_4K),
30 };
31 
32 static struct platform_device am35xx_emac_mdio_device = {
33 	.name		= "davinci_mdio",
34 	.id		= 0,
35 	.num_resources	= ARRAY_SIZE(am35xx_emac_mdio_resources),
36 	.resource	= am35xx_emac_mdio_resources,
37 	.dev.platform_data = &am35xx_emac_mdio_pdata,
38 };
39 
am35xx_enable_emac_int(void)40 static void am35xx_enable_emac_int(void)
41 {
42 	u32 regval;
43 
44 	regval = omap_ctrl_readl(AM35XX_CONTROL_LVL_INTR_CLEAR);
45 	regval = (regval | AM35XX_CPGMAC_C0_RX_PULSE_CLR |
46 		  AM35XX_CPGMAC_C0_TX_PULSE_CLR |
47 		  AM35XX_CPGMAC_C0_MISC_PULSE_CLR |
48 		  AM35XX_CPGMAC_C0_RX_THRESH_CLR);
49 	omap_ctrl_writel(regval, AM35XX_CONTROL_LVL_INTR_CLEAR);
50 	regval = omap_ctrl_readl(AM35XX_CONTROL_LVL_INTR_CLEAR);
51 }
52 
am35xx_disable_emac_int(void)53 static void am35xx_disable_emac_int(void)
54 {
55 	u32 regval;
56 
57 	regval = omap_ctrl_readl(AM35XX_CONTROL_LVL_INTR_CLEAR);
58 	regval = (regval | AM35XX_CPGMAC_C0_RX_PULSE_CLR |
59 		  AM35XX_CPGMAC_C0_TX_PULSE_CLR);
60 	omap_ctrl_writel(regval, AM35XX_CONTROL_LVL_INTR_CLEAR);
61 	regval = omap_ctrl_readl(AM35XX_CONTROL_LVL_INTR_CLEAR);
62 }
63 
64 static struct emac_platform_data am35xx_emac_pdata = {
65 	.ctrl_reg_offset	= AM35XX_EMAC_CNTRL_OFFSET,
66 	.ctrl_mod_reg_offset	= AM35XX_EMAC_CNTRL_MOD_OFFSET,
67 	.ctrl_ram_offset	= AM35XX_EMAC_CNTRL_RAM_OFFSET,
68 	.ctrl_ram_size		= AM35XX_EMAC_CNTRL_RAM_SIZE,
69 	.hw_ram_addr		= AM35XX_EMAC_HW_RAM_ADDR,
70 	.version		= EMAC_VERSION_2,
71 	.interrupt_enable	= am35xx_enable_emac_int,
72 	.interrupt_disable	= am35xx_disable_emac_int,
73 };
74 
75 static struct resource am35xx_emac_resources[] = {
76 	DEFINE_RES_MEM(AM35XX_IPSS_EMAC_BASE, 0x30000),
77 	DEFINE_RES_IRQ(INT_35XX_EMAC_C0_RXTHRESH_IRQ),
78 	DEFINE_RES_IRQ(INT_35XX_EMAC_C0_RX_PULSE_IRQ),
79 	DEFINE_RES_IRQ(INT_35XX_EMAC_C0_TX_PULSE_IRQ),
80 	DEFINE_RES_IRQ(INT_35XX_EMAC_C0_MISC_PULSE_IRQ),
81 };
82 
83 static struct platform_device am35xx_emac_device = {
84 	.name		= "davinci_emac",
85 	.id		= -1,
86 	.num_resources	= ARRAY_SIZE(am35xx_emac_resources),
87 	.resource	= am35xx_emac_resources,
88 	.dev		= {
89 		.platform_data	= &am35xx_emac_pdata,
90 	},
91 };
92 
am35xx_emac_init(unsigned long mdio_bus_freq,u8 rmii_en)93 void __init am35xx_emac_init(unsigned long mdio_bus_freq, u8 rmii_en)
94 {
95 	unsigned int regval;
96 	int err;
97 
98 	am35xx_emac_pdata.rmii_en = rmii_en;
99 	am35xx_emac_mdio_pdata.bus_freq = mdio_bus_freq;
100 	err = platform_device_register(&am35xx_emac_device);
101 	if (err) {
102 		pr_err("AM35x: failed registering EMAC device: %d\n", err);
103 		return;
104 	}
105 
106 	err = platform_device_register(&am35xx_emac_mdio_device);
107 	if (err) {
108 		pr_err("AM35x: failed registering EMAC MDIO device: %d\n", err);
109 		platform_device_unregister(&am35xx_emac_device);
110 		return;
111 	}
112 
113 	regval = omap_ctrl_readl(AM35XX_CONTROL_IP_SW_RESET);
114 	regval = regval & (~(AM35XX_CPGMACSS_SW_RST));
115 	omap_ctrl_writel(regval, AM35XX_CONTROL_IP_SW_RESET);
116 	regval = omap_ctrl_readl(AM35XX_CONTROL_IP_SW_RESET);
117 }
118