• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  * mach-davinci/devices.c
4  *
5  * DaVinci platform device setup/initialization
6  */
7 
8 #include <linux/init.h>
9 #include <linux/platform_device.h>
10 #include <linux/platform_data/i2c-davinci.h>
11 #include <linux/platform_data/mmc-davinci.h>
12 #include <linux/platform_data/edma.h>
13 #include <linux/dma-mapping.h>
14 #include <linux/io.h>
15 #include <linux/reboot.h>
16 
17 #include <mach/hardware.h>
18 #include <mach/cputype.h>
19 #include <mach/mux.h>
20 #include <mach/time.h>
21 
22 #include "davinci.h"
23 #include "irqs.h"
24 
25 #define DAVINCI_I2C_BASE	     0x01C21000
26 #define DAVINCI_ATA_BASE	     0x01C66000
27 #define DAVINCI_MMCSD0_BASE	     0x01E10000
28 #define DM355_MMCSD0_BASE	     0x01E11000
29 #define DM355_MMCSD1_BASE	     0x01E00000
30 #define DM365_MMCSD0_BASE	     0x01D11000
31 #define DM365_MMCSD1_BASE	     0x01D00000
32 
33 void __iomem  *davinci_sysmod_base;
34 
davinci_map_sysmod(void)35 void davinci_map_sysmod(void)
36 {
37 	davinci_sysmod_base = ioremap_nocache(DAVINCI_SYSTEM_MODULE_BASE,
38 					      0x800);
39 	/*
40 	 * Throw a bug since a lot of board initialization code depends
41 	 * on system module availability. ioremap() failing this early
42 	 * need careful looking into anyway.
43 	 */
44 	BUG_ON(!davinci_sysmod_base);
45 }
46 
47 static struct resource i2c_resources[] = {
48 	{
49 		.start		= DAVINCI_I2C_BASE,
50 		.end		= DAVINCI_I2C_BASE + 0x40,
51 		.flags		= IORESOURCE_MEM,
52 	},
53 	{
54 		.start		= DAVINCI_INTC_IRQ(IRQ_I2C),
55 		.flags		= IORESOURCE_IRQ,
56 	},
57 };
58 
59 static struct platform_device davinci_i2c_device = {
60 	.name           = "i2c_davinci",
61 	.id             = 1,
62 	.num_resources	= ARRAY_SIZE(i2c_resources),
63 	.resource	= i2c_resources,
64 };
65 
davinci_init_i2c(struct davinci_i2c_platform_data * pdata)66 void __init davinci_init_i2c(struct davinci_i2c_platform_data *pdata)
67 {
68 	if (cpu_is_davinci_dm644x())
69 		davinci_cfg_reg(DM644X_I2C);
70 
71 	davinci_i2c_device.dev.platform_data = pdata;
72 	(void) platform_device_register(&davinci_i2c_device);
73 }
74 
75 static struct resource ide_resources[] = {
76 	{
77 		.start		= DAVINCI_ATA_BASE,
78 		.end		= DAVINCI_ATA_BASE + 0x7ff,
79 		.flags		= IORESOURCE_MEM,
80 	},
81 	{
82 		.start		= DAVINCI_INTC_IRQ(IRQ_IDE),
83 		.end		= DAVINCI_INTC_IRQ(IRQ_IDE),
84 		.flags		= IORESOURCE_IRQ,
85 	},
86 };
87 
88 static u64 ide_dma_mask = DMA_BIT_MASK(32);
89 
90 static struct platform_device ide_device = {
91 	.name           = "palm_bk3710",
92 	.id             = -1,
93 	.resource       = ide_resources,
94 	.num_resources  = ARRAY_SIZE(ide_resources),
95 	.dev = {
96 		.dma_mask		= &ide_dma_mask,
97 		.coherent_dma_mask      = DMA_BIT_MASK(32),
98 	},
99 };
100 
davinci_init_ide(void)101 void __init davinci_init_ide(void)
102 {
103 	if (cpu_is_davinci_dm644x()) {
104 		davinci_cfg_reg(DM644X_HPIEN_DISABLE);
105 		davinci_cfg_reg(DM644X_ATAEN);
106 		davinci_cfg_reg(DM644X_HDIREN);
107 	} else if (cpu_is_davinci_dm646x()) {
108 		/* IRQ_DM646X_IDE is the same as IRQ_IDE */
109 		davinci_cfg_reg(DM646X_ATAEN);
110 	} else {
111 		WARN_ON(1);
112 		return;
113 	}
114 
115 	platform_device_register(&ide_device);
116 }
117 
118 #if IS_ENABLED(CONFIG_MMC_DAVINCI)
119 
120 static u64 mmcsd0_dma_mask = DMA_BIT_MASK(32);
121 
122 static struct resource mmcsd0_resources[] = {
123 	{
124 		/* different on dm355 */
125 		.start = DAVINCI_MMCSD0_BASE,
126 		.end   = DAVINCI_MMCSD0_BASE + SZ_4K - 1,
127 		.flags = IORESOURCE_MEM,
128 	},
129 	/* IRQs:  MMC/SD, then SDIO */
130 	{
131 		.start = DAVINCI_INTC_IRQ(IRQ_MMCINT),
132 		.flags = IORESOURCE_IRQ,
133 	}, {
134 		/* different on dm355 */
135 		.start = DAVINCI_INTC_IRQ(IRQ_SDIOINT),
136 		.flags = IORESOURCE_IRQ,
137 	},
138 };
139 
140 static struct platform_device davinci_mmcsd0_device = {
141 	.name = "dm6441-mmc",
142 	.id = 0,
143 	.dev = {
144 		.dma_mask = &mmcsd0_dma_mask,
145 		.coherent_dma_mask = DMA_BIT_MASK(32),
146 	},
147 	.num_resources = ARRAY_SIZE(mmcsd0_resources),
148 	.resource = mmcsd0_resources,
149 };
150 
151 static u64 mmcsd1_dma_mask = DMA_BIT_MASK(32);
152 
153 static struct resource mmcsd1_resources[] = {
154 	{
155 		.start = DM355_MMCSD1_BASE,
156 		.end   = DM355_MMCSD1_BASE + SZ_4K - 1,
157 		.flags = IORESOURCE_MEM,
158 	},
159 	/* IRQs:  MMC/SD, then SDIO */
160 	{
161 		.start = DAVINCI_INTC_IRQ(IRQ_DM355_MMCINT1),
162 		.flags = IORESOURCE_IRQ,
163 	}, {
164 		.start = DAVINCI_INTC_IRQ(IRQ_DM355_SDIOINT1),
165 		.flags = IORESOURCE_IRQ,
166 	},
167 };
168 
169 static struct platform_device davinci_mmcsd1_device = {
170 	.name = "dm6441-mmc",
171 	.id = 1,
172 	.dev = {
173 		.dma_mask = &mmcsd1_dma_mask,
174 		.coherent_dma_mask = DMA_BIT_MASK(32),
175 	},
176 	.num_resources = ARRAY_SIZE(mmcsd1_resources),
177 	.resource = mmcsd1_resources,
178 };
179 
180 
davinci_setup_mmc(int module,struct davinci_mmc_config * config)181 void __init davinci_setup_mmc(int module, struct davinci_mmc_config *config)
182 {
183 	struct platform_device	*pdev = NULL;
184 
185 	if (WARN_ON(cpu_is_davinci_dm646x()))
186 		return;
187 
188 	/* REVISIT: update PINMUX, ARM_IRQMUX, and EDMA_EVTMUX here too;
189 	 * for example if MMCSD1 is used for SDIO, maybe DAT2 is unused.
190 	 *
191 	 * FIXME dm6441 (no MMC/SD), dm357 (one), and dm335 (two) are
192 	 * not handled right here ...
193 	 */
194 	switch (module) {
195 	case 1:
196 		if (cpu_is_davinci_dm355()) {
197 			/* REVISIT we may not need all these pins if e.g. this
198 			 * is a hard-wired SDIO device...
199 			 */
200 			davinci_cfg_reg(DM355_SD1_CMD);
201 			davinci_cfg_reg(DM355_SD1_CLK);
202 			davinci_cfg_reg(DM355_SD1_DATA0);
203 			davinci_cfg_reg(DM355_SD1_DATA1);
204 			davinci_cfg_reg(DM355_SD1_DATA2);
205 			davinci_cfg_reg(DM355_SD1_DATA3);
206 		} else if (cpu_is_davinci_dm365()) {
207 			/* Configure pull down control */
208 			unsigned v;
209 
210 			v = __raw_readl(DAVINCI_SYSMOD_VIRT(SYSMOD_PUPDCTL1));
211 			__raw_writel(v & ~0xfc0,
212 					DAVINCI_SYSMOD_VIRT(SYSMOD_PUPDCTL1));
213 
214 			mmcsd1_resources[0].start = DM365_MMCSD1_BASE;
215 			mmcsd1_resources[0].end = DM365_MMCSD1_BASE +
216 							SZ_4K - 1;
217 			mmcsd1_resources[2].start = DAVINCI_INTC_IRQ(
218 							IRQ_DM365_SDIOINT1);
219 			davinci_mmcsd1_device.name = "da830-mmc";
220 		} else
221 			break;
222 
223 		pdev = &davinci_mmcsd1_device;
224 		break;
225 	case 0:
226 		if (cpu_is_davinci_dm355()) {
227 			mmcsd0_resources[0].start = DM355_MMCSD0_BASE;
228 			mmcsd0_resources[0].end = DM355_MMCSD0_BASE + SZ_4K - 1;
229 			mmcsd0_resources[2].start = DAVINCI_INTC_IRQ(
230 							IRQ_DM355_SDIOINT0);
231 
232 			/* expose all 6 MMC0 signals:  CLK, CMD, DATA[0..3] */
233 			davinci_cfg_reg(DM355_MMCSD0);
234 
235 			/* enable RX EDMA */
236 			davinci_cfg_reg(DM355_EVT26_MMC0_RX);
237 		} else if (cpu_is_davinci_dm365()) {
238 			mmcsd0_resources[0].start = DM365_MMCSD0_BASE;
239 			mmcsd0_resources[0].end = DM365_MMCSD0_BASE +
240 							SZ_4K - 1;
241 			mmcsd0_resources[2].start = DAVINCI_INTC_IRQ(
242 							IRQ_DM365_SDIOINT0);
243 			davinci_mmcsd0_device.name = "da830-mmc";
244 		} else if (cpu_is_davinci_dm644x()) {
245 			/* REVISIT: should this be in board-init code? */
246 			/* Power-on 3.3V IO cells */
247 			__raw_writel(0,
248 				DAVINCI_SYSMOD_VIRT(SYSMOD_VDD3P3VPWDN));
249 			/*Set up the pull regiter for MMC */
250 			davinci_cfg_reg(DM644X_MSTK);
251 		}
252 
253 		pdev = &davinci_mmcsd0_device;
254 		break;
255 	}
256 
257 	if (WARN_ON(!pdev))
258 		return;
259 
260 	pdev->dev.platform_data = config;
261 	platform_device_register(pdev);
262 }
263 
264 #else
265 
davinci_setup_mmc(int module,struct davinci_mmc_config * config)266 void __init davinci_setup_mmc(int module, struct davinci_mmc_config *config)
267 {
268 }
269 
270 #endif
271 
272 /*-------------------------------------------------------------------------*/
273 
274 static struct resource wdt_resources[] = {
275 	{
276 		.start	= DAVINCI_WDOG_BASE,
277 		.end	= DAVINCI_WDOG_BASE + SZ_1K - 1,
278 		.flags	= IORESOURCE_MEM,
279 	},
280 };
281 
282 static struct platform_device davinci_wdt_device = {
283 	.name		= "davinci-wdt",
284 	.id		= -1,
285 	.num_resources	= ARRAY_SIZE(wdt_resources),
286 	.resource	= wdt_resources,
287 };
288 
davinci_init_wdt(void)289 int davinci_init_wdt(void)
290 {
291 	return platform_device_register(&davinci_wdt_device);
292 }
293 
294 static struct platform_device davinci_gpio_device = {
295 	.name	= "davinci_gpio",
296 	.id	= -1,
297 };
298 
davinci_gpio_register(struct resource * res,int size,void * pdata)299 int davinci_gpio_register(struct resource *res, int size, void *pdata)
300 {
301 	davinci_gpio_device.resource = res;
302 	davinci_gpio_device.num_resources = size;
303 	davinci_gpio_device.dev.platform_data = pdata;
304 	return platform_device_register(&davinci_gpio_device);
305 }
306 
307 /*-------------------------------------------------------------------------*/
308 
309 /*-------------------------------------------------------------------------*/
310 
311 struct davinci_timer_instance davinci_timer_instance[2] = {
312 	{
313 		.base		= DAVINCI_TIMER0_BASE,
314 		.bottom_irq	= DAVINCI_INTC_IRQ(IRQ_TINT0_TINT12),
315 		.top_irq	= DAVINCI_INTC_IRQ(IRQ_TINT0_TINT34),
316 	},
317 	{
318 		.base		= DAVINCI_TIMER1_BASE,
319 		.bottom_irq	= DAVINCI_INTC_IRQ(IRQ_TINT1_TINT12),
320 		.top_irq	= DAVINCI_INTC_IRQ(IRQ_TINT1_TINT34),
321 	},
322 };
323 
324