aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/mach-integrator/integrator_ap.c
diff options
context:
space:
mode:
authorMauro Carvalho Chehab <mchehab@redhat.com>2012-12-27 09:44:11 -0500
committerMauro Carvalho Chehab <mchehab@redhat.com>2012-12-27 09:44:11 -0500
commita44dca1717ce2c2381339e21c07d1731a63a7888 (patch)
tree3d0b3bd26492f9fa1f1f1c1ad838315b266da7c1 /arch/arm/mach-integrator/integrator_ap.c
parent30ebc5e44d057a1619ad63fe32c8c1670c37c4b8 (diff)
parenta49f0d1ea3ec94fc7cf33a7c36a16343b74bd565 (diff)
Merge tag 'v3.8-rc1' into staging/for_v3.9
Linux 3.8-rc1 * tag 'v3.8-rc1': (10696 commits) Linux 3.8-rc1 Revert "nfsd: warn on odd reply state in nfsd_vfs_read" ARM: dts: fix duplicated build target and alphabetical sort out for exynos dm stripe: add WRITE SAME support dm: remove map_info dm snapshot: do not use map_context dm thin: dont use map_context dm raid1: dont use map_context dm flakey: dont use map_context dm raid1: rename read_record to bio_record dm: move target request nr to dm_target_io dm snapshot: use per_bio_data dm verity: use per_bio_data dm raid1: use per_bio_data dm: introduce per_bio_data dm kcopyd: add WRITE SAME support to dm_kcopyd_zero dm linear: add WRITE SAME support dm: add WRITE SAME support dm: prepare to support WRITE SAME dm ioctl: use kmalloc if possible ... Conflicts: MAINTAINERS
Diffstat (limited to 'arch/arm/mach-integrator/integrator_ap.c')
-rw-r--r--arch/arm/mach-integrator/integrator_ap.c163
1 files changed, 133 insertions, 30 deletions
diff --git a/arch/arm/mach-integrator/integrator_ap.c b/arch/arm/mach-integrator/integrator_ap.c
index e6617c134faf..11e2a4145807 100644
--- a/arch/arm/mach-integrator/integrator_ap.c
+++ b/arch/arm/mach-integrator/integrator_ap.c
@@ -31,12 +31,16 @@
31#include <linux/clockchips.h> 31#include <linux/clockchips.h>
32#include <linux/interrupt.h> 32#include <linux/interrupt.h>
33#include <linux/io.h> 33#include <linux/io.h>
34#include <linux/irqchip/versatile-fpga.h>
34#include <linux/mtd/physmap.h> 35#include <linux/mtd/physmap.h>
35#include <linux/clk.h> 36#include <linux/clk.h>
36#include <linux/platform_data/clk-integrator.h> 37#include <linux/platform_data/clk-integrator.h>
37#include <linux/of_irq.h> 38#include <linux/of_irq.h>
38#include <linux/of_address.h> 39#include <linux/of_address.h>
39#include <linux/of_platform.h> 40#include <linux/of_platform.h>
41#include <linux/stat.h>
42#include <linux/sys_soc.h>
43#include <linux/termios.h>
40#include <video/vga.h> 44#include <video/vga.h>
41 45
42#include <mach/hardware.h> 46#include <mach/hardware.h>
@@ -56,11 +60,12 @@
56#include <asm/mach/pci.h> 60#include <asm/mach/pci.h>
57#include <asm/mach/time.h> 61#include <asm/mach/time.h>
58 62
59#include <plat/fpga-irq.h>
60
61#include "common.h" 63#include "common.h"
62 64
63/* 65/* Base address to the AP system controller */
66void __iomem *ap_syscon_base;
67
68/*
64 * All IO addresses are mapped onto VA 0xFFFx.xxxx, where x.xxxx 69 * All IO addresses are mapped onto VA 0xFFFx.xxxx, where x.xxxx
65 * is the (PA >> 12). 70 * is the (PA >> 12).
66 * 71 *
@@ -68,7 +73,6 @@
68 * just for now). 73 * just for now).
69 */ 74 */
70#define VA_IC_BASE __io_address(INTEGRATOR_IC_BASE) 75#define VA_IC_BASE __io_address(INTEGRATOR_IC_BASE)
71#define VA_SC_BASE __io_address(INTEGRATOR_SC_BASE)
72#define VA_EBI_BASE __io_address(INTEGRATOR_EBI_BASE) 76#define VA_EBI_BASE __io_address(INTEGRATOR_EBI_BASE)
73#define VA_CMIC_BASE __io_address(INTEGRATOR_HDR_IC) 77#define VA_CMIC_BASE __io_address(INTEGRATOR_HDR_IC)
74 78
@@ -97,11 +101,6 @@ static struct map_desc ap_io_desc[] __initdata = {
97 .length = SZ_4K, 101 .length = SZ_4K,
98 .type = MT_DEVICE 102 .type = MT_DEVICE
99 }, { 103 }, {
100 .virtual = IO_ADDRESS(INTEGRATOR_SC_BASE),
101 .pfn = __phys_to_pfn(INTEGRATOR_SC_BASE),
102 .length = SZ_4K,
103 .type = MT_DEVICE
104 }, {
105 .virtual = IO_ADDRESS(INTEGRATOR_EBI_BASE), 104 .virtual = IO_ADDRESS(INTEGRATOR_EBI_BASE),
106 .pfn = __phys_to_pfn(INTEGRATOR_EBI_BASE), 105 .pfn = __phys_to_pfn(INTEGRATOR_EBI_BASE),
107 .length = SZ_4K, 106 .length = SZ_4K,
@@ -122,11 +121,6 @@ static struct map_desc ap_io_desc[] __initdata = {
122 .length = SZ_4K, 121 .length = SZ_4K,
123 .type = MT_DEVICE 122 .type = MT_DEVICE
124 }, { 123 }, {
125 .virtual = IO_ADDRESS(INTEGRATOR_UART1_BASE),
126 .pfn = __phys_to_pfn(INTEGRATOR_UART1_BASE),
127 .length = SZ_4K,
128 .type = MT_DEVICE
129 }, {
130 .virtual = IO_ADDRESS(INTEGRATOR_DBG_BASE), 124 .virtual = IO_ADDRESS(INTEGRATOR_DBG_BASE),
131 .pfn = __phys_to_pfn(INTEGRATOR_DBG_BASE), 125 .pfn = __phys_to_pfn(INTEGRATOR_DBG_BASE),
132 .length = SZ_4K, 126 .length = SZ_4K,
@@ -201,8 +195,6 @@ device_initcall(irq_syscore_init);
201/* 195/*
202 * Flash handling. 196 * Flash handling.
203 */ 197 */
204#define SC_CTRLC (VA_SC_BASE + INTEGRATOR_SC_CTRLC_OFFSET)
205#define SC_CTRLS (VA_SC_BASE + INTEGRATOR_SC_CTRLS_OFFSET)
206#define EBI_CSR1 (VA_EBI_BASE + INTEGRATOR_EBI_CSR1_OFFSET) 198#define EBI_CSR1 (VA_EBI_BASE + INTEGRATOR_EBI_CSR1_OFFSET)
207#define EBI_LOCK (VA_EBI_BASE + INTEGRATOR_EBI_LOCK_OFFSET) 199#define EBI_LOCK (VA_EBI_BASE + INTEGRATOR_EBI_LOCK_OFFSET)
208 200
@@ -210,7 +202,8 @@ static int ap_flash_init(struct platform_device *dev)
210{ 202{
211 u32 tmp; 203 u32 tmp;
212 204
213 writel(INTEGRATOR_SC_CTRL_nFLVPPEN | INTEGRATOR_SC_CTRL_nFLWP, SC_CTRLC); 205 writel(INTEGRATOR_SC_CTRL_nFLVPPEN | INTEGRATOR_SC_CTRL_nFLWP,
206 ap_syscon_base + INTEGRATOR_SC_CTRLC_OFFSET);
214 207
215 tmp = readl(EBI_CSR1) | INTEGRATOR_EBI_WRITE_ENABLE; 208 tmp = readl(EBI_CSR1) | INTEGRATOR_EBI_WRITE_ENABLE;
216 writel(tmp, EBI_CSR1); 209 writel(tmp, EBI_CSR1);
@@ -227,7 +220,8 @@ static void ap_flash_exit(struct platform_device *dev)
227{ 220{
228 u32 tmp; 221 u32 tmp;
229 222
230 writel(INTEGRATOR_SC_CTRL_nFLVPPEN | INTEGRATOR_SC_CTRL_nFLWP, SC_CTRLC); 223 writel(INTEGRATOR_SC_CTRL_nFLVPPEN | INTEGRATOR_SC_CTRL_nFLWP,
224 ap_syscon_base + INTEGRATOR_SC_CTRLC_OFFSET);
231 225
232 tmp = readl(EBI_CSR1) & ~INTEGRATOR_EBI_WRITE_ENABLE; 226 tmp = readl(EBI_CSR1) & ~INTEGRATOR_EBI_WRITE_ENABLE;
233 writel(tmp, EBI_CSR1); 227 writel(tmp, EBI_CSR1);
@@ -241,9 +235,12 @@ static void ap_flash_exit(struct platform_device *dev)
241 235
242static void ap_flash_set_vpp(struct platform_device *pdev, int on) 236static void ap_flash_set_vpp(struct platform_device *pdev, int on)
243{ 237{
244 void __iomem *reg = on ? SC_CTRLS : SC_CTRLC; 238 if (on)
245 239 writel(INTEGRATOR_SC_CTRL_nFLVPPEN,
246 writel(INTEGRATOR_SC_CTRL_nFLVPPEN, reg); 240 ap_syscon_base + INTEGRATOR_SC_CTRLS_OFFSET);
241 else
242 writel(INTEGRATOR_SC_CTRL_nFLVPPEN,
243 ap_syscon_base + INTEGRATOR_SC_CTRLC_OFFSET);
247} 244}
248 245
249static struct physmap_flash_data ap_flash_data = { 246static struct physmap_flash_data ap_flash_data = {
@@ -254,6 +251,45 @@ static struct physmap_flash_data ap_flash_data = {
254}; 251};
255 252
256/* 253/*
254 * For the PL010 found in the Integrator/AP some of the UART control is
255 * implemented in the system controller and accessed using a callback
256 * from the driver.
257 */
258static void integrator_uart_set_mctrl(struct amba_device *dev,
259 void __iomem *base, unsigned int mctrl)
260{
261 unsigned int ctrls = 0, ctrlc = 0, rts_mask, dtr_mask;
262 u32 phybase = dev->res.start;
263
264 if (phybase == INTEGRATOR_UART0_BASE) {
265 /* UART0 */
266 rts_mask = 1 << 4;
267 dtr_mask = 1 << 5;
268 } else {
269 /* UART1 */
270 rts_mask = 1 << 6;
271 dtr_mask = 1 << 7;
272 }
273
274 if (mctrl & TIOCM_RTS)
275 ctrlc |= rts_mask;
276 else
277 ctrls |= rts_mask;
278
279 if (mctrl & TIOCM_DTR)
280 ctrlc |= dtr_mask;
281 else
282 ctrls |= dtr_mask;
283
284 __raw_writel(ctrls, ap_syscon_base + INTEGRATOR_SC_CTRLS_OFFSET);
285 __raw_writel(ctrlc, ap_syscon_base + INTEGRATOR_SC_CTRLC_OFFSET);
286}
287
288struct amba_pl010_data ap_uart_data = {
289 .set_mctrl = integrator_uart_set_mctrl,
290};
291
292/*
257 * Where is the timer (VA)? 293 * Where is the timer (VA)?
258 */ 294 */
259#define TIMER0_VA_BASE __io_address(INTEGRATOR_TIMER0_BASE) 295#define TIMER0_VA_BASE __io_address(INTEGRATOR_TIMER0_BASE)
@@ -450,9 +486,9 @@ static struct of_dev_auxdata ap_auxdata_lookup[] __initdata = {
450 OF_DEV_AUXDATA("arm,primecell", INTEGRATOR_RTC_BASE, 486 OF_DEV_AUXDATA("arm,primecell", INTEGRATOR_RTC_BASE,
451 "rtc", NULL), 487 "rtc", NULL),
452 OF_DEV_AUXDATA("arm,primecell", INTEGRATOR_UART0_BASE, 488 OF_DEV_AUXDATA("arm,primecell", INTEGRATOR_UART0_BASE,
453 "uart0", &integrator_uart_data), 489 "uart0", &ap_uart_data),
454 OF_DEV_AUXDATA("arm,primecell", INTEGRATOR_UART1_BASE, 490 OF_DEV_AUXDATA("arm,primecell", INTEGRATOR_UART1_BASE,
455 "uart1", &integrator_uart_data), 491 "uart1", &ap_uart_data),
456 OF_DEV_AUXDATA("arm,primecell", KMI0_BASE, 492 OF_DEV_AUXDATA("arm,primecell", KMI0_BASE,
457 "kmi0", NULL), 493 "kmi0", NULL),
458 OF_DEV_AUXDATA("arm,primecell", KMI1_BASE, 494 OF_DEV_AUXDATA("arm,primecell", KMI1_BASE,
@@ -465,12 +501,60 @@ static struct of_dev_auxdata ap_auxdata_lookup[] __initdata = {
465static void __init ap_init_of(void) 501static void __init ap_init_of(void)
466{ 502{
467 unsigned long sc_dec; 503 unsigned long sc_dec;
504 struct device_node *root;
505 struct device_node *syscon;
506 struct device *parent;
507 struct soc_device *soc_dev;
508 struct soc_device_attribute *soc_dev_attr;
509 u32 ap_sc_id;
510 int err;
468 int i; 511 int i;
469 512
470 of_platform_populate(NULL, of_default_bus_match_table, 513 /* Here we create an SoC device for the root node */
471 ap_auxdata_lookup, NULL); 514 root = of_find_node_by_path("/");
515 if (!root)
516 return;
517 syscon = of_find_node_by_path("/syscon");
518 if (!syscon)
519 return;
520
521 ap_syscon_base = of_iomap(syscon, 0);
522 if (!ap_syscon_base)
523 return;
524
525 ap_sc_id = readl(ap_syscon_base);
526
527 soc_dev_attr = kzalloc(sizeof(*soc_dev_attr), GFP_KERNEL);
528 if (!soc_dev_attr)
529 return;
530
531 err = of_property_read_string(root, "compatible",
532 &soc_dev_attr->soc_id);
533 if (err)
534 return;
535 err = of_property_read_string(root, "model", &soc_dev_attr->machine);
536 if (err)
537 return;
538 soc_dev_attr->family = "Integrator";
539 soc_dev_attr->revision = kasprintf(GFP_KERNEL, "%c",
540 'A' + (ap_sc_id & 0x0f));
541
542 soc_dev = soc_device_register(soc_dev_attr);
543 if (IS_ERR_OR_NULL(soc_dev)) {
544 kfree(soc_dev_attr->revision);
545 kfree(soc_dev_attr);
546 return;
547 }
548
549 parent = soc_device_to_device(soc_dev);
550
551 if (!IS_ERR_OR_NULL(parent))
552 integrator_init_sysfs(parent, ap_sc_id);
472 553
473 sc_dec = readl(VA_SC_BASE + INTEGRATOR_SC_DEC_OFFSET); 554 of_platform_populate(root, of_default_bus_match_table,
555 ap_auxdata_lookup, parent);
556
557 sc_dec = readl(ap_syscon_base + INTEGRATOR_SC_DEC_OFFSET);
474 for (i = 0; i < 4; i++) { 558 for (i = 0; i < 4; i++) {
475 struct lm_device *lmdev; 559 struct lm_device *lmdev;
476 560
@@ -499,7 +583,6 @@ static const char * ap_dt_board_compat[] = {
499DT_MACHINE_START(INTEGRATOR_AP_DT, "ARM Integrator/AP (Device Tree)") 583DT_MACHINE_START(INTEGRATOR_AP_DT, "ARM Integrator/AP (Device Tree)")
500 .reserve = integrator_reserve, 584 .reserve = integrator_reserve,
501 .map_io = ap_map_io, 585 .map_io = ap_map_io,
502 .nr_irqs = NR_IRQS_INTEGRATOR_AP,
503 .init_early = ap_init_early, 586 .init_early = ap_init_early,
504 .init_irq = ap_init_irq_of, 587 .init_irq = ap_init_irq_of,
505 .handle_irq = fpga_handle_irq, 588 .handle_irq = fpga_handle_irq,
@@ -514,6 +597,27 @@ MACHINE_END
514#ifdef CONFIG_ATAGS 597#ifdef CONFIG_ATAGS
515 598
516/* 599/*
600 * For the ATAG boot some static mappings are needed. This will
601 * go away with the ATAG support down the road.
602 */
603
604static struct map_desc ap_io_desc_atag[] __initdata = {
605 {
606 .virtual = IO_ADDRESS(INTEGRATOR_SC_BASE),
607 .pfn = __phys_to_pfn(INTEGRATOR_SC_BASE),
608 .length = SZ_4K,
609 .type = MT_DEVICE
610 },
611};
612
613static void __init ap_map_io_atag(void)
614{
615 iotable_init(ap_io_desc_atag, ARRAY_SIZE(ap_io_desc_atag));
616 ap_syscon_base = __io_address(INTEGRATOR_SC_BASE);
617 ap_map_io();
618}
619
620/*
517 * This is where non-devicetree initialization code is collected and stashed 621 * This is where non-devicetree initialization code is collected and stashed
518 * for eventual deletion. 622 * for eventual deletion.
519 */ 623 */
@@ -581,7 +685,7 @@ static void __init ap_init(void)
581 685
582 platform_device_register(&cfi_flash_device); 686 platform_device_register(&cfi_flash_device);
583 687
584 sc_dec = readl(VA_SC_BASE + INTEGRATOR_SC_DEC_OFFSET); 688 sc_dec = readl(ap_syscon_base + INTEGRATOR_SC_DEC_OFFSET);
585 for (i = 0; i < 4; i++) { 689 for (i = 0; i < 4; i++) {
586 struct lm_device *lmdev; 690 struct lm_device *lmdev;
587 691
@@ -608,8 +712,7 @@ MACHINE_START(INTEGRATOR, "ARM-Integrator")
608 /* Maintainer: ARM Ltd/Deep Blue Solutions Ltd */ 712 /* Maintainer: ARM Ltd/Deep Blue Solutions Ltd */
609 .atag_offset = 0x100, 713 .atag_offset = 0x100,
610 .reserve = integrator_reserve, 714 .reserve = integrator_reserve,
611 .map_io = ap_map_io, 715 .map_io = ap_map_io_atag,
612 .nr_irqs = NR_IRQS_INTEGRATOR_AP,
613 .init_early = ap_init_early, 716 .init_early = ap_init_early,
614 .init_irq = ap_init_irq, 717 .init_irq = ap_init_irq,
615 .handle_irq = fpga_handle_irq, 718 .handle_irq = fpga_handle_irq,