diff options
Diffstat (limited to 'arch/ppc/syslib/mpc10x_common.c')
-rw-r--r-- | arch/ppc/syslib/mpc10x_common.c | 183 |
1 files changed, 138 insertions, 45 deletions
diff --git a/arch/ppc/syslib/mpc10x_common.c b/arch/ppc/syslib/mpc10x_common.c index fd93adfd464c..0130aeb4a2d3 100644 --- a/arch/ppc/syslib/mpc10x_common.c +++ b/arch/ppc/syslib/mpc10x_common.c | |||
@@ -21,6 +21,9 @@ | |||
21 | #include <linux/init.h> | 21 | #include <linux/init.h> |
22 | #include <linux/pci.h> | 22 | #include <linux/pci.h> |
23 | #include <linux/slab.h> | 23 | #include <linux/slab.h> |
24 | #include <linux/serial_8250.h> | ||
25 | #include <linux/fsl_devices.h> | ||
26 | #include <linux/device.h> | ||
24 | 27 | ||
25 | #include <asm/byteorder.h> | 28 | #include <asm/byteorder.h> |
26 | #include <asm/io.h> | 29 | #include <asm/io.h> |
@@ -30,16 +33,7 @@ | |||
30 | #include <asm/pci-bridge.h> | 33 | #include <asm/pci-bridge.h> |
31 | #include <asm/open_pic.h> | 34 | #include <asm/open_pic.h> |
32 | #include <asm/mpc10x.h> | 35 | #include <asm/mpc10x.h> |
33 | #include <asm/ocp.h> | 36 | #include <asm/ppc_sys.h> |
34 | |||
35 | /* The OCP structure is fixed by code below, before OCP initialises. | ||
36 | paddr depends on where the board places the EUMB. | ||
37 | - fixed in mpc10x_bridge_init(). | ||
38 | irq depends on two things: | ||
39 | > does the board use the EPIC at all? (PCORE does not). | ||
40 | > is the EPIC in serial or parallel mode? | ||
41 | - fixed in mpc10x_set_openpic(). | ||
42 | */ | ||
43 | 37 | ||
44 | #ifdef CONFIG_MPC10X_OPENPIC | 38 | #ifdef CONFIG_MPC10X_OPENPIC |
45 | #ifdef CONFIG_EPIC_SERIAL_MODE | 39 | #ifdef CONFIG_EPIC_SERIAL_MODE |
@@ -51,34 +45,127 @@ | |||
51 | #define MPC10X_DMA0_IRQ (EPIC_IRQ_BASE + 1 + NUM_8259_INTERRUPTS) | 45 | #define MPC10X_DMA0_IRQ (EPIC_IRQ_BASE + 1 + NUM_8259_INTERRUPTS) |
52 | #define MPC10X_DMA1_IRQ (EPIC_IRQ_BASE + 2 + NUM_8259_INTERRUPTS) | 46 | #define MPC10X_DMA1_IRQ (EPIC_IRQ_BASE + 2 + NUM_8259_INTERRUPTS) |
53 | #else | 47 | #else |
54 | #define MPC10X_I2C_IRQ OCP_IRQ_NA | 48 | #define MPC10X_I2C_IRQ -1 |
55 | #define MPC10X_DMA0_IRQ OCP_IRQ_NA | 49 | #define MPC10X_DMA0_IRQ -1 |
56 | #define MPC10X_DMA1_IRQ OCP_IRQ_NA | 50 | #define MPC10X_DMA1_IRQ -1 |
57 | #endif | 51 | #endif |
58 | 52 | ||
59 | 53 | static struct fsl_i2c_platform_data mpc10x_i2c_pdata = { | |
60 | struct ocp_def core_ocp[] = { | 54 | .device_flags = 0, |
61 | { .vendor = OCP_VENDOR_INVALID | ||
62 | } | ||
63 | }; | 55 | }; |
64 | 56 | ||
65 | static struct ocp_fs_i2c_data mpc10x_i2c_data = { | 57 | static struct plat_serial8250_port serial_platform_data[] = { |
66 | .flags = 0 | 58 | { }, |
67 | }; | 59 | }; |
68 | static struct ocp_def mpc10x_i2c_ocp = { | 60 | |
69 | .vendor = OCP_VENDOR_MOTOROLA, | 61 | struct platform_device ppc_sys_platform_devices[] = { |
70 | .function = OCP_FUNC_IIC, | 62 | [MPC10X_IIC1] = { |
71 | .index = 0, | 63 | .name = "fsl-i2c", |
72 | .additions = &mpc10x_i2c_data | 64 | .id = 1, |
65 | .dev.platform_data = &mpc10x_i2c_pdata, | ||
66 | .num_resources = 2, | ||
67 | .resource = (struct resource[]) { | ||
68 | { | ||
69 | .start = MPC10X_EUMB_I2C_OFFSET, | ||
70 | .end = MPC10X_EUMB_I2C_OFFSET + | ||
71 | MPC10X_EUMB_I2C_SIZE - 1, | ||
72 | .flags = IORESOURCE_MEM, | ||
73 | }, | ||
74 | { | ||
75 | .flags = IORESOURCE_IRQ | ||
76 | }, | ||
77 | }, | ||
78 | }, | ||
79 | [MPC10X_DMA0] = { | ||
80 | .name = "fsl-dma", | ||
81 | .id = 0, | ||
82 | .num_resources = 2, | ||
83 | .resource = (struct resource[]) { | ||
84 | { | ||
85 | .start = MPC10X_EUMB_DMA_OFFSET + 0x10, | ||
86 | .end = MPC10X_EUMB_DMA_OFFSET + 0x1f, | ||
87 | .flags = IORESOURCE_MEM, | ||
88 | }, | ||
89 | { | ||
90 | .flags = IORESOURCE_IRQ, | ||
91 | }, | ||
92 | }, | ||
93 | }, | ||
94 | [MPC10X_DMA1] = { | ||
95 | .name = "fsl-dma", | ||
96 | .id = 1, | ||
97 | .num_resources = 2, | ||
98 | .resource = (struct resource[]) { | ||
99 | { | ||
100 | .start = MPC10X_EUMB_DMA_OFFSET + 0x20, | ||
101 | .end = MPC10X_EUMB_DMA_OFFSET + 0x2f, | ||
102 | .flags = IORESOURCE_MEM, | ||
103 | }, | ||
104 | { | ||
105 | .flags = IORESOURCE_IRQ, | ||
106 | }, | ||
107 | }, | ||
108 | }, | ||
109 | [MPC10X_DMA1] = { | ||
110 | .name = "fsl-dma", | ||
111 | .id = 1, | ||
112 | .num_resources = 2, | ||
113 | .resource = (struct resource[]) { | ||
114 | { | ||
115 | .start = MPC10X_EUMB_DMA_OFFSET + 0x20, | ||
116 | .end = MPC10X_EUMB_DMA_OFFSET + 0x2f, | ||
117 | .flags = IORESOURCE_MEM, | ||
118 | }, | ||
119 | { | ||
120 | .flags = IORESOURCE_IRQ, | ||
121 | }, | ||
122 | }, | ||
123 | }, | ||
124 | [MPC10X_DUART] = { | ||
125 | .name = "serial8250", | ||
126 | .id = 0, | ||
127 | .dev.platform_data = serial_platform_data, | ||
128 | }, | ||
73 | }; | 129 | }; |
74 | 130 | ||
75 | static struct ocp_def mpc10x_dma_ocp[2] = { | 131 | /* We use the PCI ID to match on */ |
76 | { .vendor = OCP_VENDOR_MOTOROLA, | 132 | struct ppc_sys_spec *cur_ppc_sys_spec; |
77 | .function = OCP_FUNC_DMA, | 133 | struct ppc_sys_spec ppc_sys_specs[] = { |
78 | .index = 0 }, | 134 | { |
79 | { .vendor = OCP_VENDOR_MOTOROLA, | 135 | .ppc_sys_name = "8245", |
80 | .function = OCP_FUNC_DMA, | 136 | .mask = 0xFFFFFFFF, |
81 | .index = 1 } | 137 | .value = MPC10X_BRIDGE_8245, |
138 | .num_devices = 4, | ||
139 | .device_list = (enum ppc_sys_devices[]) | ||
140 | { | ||
141 | MPC10X_IIC1, MPC10X_DMA0, MPC10X_DMA1, MPC10X_DUART, | ||
142 | }, | ||
143 | }, | ||
144 | { | ||
145 | .ppc_sys_name = "8240", | ||
146 | .mask = 0xFFFFFFFF, | ||
147 | .value = MPC10X_BRIDGE_8240, | ||
148 | .num_devices = 3, | ||
149 | .device_list = (enum ppc_sys_devices[]) | ||
150 | { | ||
151 | MPC10X_IIC1, MPC10X_DMA0, MPC10X_DMA1, | ||
152 | }, | ||
153 | }, | ||
154 | { | ||
155 | .ppc_sys_name = "107", | ||
156 | .mask = 0xFFFFFFFF, | ||
157 | .value = MPC10X_BRIDGE_107, | ||
158 | .num_devices = 3, | ||
159 | .device_list = (enum ppc_sys_devices[]) | ||
160 | { | ||
161 | MPC10X_IIC1, MPC10X_DMA0, MPC10X_DMA1, | ||
162 | }, | ||
163 | }, | ||
164 | { /* default match */ | ||
165 | .ppc_sys_name = "", | ||
166 | .mask = 0x00000000, | ||
167 | .value = 0x00000000, | ||
168 | }, | ||
82 | }; | 169 | }; |
83 | 170 | ||
84 | /* Set resources to match bridge memory map */ | 171 | /* Set resources to match bridge memory map */ |
@@ -132,7 +219,7 @@ mpc10x_bridge_init(struct pci_controller *hose, | |||
132 | uint new_map, | 219 | uint new_map, |
133 | uint phys_eumb_base) | 220 | uint phys_eumb_base) |
134 | { | 221 | { |
135 | int host_bridge, picr1, picr1_bit; | 222 | int host_bridge, picr1, picr1_bit, i; |
136 | ulong pci_config_addr, pci_config_data; | 223 | ulong pci_config_addr, pci_config_data; |
137 | u_char pir, byte; | 224 | u_char pir, byte; |
138 | 225 | ||
@@ -273,7 +360,7 @@ mpc10x_bridge_init(struct pci_controller *hose, | |||
273 | printk("Host bridge in Agent mode\n"); | 360 | printk("Host bridge in Agent mode\n"); |
274 | /* Read or Set LMBAR & PCSRBAR? */ | 361 | /* Read or Set LMBAR & PCSRBAR? */ |
275 | } | 362 | } |
276 | 363 | ||
277 | /* Set base addr of the 8240/107 EUMB. */ | 364 | /* Set base addr of the 8240/107 EUMB. */ |
278 | early_write_config_dword(hose, | 365 | early_write_config_dword(hose, |
279 | 0, | 366 | 0, |
@@ -287,17 +374,6 @@ mpc10x_bridge_init(struct pci_controller *hose, | |||
287 | ioremap(phys_eumb_base + MPC10X_EUMB_EPIC_OFFSET, | 374 | ioremap(phys_eumb_base + MPC10X_EUMB_EPIC_OFFSET, |
288 | MPC10X_EUMB_EPIC_SIZE); | 375 | MPC10X_EUMB_EPIC_SIZE); |
289 | #endif | 376 | #endif |
290 | mpc10x_i2c_ocp.paddr = phys_eumb_base + MPC10X_EUMB_I2C_OFFSET; | ||
291 | mpc10x_i2c_ocp.irq = MPC10X_I2C_IRQ; | ||
292 | ocp_add_one_device(&mpc10x_i2c_ocp); | ||
293 | mpc10x_dma_ocp[0].paddr = phys_eumb_base + | ||
294 | MPC10X_EUMB_DMA_OFFSET + 0x100; | ||
295 | mpc10x_dma_ocp[0].irq = MPC10X_DMA0_IRQ; | ||
296 | ocp_add_one_device(&mpc10x_dma_ocp[0]); | ||
297 | mpc10x_dma_ocp[1].paddr = phys_eumb_base + | ||
298 | MPC10X_EUMB_DMA_OFFSET + 0x200; | ||
299 | mpc10x_dma_ocp[1].irq = MPC10X_DMA1_IRQ; | ||
300 | ocp_add_one_device(&mpc10x_dma_ocp[1]); | ||
301 | } | 377 | } |
302 | 378 | ||
303 | #ifdef CONFIG_MPC10X_STORE_GATHERING | 379 | #ifdef CONFIG_MPC10X_STORE_GATHERING |
@@ -306,6 +382,23 @@ mpc10x_bridge_init(struct pci_controller *hose, | |||
306 | mpc10x_disable_store_gathering(hose); | 382 | mpc10x_disable_store_gathering(hose); |
307 | #endif | 383 | #endif |
308 | 384 | ||
385 | /* setup platform devices for MPC10x bridges */ | ||
386 | identify_ppc_sys_by_id (host_bridge); | ||
387 | |||
388 | for (i = 0; i < cur_ppc_sys_spec->num_devices; i++) { | ||
389 | unsigned int dev_id = cur_ppc_sys_spec->device_list[i]; | ||
390 | ppc_sys_fixup_mem_resource(&ppc_sys_platform_devices[dev_id], | ||
391 | phys_eumb_base); | ||
392 | } | ||
393 | |||
394 | /* IRQ's are determined at runtime */ | ||
395 | ppc_sys_platform_devices[MPC10X_IIC1].resource[1].start = MPC10X_I2C_IRQ; | ||
396 | ppc_sys_platform_devices[MPC10X_IIC1].resource[1].end = MPC10X_I2C_IRQ; | ||
397 | ppc_sys_platform_devices[MPC10X_DMA0].resource[1].start = MPC10X_DMA0_IRQ; | ||
398 | ppc_sys_platform_devices[MPC10X_DMA0].resource[1].end = MPC10X_DMA0_IRQ; | ||
399 | ppc_sys_platform_devices[MPC10X_DMA1].resource[1].start = MPC10X_DMA1_IRQ; | ||
400 | ppc_sys_platform_devices[MPC10X_DMA1].resource[1].end = MPC10X_DMA1_IRQ; | ||
401 | |||
309 | /* | 402 | /* |
310 | * 8240 erratum 26, 8241/8245 erratum 29, 107 erratum 23: speculative | 403 | * 8240 erratum 26, 8241/8245 erratum 29, 107 erratum 23: speculative |
311 | * PCI reads may return stale data so turn off. | 404 | * PCI reads may return stale data so turn off. |
@@ -330,7 +423,7 @@ mpc10x_bridge_init(struct pci_controller *hose, | |||
330 | * 8245 (Rev 2., dated 10/2003) says PICR2[0] is reserverd. | 423 | * 8245 (Rev 2., dated 10/2003) says PICR2[0] is reserverd. |
331 | */ | 424 | */ |
332 | if (host_bridge == MPC10X_BRIDGE_8245) { | 425 | if (host_bridge == MPC10X_BRIDGE_8245) { |
333 | ulong picr2; | 426 | u32 picr2; |
334 | 427 | ||
335 | early_read_config_dword(hose, 0, PCI_DEVFN(0,0), | 428 | early_read_config_dword(hose, 0, PCI_DEVFN(0,0), |
336 | MPC10X_CFG_PICR2_REG, &picr2); | 429 | MPC10X_CFG_PICR2_REG, &picr2); |