diff options
Diffstat (limited to 'arch/mips/bcm47xx')
-rw-r--r-- | arch/mips/bcm47xx/Kconfig | 31 | ||||
-rw-r--r-- | arch/mips/bcm47xx/Makefile | 3 | ||||
-rw-r--r-- | arch/mips/bcm47xx/gpio.c | 83 | ||||
-rw-r--r-- | arch/mips/bcm47xx/irq.c | 12 | ||||
-rw-r--r-- | arch/mips/bcm47xx/nvram.c | 29 | ||||
-rw-r--r-- | arch/mips/bcm47xx/serial.c | 46 | ||||
-rw-r--r-- | arch/mips/bcm47xx/setup.c | 91 | ||||
-rw-r--r-- | arch/mips/bcm47xx/time.c | 16 | ||||
-rw-r--r-- | arch/mips/bcm47xx/wgt634u.c | 14 |
9 files changed, 283 insertions, 42 deletions
diff --git a/arch/mips/bcm47xx/Kconfig b/arch/mips/bcm47xx/Kconfig new file mode 100644 index 000000000000..6210b8d84109 --- /dev/null +++ b/arch/mips/bcm47xx/Kconfig | |||
@@ -0,0 +1,31 @@ | |||
1 | if BCM47XX | ||
2 | |||
3 | config BCM47XX_SSB | ||
4 | bool "SSB Support for Broadcom BCM47XX" | ||
5 | select SYS_HAS_CPU_MIPS32_R1 | ||
6 | select SSB | ||
7 | select SSB_DRIVER_MIPS | ||
8 | select SSB_DRIVER_EXTIF | ||
9 | select SSB_EMBEDDED | ||
10 | select SSB_B43_PCI_BRIDGE if PCI | ||
11 | select SSB_PCICORE_HOSTMODE if PCI | ||
12 | default y | ||
13 | help | ||
14 | Add support for old Broadcom BCM47xx boards with Sonics Silicon Backplane support. | ||
15 | |||
16 | This will generate an image with support for SSB and MIPS32 R1 instruction set. | ||
17 | |||
18 | config BCM47XX_BCMA | ||
19 | bool "BCMA Support for Broadcom BCM47XX" | ||
20 | select SYS_HAS_CPU_MIPS32_R2 | ||
21 | select BCMA | ||
22 | select BCMA_HOST_SOC | ||
23 | select BCMA_DRIVER_MIPS | ||
24 | select BCMA_DRIVER_PCI_HOSTMODE if PCI | ||
25 | default y | ||
26 | help | ||
27 | Add support for new Broadcom BCM47xx boards with Broadcom specific Advanced Microcontroller Bus. | ||
28 | |||
29 | This will generate an image with support for BCMA and MIPS32 R2 instruction set. | ||
30 | |||
31 | endif | ||
diff --git a/arch/mips/bcm47xx/Makefile b/arch/mips/bcm47xx/Makefile index 7465e8a72d9a..4add17349ff9 100644 --- a/arch/mips/bcm47xx/Makefile +++ b/arch/mips/bcm47xx/Makefile | |||
@@ -3,4 +3,5 @@ | |||
3 | # under Linux. | 3 | # under Linux. |
4 | # | 4 | # |
5 | 5 | ||
6 | obj-y := gpio.o irq.o nvram.o prom.o serial.o setup.o time.o wgt634u.o | 6 | obj-y += gpio.o irq.o nvram.o prom.o serial.o setup.o time.o |
7 | obj-$(CONFIG_BCM47XX_SSB) += wgt634u.o | ||
diff --git a/arch/mips/bcm47xx/gpio.c b/arch/mips/bcm47xx/gpio.c index e4a5ee9c9721..5ebdf62e96bb 100644 --- a/arch/mips/bcm47xx/gpio.c +++ b/arch/mips/bcm47xx/gpio.c | |||
@@ -6,6 +6,7 @@ | |||
6 | * Copyright (C) 2007 Aurelien Jarno <aurelien@aurel32.net> | 6 | * Copyright (C) 2007 Aurelien Jarno <aurelien@aurel32.net> |
7 | */ | 7 | */ |
8 | 8 | ||
9 | #include <linux/export.h> | ||
9 | #include <linux/ssb/ssb.h> | 10 | #include <linux/ssb/ssb.h> |
10 | #include <linux/ssb/ssb_driver_chipcommon.h> | 11 | #include <linux/ssb/ssb_driver_chipcommon.h> |
11 | #include <linux/ssb/ssb_driver_extif.h> | 12 | #include <linux/ssb/ssb_driver_extif.h> |
@@ -20,42 +21,82 @@ static DECLARE_BITMAP(gpio_in_use, BCM47XX_EXTIF_GPIO_LINES); | |||
20 | 21 | ||
21 | int gpio_request(unsigned gpio, const char *tag) | 22 | int gpio_request(unsigned gpio, const char *tag) |
22 | { | 23 | { |
23 | if (ssb_chipco_available(&ssb_bcm47xx.chipco) && | 24 | switch (bcm47xx_bus_type) { |
24 | ((unsigned)gpio >= BCM47XX_CHIPCO_GPIO_LINES)) | 25 | #ifdef CONFIG_BCM47XX_SSB |
25 | return -EINVAL; | 26 | case BCM47XX_BUS_TYPE_SSB: |
27 | if (ssb_chipco_available(&bcm47xx_bus.ssb.chipco) && | ||
28 | ((unsigned)gpio >= BCM47XX_CHIPCO_GPIO_LINES)) | ||
29 | return -EINVAL; | ||
26 | 30 | ||
27 | if (ssb_extif_available(&ssb_bcm47xx.extif) && | 31 | if (ssb_extif_available(&bcm47xx_bus.ssb.extif) && |
28 | ((unsigned)gpio >= BCM47XX_EXTIF_GPIO_LINES)) | 32 | ((unsigned)gpio >= BCM47XX_EXTIF_GPIO_LINES)) |
29 | return -EINVAL; | 33 | return -EINVAL; |
30 | 34 | ||
31 | if (test_and_set_bit(gpio, gpio_in_use)) | 35 | if (test_and_set_bit(gpio, gpio_in_use)) |
32 | return -EBUSY; | 36 | return -EBUSY; |
33 | 37 | ||
34 | return 0; | 38 | return 0; |
39 | #endif | ||
40 | #ifdef CONFIG_BCM47XX_BCMA | ||
41 | case BCM47XX_BUS_TYPE_BCMA: | ||
42 | if (gpio >= BCM47XX_CHIPCO_GPIO_LINES) | ||
43 | return -EINVAL; | ||
44 | |||
45 | if (test_and_set_bit(gpio, gpio_in_use)) | ||
46 | return -EBUSY; | ||
47 | |||
48 | return 0; | ||
49 | #endif | ||
50 | } | ||
51 | return -EINVAL; | ||
35 | } | 52 | } |
36 | EXPORT_SYMBOL(gpio_request); | 53 | EXPORT_SYMBOL(gpio_request); |
37 | 54 | ||
38 | void gpio_free(unsigned gpio) | 55 | void gpio_free(unsigned gpio) |
39 | { | 56 | { |
40 | if (ssb_chipco_available(&ssb_bcm47xx.chipco) && | 57 | switch (bcm47xx_bus_type) { |
41 | ((unsigned)gpio >= BCM47XX_CHIPCO_GPIO_LINES)) | 58 | #ifdef CONFIG_BCM47XX_SSB |
42 | return; | 59 | case BCM47XX_BUS_TYPE_SSB: |
60 | if (ssb_chipco_available(&bcm47xx_bus.ssb.chipco) && | ||
61 | ((unsigned)gpio >= BCM47XX_CHIPCO_GPIO_LINES)) | ||
62 | return; | ||
63 | |||
64 | if (ssb_extif_available(&bcm47xx_bus.ssb.extif) && | ||
65 | ((unsigned)gpio >= BCM47XX_EXTIF_GPIO_LINES)) | ||
66 | return; | ||
43 | 67 | ||
44 | if (ssb_extif_available(&ssb_bcm47xx.extif) && | 68 | clear_bit(gpio, gpio_in_use); |
45 | ((unsigned)gpio >= BCM47XX_EXTIF_GPIO_LINES)) | ||
46 | return; | 69 | return; |
70 | #endif | ||
71 | #ifdef CONFIG_BCM47XX_BCMA | ||
72 | case BCM47XX_BUS_TYPE_BCMA: | ||
73 | if (gpio >= BCM47XX_CHIPCO_GPIO_LINES) | ||
74 | return; | ||
47 | 75 | ||
48 | clear_bit(gpio, gpio_in_use); | 76 | clear_bit(gpio, gpio_in_use); |
77 | return; | ||
78 | #endif | ||
79 | } | ||
49 | } | 80 | } |
50 | EXPORT_SYMBOL(gpio_free); | 81 | EXPORT_SYMBOL(gpio_free); |
51 | 82 | ||
52 | int gpio_to_irq(unsigned gpio) | 83 | int gpio_to_irq(unsigned gpio) |
53 | { | 84 | { |
54 | if (ssb_chipco_available(&ssb_bcm47xx.chipco)) | 85 | switch (bcm47xx_bus_type) { |
55 | return ssb_mips_irq(ssb_bcm47xx.chipco.dev) + 2; | 86 | #ifdef CONFIG_BCM47XX_SSB |
56 | else if (ssb_extif_available(&ssb_bcm47xx.extif)) | 87 | case BCM47XX_BUS_TYPE_SSB: |
57 | return ssb_mips_irq(ssb_bcm47xx.extif.dev) + 2; | 88 | if (ssb_chipco_available(&bcm47xx_bus.ssb.chipco)) |
58 | else | 89 | return ssb_mips_irq(bcm47xx_bus.ssb.chipco.dev) + 2; |
59 | return -EINVAL; | 90 | else if (ssb_extif_available(&bcm47xx_bus.ssb.extif)) |
91 | return ssb_mips_irq(bcm47xx_bus.ssb.extif.dev) + 2; | ||
92 | else | ||
93 | return -EINVAL; | ||
94 | #endif | ||
95 | #ifdef CONFIG_BCM47XX_BCMA | ||
96 | case BCM47XX_BUS_TYPE_BCMA: | ||
97 | return bcma_core_mips_irq(bcm47xx_bus.bcma.bus.drv_cc.core) + 2; | ||
98 | #endif | ||
99 | } | ||
100 | return -EINVAL; | ||
60 | } | 101 | } |
61 | EXPORT_SYMBOL_GPL(gpio_to_irq); | 102 | EXPORT_SYMBOL_GPL(gpio_to_irq); |
diff --git a/arch/mips/bcm47xx/irq.c b/arch/mips/bcm47xx/irq.c index 325757acd020..8cf3833b2d29 100644 --- a/arch/mips/bcm47xx/irq.c +++ b/arch/mips/bcm47xx/irq.c | |||
@@ -26,6 +26,7 @@ | |||
26 | #include <linux/interrupt.h> | 26 | #include <linux/interrupt.h> |
27 | #include <linux/irq.h> | 27 | #include <linux/irq.h> |
28 | #include <asm/irq_cpu.h> | 28 | #include <asm/irq_cpu.h> |
29 | #include <bcm47xx.h> | ||
29 | 30 | ||
30 | void plat_irq_dispatch(void) | 31 | void plat_irq_dispatch(void) |
31 | { | 32 | { |
@@ -51,5 +52,16 @@ void plat_irq_dispatch(void) | |||
51 | 52 | ||
52 | void __init arch_init_irq(void) | 53 | void __init arch_init_irq(void) |
53 | { | 54 | { |
55 | #ifdef CONFIG_BCM47XX_BCMA | ||
56 | if (bcm47xx_bus_type == BCM47XX_BUS_TYPE_BCMA) { | ||
57 | bcma_write32(bcm47xx_bus.bcma.bus.drv_mips.core, | ||
58 | BCMA_MIPS_MIPS74K_INTMASK(5), 1 << 31); | ||
59 | /* | ||
60 | * the kernel reads the timer irq from some register and thinks | ||
61 | * it's #5, but we offset it by 2 and route to #7 | ||
62 | */ | ||
63 | cp0_compare_irq = 7; | ||
64 | } | ||
65 | #endif | ||
54 | mips_cpu_irq_init(); | 66 | mips_cpu_irq_init(); |
55 | } | 67 | } |
diff --git a/arch/mips/bcm47xx/nvram.c b/arch/mips/bcm47xx/nvram.c index 54db815bc86c..a84e3bb7387f 100644 --- a/arch/mips/bcm47xx/nvram.c +++ b/arch/mips/bcm47xx/nvram.c | |||
@@ -26,14 +26,35 @@ static char nvram_buf[NVRAM_SPACE]; | |||
26 | /* Probe for NVRAM header */ | 26 | /* Probe for NVRAM header */ |
27 | static void early_nvram_init(void) | 27 | static void early_nvram_init(void) |
28 | { | 28 | { |
29 | struct ssb_mipscore *mcore = &ssb_bcm47xx.mipscore; | 29 | #ifdef CONFIG_BCM47XX_SSB |
30 | struct ssb_mipscore *mcore_ssb; | ||
31 | #endif | ||
32 | #ifdef CONFIG_BCM47XX_BCMA | ||
33 | struct bcma_drv_cc *bcma_cc; | ||
34 | #endif | ||
30 | struct nvram_header *header; | 35 | struct nvram_header *header; |
31 | int i; | 36 | int i; |
32 | u32 base, lim, off; | 37 | u32 base = 0; |
38 | u32 lim = 0; | ||
39 | u32 off; | ||
33 | u32 *src, *dst; | 40 | u32 *src, *dst; |
34 | 41 | ||
35 | base = mcore->flash_window; | 42 | switch (bcm47xx_bus_type) { |
36 | lim = mcore->flash_window_size; | 43 | #ifdef CONFIG_BCM47XX_SSB |
44 | case BCM47XX_BUS_TYPE_SSB: | ||
45 | mcore_ssb = &bcm47xx_bus.ssb.mipscore; | ||
46 | base = mcore_ssb->flash_window; | ||
47 | lim = mcore_ssb->flash_window_size; | ||
48 | break; | ||
49 | #endif | ||
50 | #ifdef CONFIG_BCM47XX_BCMA | ||
51 | case BCM47XX_BUS_TYPE_BCMA: | ||
52 | bcma_cc = &bcm47xx_bus.bcma.bus.drv_cc; | ||
53 | base = bcma_cc->pflash.window; | ||
54 | lim = bcma_cc->pflash.window_size; | ||
55 | break; | ||
56 | #endif | ||
57 | } | ||
37 | 58 | ||
38 | off = FLASH_MIN; | 59 | off = FLASH_MIN; |
39 | while (off <= lim) { | 60 | while (off <= lim) { |
diff --git a/arch/mips/bcm47xx/serial.c b/arch/mips/bcm47xx/serial.c index 59c11afdb2ab..57981e4fe2bc 100644 --- a/arch/mips/bcm47xx/serial.c +++ b/arch/mips/bcm47xx/serial.c | |||
@@ -23,10 +23,11 @@ static struct platform_device uart8250_device = { | |||
23 | }, | 23 | }, |
24 | }; | 24 | }; |
25 | 25 | ||
26 | static int __init uart8250_init(void) | 26 | #ifdef CONFIG_BCM47XX_SSB |
27 | static int __init uart8250_init_ssb(void) | ||
27 | { | 28 | { |
28 | int i; | 29 | int i; |
29 | struct ssb_mipscore *mcore = &(ssb_bcm47xx.mipscore); | 30 | struct ssb_mipscore *mcore = &(bcm47xx_bus.ssb.mipscore); |
30 | 31 | ||
31 | memset(&uart8250_data, 0, sizeof(uart8250_data)); | 32 | memset(&uart8250_data, 0, sizeof(uart8250_data)); |
32 | 33 | ||
@@ -44,6 +45,47 @@ static int __init uart8250_init(void) | |||
44 | } | 45 | } |
45 | return platform_device_register(&uart8250_device); | 46 | return platform_device_register(&uart8250_device); |
46 | } | 47 | } |
48 | #endif | ||
49 | |||
50 | #ifdef CONFIG_BCM47XX_BCMA | ||
51 | static int __init uart8250_init_bcma(void) | ||
52 | { | ||
53 | int i; | ||
54 | struct bcma_drv_cc *cc = &(bcm47xx_bus.bcma.bus.drv_cc); | ||
55 | |||
56 | memset(&uart8250_data, 0, sizeof(uart8250_data)); | ||
57 | |||
58 | for (i = 0; i < cc->nr_serial_ports; i++) { | ||
59 | struct plat_serial8250_port *p = &(uart8250_data[i]); | ||
60 | struct bcma_serial_port *bcma_port; | ||
61 | bcma_port = &(cc->serial_ports[i]); | ||
62 | |||
63 | p->mapbase = (unsigned int) bcma_port->regs; | ||
64 | p->membase = (void *) bcma_port->regs; | ||
65 | p->irq = bcma_port->irq + 2; | ||
66 | p->uartclk = bcma_port->baud_base; | ||
67 | p->regshift = bcma_port->reg_shift; | ||
68 | p->iotype = UPIO_MEM; | ||
69 | p->flags = UPF_BOOT_AUTOCONF | UPF_SHARE_IRQ; | ||
70 | } | ||
71 | return platform_device_register(&uart8250_device); | ||
72 | } | ||
73 | #endif | ||
74 | |||
75 | static int __init uart8250_init(void) | ||
76 | { | ||
77 | switch (bcm47xx_bus_type) { | ||
78 | #ifdef CONFIG_BCM47XX_SSB | ||
79 | case BCM47XX_BUS_TYPE_SSB: | ||
80 | return uart8250_init_ssb(); | ||
81 | #endif | ||
82 | #ifdef CONFIG_BCM47XX_BCMA | ||
83 | case BCM47XX_BUS_TYPE_BCMA: | ||
84 | return uart8250_init_bcma(); | ||
85 | #endif | ||
86 | } | ||
87 | return -EINVAL; | ||
88 | } | ||
47 | 89 | ||
48 | module_init(uart8250_init); | 90 | module_init(uart8250_init); |
49 | 91 | ||
diff --git a/arch/mips/bcm47xx/setup.c b/arch/mips/bcm47xx/setup.c index cfae81571ded..1cfdda03546a 100644 --- a/arch/mips/bcm47xx/setup.c +++ b/arch/mips/bcm47xx/setup.c | |||
@@ -26,24 +26,40 @@ | |||
26 | * 675 Mass Ave, Cambridge, MA 02139, USA. | 26 | * 675 Mass Ave, Cambridge, MA 02139, USA. |
27 | */ | 27 | */ |
28 | 28 | ||
29 | #include <linux/export.h> | ||
29 | #include <linux/types.h> | 30 | #include <linux/types.h> |
30 | #include <linux/ssb/ssb.h> | 31 | #include <linux/ssb/ssb.h> |
31 | #include <linux/ssb/ssb_embedded.h> | 32 | #include <linux/ssb/ssb_embedded.h> |
33 | #include <linux/bcma/bcma_soc.h> | ||
32 | #include <asm/bootinfo.h> | 34 | #include <asm/bootinfo.h> |
33 | #include <asm/reboot.h> | 35 | #include <asm/reboot.h> |
34 | #include <asm/time.h> | 36 | #include <asm/time.h> |
35 | #include <bcm47xx.h> | 37 | #include <bcm47xx.h> |
36 | #include <asm/mach-bcm47xx/nvram.h> | 38 | #include <asm/mach-bcm47xx/nvram.h> |
37 | 39 | ||
38 | struct ssb_bus ssb_bcm47xx; | 40 | union bcm47xx_bus bcm47xx_bus; |
39 | EXPORT_SYMBOL(ssb_bcm47xx); | 41 | EXPORT_SYMBOL(bcm47xx_bus); |
42 | |||
43 | enum bcm47xx_bus_type bcm47xx_bus_type; | ||
44 | EXPORT_SYMBOL(bcm47xx_bus_type); | ||
40 | 45 | ||
41 | static void bcm47xx_machine_restart(char *command) | 46 | static void bcm47xx_machine_restart(char *command) |
42 | { | 47 | { |
43 | printk(KERN_ALERT "Please stand by while rebooting the system...\n"); | 48 | printk(KERN_ALERT "Please stand by while rebooting the system...\n"); |
44 | local_irq_disable(); | 49 | local_irq_disable(); |
45 | /* Set the watchdog timer to reset immediately */ | 50 | /* Set the watchdog timer to reset immediately */ |
46 | ssb_watchdog_timer_set(&ssb_bcm47xx, 1); | 51 | switch (bcm47xx_bus_type) { |
52 | #ifdef CONFIG_BCM47XX_SSB | ||
53 | case BCM47XX_BUS_TYPE_SSB: | ||
54 | ssb_watchdog_timer_set(&bcm47xx_bus.ssb, 1); | ||
55 | break; | ||
56 | #endif | ||
57 | #ifdef CONFIG_BCM47XX_BCMA | ||
58 | case BCM47XX_BUS_TYPE_BCMA: | ||
59 | bcma_chipco_watchdog_timer_set(&bcm47xx_bus.bcma.bus.drv_cc, 1); | ||
60 | break; | ||
61 | #endif | ||
62 | } | ||
47 | while (1) | 63 | while (1) |
48 | cpu_relax(); | 64 | cpu_relax(); |
49 | } | 65 | } |
@@ -52,11 +68,23 @@ static void bcm47xx_machine_halt(void) | |||
52 | { | 68 | { |
53 | /* Disable interrupts and watchdog and spin forever */ | 69 | /* Disable interrupts and watchdog and spin forever */ |
54 | local_irq_disable(); | 70 | local_irq_disable(); |
55 | ssb_watchdog_timer_set(&ssb_bcm47xx, 0); | 71 | switch (bcm47xx_bus_type) { |
72 | #ifdef CONFIG_BCM47XX_SSB | ||
73 | case BCM47XX_BUS_TYPE_SSB: | ||
74 | ssb_watchdog_timer_set(&bcm47xx_bus.ssb, 0); | ||
75 | break; | ||
76 | #endif | ||
77 | #ifdef CONFIG_BCM47XX_BCMA | ||
78 | case BCM47XX_BUS_TYPE_BCMA: | ||
79 | bcma_chipco_watchdog_timer_set(&bcm47xx_bus.bcma.bus.drv_cc, 0); | ||
80 | break; | ||
81 | #endif | ||
82 | } | ||
56 | while (1) | 83 | while (1) |
57 | cpu_relax(); | 84 | cpu_relax(); |
58 | } | 85 | } |
59 | 86 | ||
87 | #ifdef CONFIG_BCM47XX_SSB | ||
60 | #define READ_FROM_NVRAM(_outvar, name, buf) \ | 88 | #define READ_FROM_NVRAM(_outvar, name, buf) \ |
61 | if (nvram_getprefix(prefix, name, buf, sizeof(buf)) >= 0)\ | 89 | if (nvram_getprefix(prefix, name, buf, sizeof(buf)) >= 0)\ |
62 | sprom->_outvar = simple_strtoul(buf, NULL, 0); | 90 | sprom->_outvar = simple_strtoul(buf, NULL, 0); |
@@ -247,7 +275,7 @@ static int bcm47xx_get_invariants(struct ssb_bus *bus, | |||
247 | return 0; | 275 | return 0; |
248 | } | 276 | } |
249 | 277 | ||
250 | void __init plat_mem_setup(void) | 278 | static void __init bcm47xx_register_ssb(void) |
251 | { | 279 | { |
252 | int err; | 280 | int err; |
253 | char buf[100]; | 281 | char buf[100]; |
@@ -258,12 +286,12 @@ void __init plat_mem_setup(void) | |||
258 | printk(KERN_WARNING "bcm47xx: someone else already registered" | 286 | printk(KERN_WARNING "bcm47xx: someone else already registered" |
259 | " a ssb SPROM callback handler (err %d)\n", err); | 287 | " a ssb SPROM callback handler (err %d)\n", err); |
260 | 288 | ||
261 | err = ssb_bus_ssbbus_register(&ssb_bcm47xx, SSB_ENUM_BASE, | 289 | err = ssb_bus_ssbbus_register(&(bcm47xx_bus.ssb), SSB_ENUM_BASE, |
262 | bcm47xx_get_invariants); | 290 | bcm47xx_get_invariants); |
263 | if (err) | 291 | if (err) |
264 | panic("Failed to initialize SSB bus (err %d)\n", err); | 292 | panic("Failed to initialize SSB bus (err %d)\n", err); |
265 | 293 | ||
266 | mcore = &ssb_bcm47xx.mipscore; | 294 | mcore = &bcm47xx_bus.ssb.mipscore; |
267 | if (nvram_getenv("kernel_args", buf, sizeof(buf)) >= 0) { | 295 | if (nvram_getenv("kernel_args", buf, sizeof(buf)) >= 0) { |
268 | if (strstr(buf, "console=ttyS1")) { | 296 | if (strstr(buf, "console=ttyS1")) { |
269 | struct ssb_serial_port port; | 297 | struct ssb_serial_port port; |
@@ -276,8 +304,57 @@ void __init plat_mem_setup(void) | |||
276 | memcpy(&mcore->serial_ports[1], &port, sizeof(port)); | 304 | memcpy(&mcore->serial_ports[1], &port, sizeof(port)); |
277 | } | 305 | } |
278 | } | 306 | } |
307 | } | ||
308 | #endif | ||
309 | |||
310 | #ifdef CONFIG_BCM47XX_BCMA | ||
311 | static void __init bcm47xx_register_bcma(void) | ||
312 | { | ||
313 | int err; | ||
314 | |||
315 | err = bcma_host_soc_register(&bcm47xx_bus.bcma); | ||
316 | if (err) | ||
317 | panic("Failed to initialize BCMA bus (err %d)\n", err); | ||
318 | } | ||
319 | #endif | ||
320 | |||
321 | void __init plat_mem_setup(void) | ||
322 | { | ||
323 | struct cpuinfo_mips *c = ¤t_cpu_data; | ||
324 | |||
325 | if (c->cputype == CPU_74K) { | ||
326 | printk(KERN_INFO "bcm47xx: using bcma bus\n"); | ||
327 | #ifdef CONFIG_BCM47XX_BCMA | ||
328 | bcm47xx_bus_type = BCM47XX_BUS_TYPE_BCMA; | ||
329 | bcm47xx_register_bcma(); | ||
330 | #endif | ||
331 | } else { | ||
332 | printk(KERN_INFO "bcm47xx: using ssb bus\n"); | ||
333 | #ifdef CONFIG_BCM47XX_SSB | ||
334 | bcm47xx_bus_type = BCM47XX_BUS_TYPE_SSB; | ||
335 | bcm47xx_register_ssb(); | ||
336 | #endif | ||
337 | } | ||
279 | 338 | ||
280 | _machine_restart = bcm47xx_machine_restart; | 339 | _machine_restart = bcm47xx_machine_restart; |
281 | _machine_halt = bcm47xx_machine_halt; | 340 | _machine_halt = bcm47xx_machine_halt; |
282 | pm_power_off = bcm47xx_machine_halt; | 341 | pm_power_off = bcm47xx_machine_halt; |
283 | } | 342 | } |
343 | |||
344 | static int __init bcm47xx_register_bus_complete(void) | ||
345 | { | ||
346 | switch (bcm47xx_bus_type) { | ||
347 | #ifdef CONFIG_BCM47XX_SSB | ||
348 | case BCM47XX_BUS_TYPE_SSB: | ||
349 | /* Nothing to do */ | ||
350 | break; | ||
351 | #endif | ||
352 | #ifdef CONFIG_BCM47XX_BCMA | ||
353 | case BCM47XX_BUS_TYPE_BCMA: | ||
354 | bcma_bus_register(&bcm47xx_bus.bcma.bus); | ||
355 | break; | ||
356 | #endif | ||
357 | } | ||
358 | return 0; | ||
359 | } | ||
360 | device_initcall(bcm47xx_register_bus_complete); | ||
diff --git a/arch/mips/bcm47xx/time.c b/arch/mips/bcm47xx/time.c index 0c6f47b3fd94..536374dcba78 100644 --- a/arch/mips/bcm47xx/time.c +++ b/arch/mips/bcm47xx/time.c | |||
@@ -30,7 +30,7 @@ | |||
30 | 30 | ||
31 | void __init plat_time_init(void) | 31 | void __init plat_time_init(void) |
32 | { | 32 | { |
33 | unsigned long hz; | 33 | unsigned long hz = 0; |
34 | 34 | ||
35 | /* | 35 | /* |
36 | * Use deterministic values for initial counter interrupt | 36 | * Use deterministic values for initial counter interrupt |
@@ -39,7 +39,19 @@ void __init plat_time_init(void) | |||
39 | write_c0_count(0); | 39 | write_c0_count(0); |
40 | write_c0_compare(0xffff); | 40 | write_c0_compare(0xffff); |
41 | 41 | ||
42 | hz = ssb_cpu_clock(&ssb_bcm47xx.mipscore) / 2; | 42 | switch (bcm47xx_bus_type) { |
43 | #ifdef CONFIG_BCM47XX_SSB | ||
44 | case BCM47XX_BUS_TYPE_SSB: | ||
45 | hz = ssb_cpu_clock(&bcm47xx_bus.ssb.mipscore) / 2; | ||
46 | break; | ||
47 | #endif | ||
48 | #ifdef CONFIG_BCM47XX_BCMA | ||
49 | case BCM47XX_BUS_TYPE_BCMA: | ||
50 | hz = bcma_cpu_clock(&bcm47xx_bus.bcma.bus.drv_mips) / 2; | ||
51 | break; | ||
52 | #endif | ||
53 | } | ||
54 | |||
43 | if (!hz) | 55 | if (!hz) |
44 | hz = 100000000; | 56 | hz = 100000000; |
45 | 57 | ||
diff --git a/arch/mips/bcm47xx/wgt634u.c b/arch/mips/bcm47xx/wgt634u.c index 74d06965326f..e9f9ec8d443b 100644 --- a/arch/mips/bcm47xx/wgt634u.c +++ b/arch/mips/bcm47xx/wgt634u.c | |||
@@ -108,7 +108,7 @@ static irqreturn_t gpio_interrupt(int irq, void *ignored) | |||
108 | 108 | ||
109 | /* Interrupts are shared, check if the current one is | 109 | /* Interrupts are shared, check if the current one is |
110 | a GPIO interrupt. */ | 110 | a GPIO interrupt. */ |
111 | if (!ssb_chipco_irq_status(&ssb_bcm47xx.chipco, | 111 | if (!ssb_chipco_irq_status(&bcm47xx_bus.ssb.chipco, |
112 | SSB_CHIPCO_IRQ_GPIO)) | 112 | SSB_CHIPCO_IRQ_GPIO)) |
113 | return IRQ_NONE; | 113 | return IRQ_NONE; |
114 | 114 | ||
@@ -132,22 +132,26 @@ static int __init wgt634u_init(void) | |||
132 | * machine. Use the MAC address as an heuristic. Netgear Inc. has | 132 | * machine. Use the MAC address as an heuristic. Netgear Inc. has |
133 | * been allocated ranges 00:09:5b:xx:xx:xx and 00:0f:b5:xx:xx:xx. | 133 | * been allocated ranges 00:09:5b:xx:xx:xx and 00:0f:b5:xx:xx:xx. |
134 | */ | 134 | */ |
135 | u8 *et0mac; | ||
135 | 136 | ||
136 | u8 *et0mac = ssb_bcm47xx.sprom.et0mac; | 137 | if (bcm47xx_bus_type != BCM47XX_BUS_TYPE_SSB) |
138 | return -ENODEV; | ||
139 | |||
140 | et0mac = bcm47xx_bus.ssb.sprom.et0mac; | ||
137 | 141 | ||
138 | if (et0mac[0] == 0x00 && | 142 | if (et0mac[0] == 0x00 && |
139 | ((et0mac[1] == 0x09 && et0mac[2] == 0x5b) || | 143 | ((et0mac[1] == 0x09 && et0mac[2] == 0x5b) || |
140 | (et0mac[1] == 0x0f && et0mac[2] == 0xb5))) { | 144 | (et0mac[1] == 0x0f && et0mac[2] == 0xb5))) { |
141 | struct ssb_mipscore *mcore = &ssb_bcm47xx.mipscore; | 145 | struct ssb_mipscore *mcore = &bcm47xx_bus.ssb.mipscore; |
142 | 146 | ||
143 | printk(KERN_INFO "WGT634U machine detected.\n"); | 147 | printk(KERN_INFO "WGT634U machine detected.\n"); |
144 | 148 | ||
145 | if (!request_irq(gpio_to_irq(WGT634U_GPIO_RESET), | 149 | if (!request_irq(gpio_to_irq(WGT634U_GPIO_RESET), |
146 | gpio_interrupt, IRQF_SHARED, | 150 | gpio_interrupt, IRQF_SHARED, |
147 | "WGT634U GPIO", &ssb_bcm47xx.chipco)) { | 151 | "WGT634U GPIO", &bcm47xx_bus.ssb.chipco)) { |
148 | gpio_direction_input(WGT634U_GPIO_RESET); | 152 | gpio_direction_input(WGT634U_GPIO_RESET); |
149 | gpio_intmask(WGT634U_GPIO_RESET, 1); | 153 | gpio_intmask(WGT634U_GPIO_RESET, 1); |
150 | ssb_chipco_irq_mask(&ssb_bcm47xx.chipco, | 154 | ssb_chipco_irq_mask(&bcm47xx_bus.ssb.chipco, |
151 | SSB_CHIPCO_IRQ_GPIO, | 155 | SSB_CHIPCO_IRQ_GPIO, |
152 | SSB_CHIPCO_IRQ_GPIO); | 156 | SSB_CHIPCO_IRQ_GPIO); |
153 | } | 157 | } |