aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/mach-lh7a40x/arch-lpd7a40x.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/arm/mach-lh7a40x/arch-lpd7a40x.c')
-rw-r--r--arch/arm/mach-lh7a40x/arch-lpd7a40x.c200
1 files changed, 140 insertions, 60 deletions
diff --git a/arch/arm/mach-lh7a40x/arch-lpd7a40x.c b/arch/arm/mach-lh7a40x/arch-lpd7a40x.c
index 12e23277c5ea..c0e6854289f1 100644
--- a/arch/arm/mach-lh7a40x/arch-lpd7a40x.c
+++ b/arch/arm/mach-lh7a40x/arch-lpd7a40x.c
@@ -23,6 +23,28 @@
23 23
24#include "common.h" 24#include "common.h"
25 25
26#define CPLD_INT_NETHERNET (1<<0)
27#define CPLD_INTMASK_ETHERNET (1<<2)
28#if defined (CONFIG_MACH_LPD7A400)
29# define CPLD_INT_NTOUCH (1<<1)
30# define CPLD_INTMASK_TOUCH (1<<3)
31# define CPLD_INT_PEN (1<<4)
32# define CPLD_INTMASK_PEN (1<<4)
33# define CPLD_INT_PIRQ (1<<4)
34#endif
35#define CPLD_INTMASK_CPLD (1<<7)
36#define CPLD_INT_CPLD (1<<6)
37
38#define CPLD_CONTROL_SWINT (1<<7) /* Disable all CPLD IRQs */
39#define CPLD_CONTROL_OCMSK (1<<6) /* Mask USB1 connect IRQ */
40#define CPLD_CONTROL_PDRV (1<<5) /* PCC_nDRV high */
41#define CPLD_CONTROL_USB1C (1<<4) /* USB1 connect IRQ active */
42#define CPLD_CONTROL_USB1P (1<<3) /* USB1 power disable */
43#define CPLD_CONTROL_AWKP (1<<2) /* Auto-wakeup disabled */
44#define CPLD_CONTROL_LCD_ENABLE (1<<1) /* LCD Vee enable */
45#define CPLD_CONTROL_WRLAN_NENABLE (1<<0) /* SMC91x power disable */
46
47
26static struct resource smc91x_resources[] = { 48static struct resource smc91x_resources[] = {
27 [0] = { 49 [0] = {
28 .start = CPLD00_PHYS, 50 .start = CPLD00_PHYS,
@@ -48,12 +70,12 @@ static struct platform_device smc91x_device = {
48static struct resource lh7a40x_usbclient_resources[] = { 70static struct resource lh7a40x_usbclient_resources[] = {
49 [0] = { 71 [0] = {
50 .start = USB_PHYS, 72 .start = USB_PHYS,
51 .end = (USB_PHYS + 0xFF), 73 .end = (USB_PHYS + PAGE_SIZE),
52 .flags = IORESOURCE_MEM, 74 .flags = IORESOURCE_MEM,
53 }, 75 },
54 [1] = { 76 [1] = {
55 .start = IRQ_USBINTR, 77 .start = IRQ_USB,
56 .end = IRQ_USBINTR, 78 .end = IRQ_USB,
57 .flags = IORESOURCE_IRQ, 79 .flags = IORESOURCE_IRQ,
58 }, 80 },
59}; 81};
@@ -61,7 +83,8 @@ static struct resource lh7a40x_usbclient_resources[] = {
61static u64 lh7a40x_usbclient_dma_mask = 0xffffffffUL; 83static u64 lh7a40x_usbclient_dma_mask = 0xffffffffUL;
62 84
63static struct platform_device lh7a40x_usbclient_device = { 85static struct platform_device lh7a40x_usbclient_device = {
64 .name = "lh7a40x_udc", 86// .name = "lh7a40x_udc",
87 .name = "lh7-udc",
65 .id = 0, 88 .id = 0,
66 .dev = { 89 .dev = {
67 .dma_mask = &lh7a40x_usbclient_dma_mask, 90 .dma_mask = &lh7a40x_usbclient_dma_mask,
@@ -101,7 +124,7 @@ static struct platform_device lh7a404_usbhost_device = {
101 124
102#endif 125#endif
103 126
104static struct platform_device *lpd7a40x_devs[] __initdata = { 127static struct platform_device* lpd7a40x_devs[] __initdata = {
105 &smc91x_device, 128 &smc91x_device,
106 &lh7a40x_usbclient_device, 129 &lh7a40x_usbclient_device,
107#if defined (CONFIG_ARCH_LH7A404) 130#if defined (CONFIG_ARCH_LH7A404)
@@ -113,29 +136,52 @@ extern void lpd7a400_map_io (void);
113 136
114static void __init lpd7a40x_init (void) 137static void __init lpd7a40x_init (void)
115{ 138{
116 CPLD_CONTROL |= (1<<6); /* Mask USB1 connection IRQ */ 139#if defined (CONFIG_MACH_LPD7A400)
140 CPLD_CONTROL |= 0
141 | CPLD_CONTROL_SWINT /* Disable software interrupt */
142 | CPLD_CONTROL_OCMSK; /* Mask USB1 connection IRQ */
117 CPLD_CONTROL &= ~(0 143 CPLD_CONTROL &= ~(0
118 | (1<<1) /* Disable LCD */ 144 | CPLD_CONTROL_LCD_ENABLE /* Disable LCD */
119 | (1<<0) /* Enable WLAN */ 145 | CPLD_CONTROL_WRLAN_NENABLE /* Enable SMC91x */
120 ); 146 );
147#endif
148
149#if defined (CONFIG_MACH_LPD7A404)
150 CPLD_CONTROL &= ~(0
151 | CPLD_CONTROL_WRLAN_NENABLE /* Enable SMC91x */
152 );
153#endif
121 154
122 platform_add_devices (lpd7a40x_devs, ARRAY_SIZE (lpd7a40x_devs)); 155 platform_add_devices (lpd7a40x_devs, ARRAY_SIZE (lpd7a40x_devs));
156#if defined (CONFIG_FB_ARMCLCD)
157 lh7a40x_clcd_init ();
158#endif
123} 159}
124 160
125static void lh7a40x_ack_cpld_irq (u32 irq) 161static void lh7a40x_ack_cpld_irq (u32 irq)
126{ 162{
127 /* CPLD doesn't have ack capability */ 163 /* CPLD doesn't have ack capability, but some devices may */
164
165#if defined (CPLD_INTMASK_TOUCH)
166 /* The touch control *must* mask the the interrupt because the
167 * interrupt bit is read by the driver to determine if the pen
168 * is still down. */
169 if (irq == IRQ_TOUCH)
170 CPLD_INTERRUPTS |= CPLD_INTMASK_TOUCH;
171#endif
128} 172}
129 173
130static void lh7a40x_mask_cpld_irq (u32 irq) 174static void lh7a40x_mask_cpld_irq (u32 irq)
131{ 175{
132 switch (irq) { 176 switch (irq) {
133 case IRQ_LPD7A40X_ETH_INT: 177 case IRQ_LPD7A40X_ETH_INT:
134 CPLD_INTERRUPTS = CPLD_INTERRUPTS | 0x4; 178 CPLD_INTERRUPTS |= CPLD_INTMASK_ETHERNET;
135 break; 179 break;
136 case IRQ_LPD7A400_TS: 180#if defined (IRQ_TOUCH)
137 CPLD_INTERRUPTS = CPLD_INTERRUPTS | 0x8; 181 case IRQ_TOUCH:
182 CPLD_INTERRUPTS |= CPLD_INTMASK_TOUCH;
138 break; 183 break;
184#endif
139 } 185 }
140} 186}
141 187
@@ -143,11 +189,13 @@ static void lh7a40x_unmask_cpld_irq (u32 irq)
143{ 189{
144 switch (irq) { 190 switch (irq) {
145 case IRQ_LPD7A40X_ETH_INT: 191 case IRQ_LPD7A40X_ETH_INT:
146 CPLD_INTERRUPTS = CPLD_INTERRUPTS & ~ 0x4; 192 CPLD_INTERRUPTS &= ~CPLD_INTMASK_ETHERNET;
147 break; 193 break;
148 case IRQ_LPD7A400_TS: 194#if defined (IRQ_TOUCH)
149 CPLD_INTERRUPTS = CPLD_INTERRUPTS & ~ 0x8; 195 case IRQ_TOUCH:
196 CPLD_INTERRUPTS &= ~CPLD_INTMASK_TOUCH;
150 break; 197 break;
198#endif
151 } 199 }
152} 200}
153 201
@@ -164,11 +212,13 @@ static void lpd7a40x_cpld_handler (unsigned int irq, struct irqdesc *desc,
164 212
165 desc->chip->ack (irq); 213 desc->chip->ack (irq);
166 214
167 if ((mask & 0x1) == 0) /* WLAN */ 215 if ((mask & (1<<0)) == 0) /* WLAN */
168 IRQ_DISPATCH (IRQ_LPD7A40X_ETH_INT); 216 IRQ_DISPATCH (IRQ_LPD7A40X_ETH_INT);
169 217
170 if ((mask & 0x2) == 0) /* Touch */ 218#if defined (IRQ_TOUCH)
171 IRQ_DISPATCH (IRQ_LPD7A400_TS); 219 if ((mask & (1<<1)) == 0) /* Touch */
220 IRQ_DISPATCH (IRQ_TOUCH);
221#endif
172 222
173 desc->chip->unmask (irq); /* Level-triggered need this */ 223 desc->chip->unmask (irq); /* Level-triggered need this */
174} 224}
@@ -204,9 +254,21 @@ void __init lh7a40x_init_board_irq (void)
204 254
205 /* Then, configure CPLD interrupt */ 255 /* Then, configure CPLD interrupt */
206 256
207 CPLD_INTERRUPTS = 0x9c; /* Disable all CPLD interrupts */ 257 /* Disable all CPLD interrupts */
258#if defined (CONFIG_MACH_LPD7A400)
259 CPLD_INTERRUPTS = CPLD_INTMASK_TOUCH | CPLD_INTMASK_PEN
260 | CPLD_INTMASK_ETHERNET;
261 /* *** FIXME: don't know why we need 7 and 4. 7 is way wrong
262 and 4 is uncefined. */
263 // (1<<7)|(1<<4)|(1<<3)|(1<<2);
264#endif
265#if defined (CONFIG_MACH_LPD7A404)
266 CPLD_INTERRUPTS = CPLD_INTMASK_ETHERNET;
267 /* *** FIXME: don't know why we need 6 and 5, neither is defined. */
268 // (1<<6)|(1<<5)|(1<<3);
269#endif
208 GPIO_PFDD &= ~(1 << pinCPLD); /* Make input */ 270 GPIO_PFDD &= ~(1 << pinCPLD); /* Make input */
209 GPIO_INTTYPE1 |= (1 << pinCPLD); /* Edge triggered */ 271 GPIO_INTTYPE1 &= ~(1 << pinCPLD); /* Level triggered */
210 GPIO_INTTYPE2 &= ~(1 << pinCPLD); /* Active low */ 272 GPIO_INTTYPE2 &= ~(1 << pinCPLD); /* Active low */
211 barrier (); 273 barrier ();
212 GPIO_GPIOFINTEN |= (1 << pinCPLD); /* Enable */ 274 GPIO_GPIOFINTEN |= (1 << pinCPLD); /* Enable */
@@ -216,7 +278,7 @@ void __init lh7a40x_init_board_irq (void)
216 for (irq = IRQ_BOARD_START; 278 for (irq = IRQ_BOARD_START;
217 irq < IRQ_BOARD_START + NR_IRQ_BOARD; ++irq) { 279 irq < IRQ_BOARD_START + NR_IRQ_BOARD; ++irq) {
218 set_irq_chip (irq, &lpd7a40x_cpld_chip); 280 set_irq_chip (irq, &lpd7a40x_cpld_chip);
219 set_irq_handler (irq, do_edge_IRQ); 281 set_irq_handler (irq, do_level_IRQ);
220 set_irq_flags (irq, IRQF_VALID); 282 set_irq_flags (irq, IRQF_VALID);
221 } 283 }
222 284
@@ -226,91 +288,109 @@ void __init lh7a40x_init_board_irq (void)
226 lpd7a40x_cpld_handler); 288 lpd7a40x_cpld_handler);
227} 289}
228 290
229static struct map_desc lpd7a400_io_desc[] __initdata = { 291static struct map_desc lpd7a40x_io_desc[] __initdata = {
230 { 292 {
231 .virtual = IO_VIRT, 293 .virtual = IO_VIRT,
232 .pfn = __phys_to_pfn(IO_PHYS), 294 .pfn = __phys_to_pfn(IO_PHYS),
233 .length = IO_SIZE, 295 .length = IO_SIZE,
234 .type = MT_DEVICE 296 .type = MT_DEVICE
235 }, { /* Mapping added to work around chip select problems */ 297 },
298 { /* Mapping added to work around chip select problems */
236 .virtual = IOBARRIER_VIRT, 299 .virtual = IOBARRIER_VIRT,
237 .pfn = __phys_to_pfn(IOBARRIER_PHYS), 300 .pfn = __phys_to_pfn(IOBARRIER_PHYS),
238 .length = IOBARRIER_SIZE, 301 .length = IOBARRIER_SIZE,
239 .type = MT_DEVICE 302 .type = MT_DEVICE
240 }, { 303 },
304 {
241 .virtual = CF_VIRT, 305 .virtual = CF_VIRT,
242 .pfn = __phys_to_pfn(CF_PHYS), 306 .pfn = __phys_to_pfn(CF_PHYS),
243 .length = CF_SIZE, 307 .length = CF_SIZE,
244 .type = MT_DEVICE 308 .type = MT_DEVICE
245 }, { 309 },
310 {
246 .virtual = CPLD02_VIRT, 311 .virtual = CPLD02_VIRT,
247 .pfn = __phys_to_pfn(CPLD02_PHYS), 312 .pfn = __phys_to_pfn(CPLD02_PHYS),
248 .length = CPLD02_SIZE, 313 .length = CPLD02_SIZE,
249 .type = MT_DEVICE 314 .type = MT_DEVICE
250 }, { 315 },
316 {
251 .virtual = CPLD06_VIRT, 317 .virtual = CPLD06_VIRT,
252 .pfn = __phys_to_pfn(CPLD06_PHYS), 318 .pfn = __phys_to_pfn(CPLD06_PHYS),
253 .length = CPLD06_SIZE, 319 .length = CPLD06_SIZE,
320 .type = MT_DEVICE
321 },
322 {
323 .virtual = CPLD08_VIRT,
324 .pfn = __phys_to_pfn(CPLD08_PHYS),
325 .length = CPLD08_SIZE,
254 .type = MT_DEVICE 326 .type = MT_DEVICE
255 }, { 327 },
328 {
256 .virtual = CPLD08_VIRT, 329 .virtual = CPLD08_VIRT,
257 .pfn = __phys_to_pfn(CPLD08_PHYS), 330 .pfn = __phys_to_pfn(CPLD08_PHYS),
258 .length = CPLD08_SIZE, 331 .length = CPLD08_SIZE,
259 .type = MT_DEVICE 332 .type = MT_DEVICE
260 }, { 333 },
334 {
335 .virtual = CPLD0A_VIRT,
336 .pfn = __phys_to_pfn(CPLD0A_PHYS),
337 .length = CPLD0A_SIZE,
338 .type = MT_DEVICE
339 },
340 {
261 .virtual = CPLD0C_VIRT, 341 .virtual = CPLD0C_VIRT,
262 .pfn = __phys_to_pfn(CPLD0C_PHYS), 342 .pfn = __phys_to_pfn(CPLD0C_PHYS),
263 .length = CPLD0C_SIZE, 343 .length = CPLD0C_SIZE,
264 .type = MT_DEVICE 344 .type = MT_DEVICE
265 }, { 345 },
346 {
266 .virtual = CPLD0E_VIRT, 347 .virtual = CPLD0E_VIRT,
267 .pfn = __phys_to_pfn(CPLD0E_PHYS), 348 .pfn = __phys_to_pfn(CPLD0E_PHYS),
268 .length = CPLD0E_SIZE, 349 .length = CPLD0E_SIZE,
269 .type = MT_DEVICE 350 .type = MT_DEVICE
270 }, { 351 },
352 {
271 .virtual = CPLD10_VIRT, 353 .virtual = CPLD10_VIRT,
272 .pfn = __phys_to_pfn(CPLD10_PHYS), 354 .pfn = __phys_to_pfn(CPLD10_PHYS),
273 .length = CPLD10_SIZE, 355 .length = CPLD10_SIZE,
274 .type = MT_DEVICE 356 .type = MT_DEVICE
275 }, { 357 },
358 {
276 .virtual = CPLD12_VIRT, 359 .virtual = CPLD12_VIRT,
277 .pfn = __phys_to_pfn(CPLD12_PHYS), 360 .pfn = __phys_to_pfn(CPLD12_PHYS),
278 .length = CPLD12_SIZE, 361 .length = CPLD12_SIZE,
279 .type = MT_DEVICE 362 .type = MT_DEVICE
280 }, { 363 },
364 {
281 .virtual = CPLD14_VIRT, 365 .virtual = CPLD14_VIRT,
282 .pfn = __phys_to_pfn(CPLD14_PHYS), 366 .pfn = __phys_to_pfn(CPLD14_PHYS),
283 .length = CPLD14_SIZE, 367 .length = CPLD14_SIZE,
284 .type = MT_DEVICE 368 .type = MT_DEVICE
285 }, { 369 },
370 {
286 .virtual = CPLD16_VIRT, 371 .virtual = CPLD16_VIRT,
287 .pfn = __phys_to_pfn(CPLD16_PHYS), 372 .pfn = __phys_to_pfn(CPLD16_PHYS),
288 .length = CPLD16_SIZE, 373 .length = CPLD16_SIZE,
289 .type = MT_DEVICE 374 .type = MT_DEVICE
290 }, { 375 },
376 {
291 .virtual = CPLD18_VIRT, 377 .virtual = CPLD18_VIRT,
292 .pfn = __phys_to_pfn(CPLD18_PHYS), 378 .pfn = __phys_to_pfn(CPLD18_PHYS),
293 .length = CPLD18_SIZE, 379 .length = CPLD18_SIZE,
294 .type = MT_DEVICE 380 .type = MT_DEVICE
295 }, { 381 },
382 {
296 .virtual = CPLD1A_VIRT, 383 .virtual = CPLD1A_VIRT,
297 .pfn = __phys_to_pfn(CPLD1A_PHYS), 384 .pfn = __phys_to_pfn(CPLD1A_PHYS),
298 .length = CPLD1A_SIZE, 385 .length = CPLD1A_SIZE,
299 .type = MT_DEVICE 386 .type = MT_DEVICE
300 }, 387 },
301 /* This mapping is redundant since the smc driver performs another. */
302/* { CPLD00_VIRT, CPLD00_PHYS, CPLD00_SIZE, MT_DEVICE }, */
303}; 388};
304 389
305void __init 390void __init
306lpd7a400_map_io(void) 391lpd7a40x_map_io(void)
307{ 392{
308 iotable_init (lpd7a400_io_desc, ARRAY_SIZE (lpd7a400_io_desc)); 393 iotable_init (lpd7a40x_io_desc, ARRAY_SIZE (lpd7a40x_io_desc));
309
310 /* Fixup (improve) Static Memory Controller settings */
311 SMC_BCR0 = 0x200039af; /* Boot Flash */
312 SMC_BCR6 = 0x1000fbe0; /* CPLD */
313 SMC_BCR7 = 0x1000b2c2; /* Compact Flash */
314} 394}
315 395
316#ifdef CONFIG_MACH_LPD7A400 396#ifdef CONFIG_MACH_LPD7A400
@@ -320,7 +400,7 @@ MACHINE_START (LPD7A400, "Logic Product Development LPD7A400-10")
320 .phys_io = 0x80000000, 400 .phys_io = 0x80000000,
321 .io_pg_offst = ((io_p2v (0x80000000))>>18) & 0xfffc, 401 .io_pg_offst = ((io_p2v (0x80000000))>>18) & 0xfffc,
322 .boot_params = 0xc0000100, 402 .boot_params = 0xc0000100,
323 .map_io = lpd7a400_map_io, 403 .map_io = lpd7a40x_map_io,
324 .init_irq = lh7a400_init_irq, 404 .init_irq = lh7a400_init_irq,
325 .timer = &lh7a40x_timer, 405 .timer = &lh7a40x_timer,
326 .init_machine = lpd7a40x_init, 406 .init_machine = lpd7a40x_init,
@@ -335,7 +415,7 @@ MACHINE_START (LPD7A404, "Logic Product Development LPD7A404-10")
335 .phys_io = 0x80000000, 415 .phys_io = 0x80000000,
336 .io_pg_offst = ((io_p2v (0x80000000))>>18) & 0xfffc, 416 .io_pg_offst = ((io_p2v (0x80000000))>>18) & 0xfffc,
337 .boot_params = 0xc0000100, 417 .boot_params = 0xc0000100,
338 .map_io = lpd7a400_map_io, 418 .map_io = lpd7a40x_map_io,
339 .init_irq = lh7a404_init_irq, 419 .init_irq = lh7a404_init_irq,
340 .timer = &lh7a40x_timer, 420 .timer = &lh7a40x_timer,
341 .init_machine = lpd7a40x_init, 421 .init_machine = lpd7a40x_init,