diff options
author | Gabor Juhos <juhosg@openwrt.org> | 2013-09-07 11:34:03 +0000 |
---|---|---|
committer | Gabor Juhos <juhosg@openwrt.org> | 2013-09-07 11:34:03 +0000 |
commit | 76017db3240e86fcf86112050c54379db596972a (patch) | |
tree | 41329494ad8288cd05bbc59d5a23b3922cd661a3 /target/linux/ppc40x/patches-3.10 | |
parent | 7f0189d4b0db4839ebc9520be0272078c7fbb0f1 (diff) | |
download | master-187ad058-76017db3240e86fcf86112050c54379db596972a.tar.gz master-187ad058-76017db3240e86fcf86112050c54379db596972a.tar.bz2 master-187ad058-76017db3240e86fcf86112050c54379db596972a.zip |
ppc40x: add support for 3.10
Signed-off-by: Gabor Juhos <juhosg@openwrt.org>
git-svn-id: svn://svn.openwrt.org/openwrt/trunk@37912 3c298f89-4303-0410-b956-a3cf2f4a3e73
Diffstat (limited to 'target/linux/ppc40x/patches-3.10')
7 files changed, 1809 insertions, 0 deletions
diff --git a/target/linux/ppc40x/patches-3.10/003-powerpc-add-EBC_BXCR-defines.patch b/target/linux/ppc40x/patches-3.10/003-powerpc-add-EBC_BXCR-defines.patch new file mode 100644 index 0000000000..660b8bcd49 --- /dev/null +++ b/target/linux/ppc40x/patches-3.10/003-powerpc-add-EBC_BXCR-defines.patch @@ -0,0 +1,27 @@ +--- a/arch/powerpc/boot/dcr.h ++++ b/arch/powerpc/boot/dcr.h +@@ -55,6 +55,14 @@ static const unsigned long sdram_bxcr[] + #define EBC_BXCR(n) (n) + #define EBC_BXCR_BAS 0xfff00000 + #define EBC_BXCR_BS 0x000e0000 ++#define EBC_BXCR_BS_1M 0x00000000 ++#define EBC_BXCR_BS_2M 0x00020000 ++#define EBC_BXCR_BS_4M 0x00040000 ++#define EBC_BXCR_BS_8M 0x00060000 ++#define EBC_BXCR_BS_16M 0x00080000 ++#define EBC_BXCR_BS_32M 0x000a0000 ++#define EBC_BXCR_BS_64M 0x000c0000 ++#define EBC_BXCR_BS_128M 0x000e0000 + #define EBC_BXCR_BANK_SIZE(reg) \ + (0x100000 << (((reg) & EBC_BXCR_BS) >> 17)) + #define EBC_BXCR_BU 0x00018000 +@@ -63,6 +71,9 @@ static const unsigned long sdram_bxcr[] + #define EBC_BXCR_BU_WO 0x00010000 + #define EBC_BXCR_BU_RW 0x00018000 + #define EBC_BXCR_BW 0x00006000 ++#define EBC_BXCR_BW_8 0x00000000 ++#define EBC_BXCR_BW_16 0x00002000 ++#define EBC_BXCR_BW_32 0x00006000 + #define EBC_B0AP 0x10 + #define EBC_B1AP 0x11 + #define EBC_B2AP 0x12 diff --git a/target/linux/ppc40x/patches-3.10/004-magicbox.patch b/target/linux/ppc40x/patches-3.10/004-magicbox.patch new file mode 100644 index 0000000000..284fec90ad --- /dev/null +++ b/target/linux/ppc40x/patches-3.10/004-magicbox.patch @@ -0,0 +1,446 @@ +--- /dev/null ++++ b/arch/powerpc/boot/cuboot-magicbox.c +@@ -0,0 +1,98 @@ ++/* ++ * Old U-boot compatibility for Magicbox boards ++ * ++ * Author: Imre Kaloz <kaloz@openwrt.org> ++ * Gabor Juhos <juhosg@openwrt.org> ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include "ops.h" ++#include "io.h" ++#include "dcr.h" ++#include "stdio.h" ++#include "4xx.h" ++#include "44x.h" ++#include "cuboot.h" ++ ++#define TARGET_4xx ++#define TARGET_405EP ++#include "ppcboot.h" ++ ++static bd_t bd; ++ ++static void fixup_perwe(void) ++{ ++ ++#define DCRN_CPC0_PCI_BASE 0xf9 ++ ++ /* Turn on PerWE instead of PCIINT */ ++ mtdcr(DCRN_CPC0_PCI_BASE, ++ mfdcr(DCRN_CPC0_PCI_BASE) | (0x80000000L >> 27)); ++ ++#undef DCRN_CPC0_PCI_BASE ++} ++ ++static void fixup_cf_card(void) ++{ ++ ++#define CF_CS0_BASE 0xff100000 ++#define CF_CS1_BASE 0xff200000 ++ ++ /* PerCS1 (CF's CS0): base 0xff100000, 16-bit, rw */ ++ mtdcr(DCRN_EBC0_CFGADDR, EBC_B1CR); ++ mtdcr(DCRN_EBC0_CFGDATA, CF_CS0_BASE | EBC_BXCR_BS_1M | ++ EBC_BXCR_BU_RW | EBC_BXCR_BW_16); ++ mtdcr(DCRN_EBC0_CFGADDR, EBC_B1AP); ++ mtdcr(DCRN_EBC0_CFGDATA, 0x080bd800); ++ ++ /* PerCS2 (CF's CS1): base 0xff200000, 16-bit, rw */ ++ mtdcr(DCRN_EBC0_CFGADDR, EBC_B2CR); ++ mtdcr(DCRN_EBC0_CFGDATA, CF_CS1_BASE | EBC_BXCR_BS_1M | ++ EBC_BXCR_BU_RW | EBC_BXCR_BW_16); ++ mtdcr(DCRN_EBC0_CFGADDR, EBC_B2AP); ++ mtdcr(DCRN_EBC0_CFGDATA, 0x080bd800); ++ ++#undef CF_CS0_BASE ++#undef CF_CS1_BASE ++} ++ ++static void magicbox_fixups(void) ++{ ++ ibm405ep_fixup_clocks(bd.bi_procfreq / 8); ++ ibm4xx_sdram_fixup_memsize(); ++ ++ /* Magicbox v1 has only one ethernet, one serial and no ++ * CF slot -- detect it using it's fake enet1addr ++ */ ++ if ((bd.bi_enet1addr[2] == 0x02) && ++ (bd.bi_enet1addr[3] == 0xfa) && ++ (bd.bi_enet1addr[4] == 0xf0) && ++ (bd.bi_enet1addr[5] == 0x80)) { ++ void *devp; ++ devp = finddevice("/plb/opb/ethernet@ef600900"); ++ del_node(devp); ++ devp = finddevice("/plb/opb/serial@ef600400"); ++ del_node(devp); ++ devp = finddevice("/plb/ebc/cf_card@ff100000"); ++ del_node(devp); ++ ++ } else { ++ fixup_perwe(); ++ fixup_cf_card(); ++ } ++ ++ dt_fixup_mac_addresses(&bd.bi_enetaddr, &bd.bi_enet1addr); ++} ++ ++void platform_init(unsigned long r3, unsigned long r4, unsigned long r5, ++ unsigned long r6, unsigned long r7) ++{ ++ CUBOOT_INIT(); ++ platform_ops.fixups = magicbox_fixups; ++ platform_ops.exit = ibm40x_dbcr_reset; ++ fdt_init(_dtb_start); ++ serial_console_init(); ++} +--- /dev/null ++++ b/arch/powerpc/boot/dts/magicbox.dts +@@ -0,0 +1,285 @@ ++/* ++ * Device Tree Source for Magicbox boards ++ * ++ * Copyright 2008-2009 Imre Kaloz <kaloz@openwrt.org> ++ * Copyright 2009 Gabor Juhos <juhosg@openwrt.org> ++ * ++ * Based on walnut.dts ++ * ++ * This file is licensed under the terms of the GNU General Public ++ * License version 2. This program is licensed "as is" without ++ * any warranty of any kind, whether express or implied. ++ */ ++ ++/dts-v1/; ++ ++/ { ++ #address-cells = <1>; ++ #size-cells = <1>; ++ model = "magicbox"; ++ compatible = "magicbox"; ++ dcr-parent = <&{/cpus/cpu@0}>; ++ ++ aliases { ++ ethernet0 = &EMAC0; ++ ethernet1 = &EMAC1; ++ serial0 = &UART0; ++ serial1 = &UART1; ++ }; ++ ++ cpus { ++ #address-cells = <1>; ++ #size-cells = <0>; ++ ++ cpu@0 { ++ device_type = "cpu"; ++ model = "PowerPC,405EP"; ++ reg = <0x00000000>; ++ clock-frequency = <0>; /* Filled in by zImage */ ++ timebase-frequency = <0>; /* Filled in by zImage */ ++ i-cache-line-size = <0x20>; ++ d-cache-line-size = <0x20>; ++ i-cache-size = <0x4000>; ++ d-cache-size = <0x4000>; ++ dcr-controller; ++ dcr-access-method = "native"; ++ }; ++ }; ++ ++ memory { ++ device_type = "memory"; ++ reg = <0x00000000 0x00000000>; /* Filled in by zImage */ ++ }; ++ ++ UIC0: interrupt-controller { ++ compatible = "ibm,uic"; ++ interrupt-controller; ++ cell-index = <0>; ++ dcr-reg = <0x0c0 0x009>; ++ #address-cells = <0>; ++ #size-cells = <0>; ++ #interrupt-cells = <2>; ++ }; ++ ++ plb { ++ compatible = "ibm,plb3"; ++ #address-cells = <1>; ++ #size-cells = <1>; ++ ranges; ++ clock-frequency = <0>; /* Filled in by zImage */ ++ ++ SDRAM0: memory-controller { ++ compatible = "ibm,sdram-405ep"; ++ dcr-reg = <0x010 0x002>; ++ }; ++ ++ MAL: mcmal { ++ compatible = "ibm,mcmal-405ep", "ibm,mcmal"; ++ dcr-reg = <0x180 0x062>; ++ num-tx-chans = <4>; ++ num-rx-chans = <2>; ++ interrupt-parent = <&UIC0>; ++ interrupts = < ++ 0xb 0x4 /* TXEOB */ ++ 0xc 0x4 /* RXEOB */ ++ 0xa 0x4 /* SERR */ ++ 0xd 0x4 /* TXDE */ ++ 0xe 0x4 /* RXDE */>; ++ }; ++ ++ POB0: opb { ++ compatible = "ibm,opb-405ep", "ibm,opb"; ++ #address-cells = <1>; ++ #size-cells = <1>; ++ ranges = <0xef600000 0xef600000 0x00a00000>; ++ dcr-reg = <0x0a0 0x005>; ++ clock-frequency = <0>; /* Filled in by zImage */ ++ ++ UART0: serial@ef600300 { ++ device_type = "serial"; ++ compatible = "ns16550"; ++ reg = <0xef600300 0x00000008>; ++ virtual-reg = <0xef600300>; ++ clock-frequency = <0>; /* Filled in by zImage */ ++ current-speed = <115200>; ++ interrupt-parent = <&UIC0>; ++ interrupts = <0x0 0x4>; ++ }; ++ ++ UART1: serial@ef600400 { ++ device_type = "serial"; ++ compatible = "ns16550"; ++ reg = <0xef600400 0x00000008>; ++ virtual-reg = <0xef600400>; ++ clock-frequency = <0>; /* Filled in by zImage */ ++ current-speed = <115200>; ++ interrupt-parent = <&UIC0>; ++ interrupts = <0x1 0x4>; ++ }; ++ ++ IIC: i2c@ef600500 { ++ compatible = "ibm,iic-405ep", "ibm,iic"; ++ #address-cells = <1>; ++ #size-cells = <0>; ++ reg = <0xef600500 0x00000011>; ++ interrupt-parent = <&UIC0>; ++ interrupts = <0x2 0x4>; ++ ++ dtt@48 { ++ compatible = "national,lm75"; ++ reg = <0x48>; ++ }; ++ ++ eeprom@50 { ++ compatible = "at24,24c16"; ++ reg = <0x50>; ++ }; ++ }; ++ ++ GPIO0: gpio-controller@ef600700 { ++ compatible = "ibm,ppc4xx-gpio"; ++ reg = <0xef600700 0x00000020>; ++ #gpio-cells = <2>; ++ gpio-controller; ++ }; ++ ++ EMAC0: ethernet@ef600800 { ++ linux,network-index = <0x0>; ++ device_type = "network"; ++ compatible = "ibm,emac-405ep", "ibm,emac"; ++ interrupt-parent = <&UIC0>; ++ interrupts = < ++ 0xf 0x4 /* Ethernet */ ++ 0x9 0x4 /* Ethernet Wake Up */>; ++ local-mac-address = [000000000000]; /* Filled in by zImage */ ++ reg = <0xef600800 0x00000070>; ++ mal-device = <&MAL>; ++ mal-tx-channel = <0>; ++ mal-rx-channel = <0>; ++ cell-index = <0>; ++ max-frame-size = <0x5dc>; ++ rx-fifo-size = <0x1000>; ++ tx-fifo-size = <0x800>; ++ phy-mode = "mii"; ++ phy-map = <0x00000000>; ++ }; ++ ++ EMAC1: ethernet@ef600900 { ++ linux,network-index = <0x1>; ++ device_type = "network"; ++ compatible = "ibm,emac-405ep", "ibm,emac"; ++ interrupt-parent = <&UIC0>; ++ interrupts = < ++ 0x11 0x4 /* Ethernet */ ++ 0x09 0x4 /* Ethernet Wake Up */>; ++ local-mac-address = [000000000000]; /* Filled in by zImage */ ++ reg = <0xef600900 0x00000070>; ++ mal-device = <&MAL>; ++ mal-tx-channel = <2>; ++ mal-rx-channel = <1>; ++ cell-index = <1>; ++ max-frame-size = <0x5dc>; ++ rx-fifo-size = <0x1000>; ++ tx-fifo-size = <0x800>; ++ mdio-device = <&EMAC0>; ++ phy-mode = "mii"; ++ phy-map = <0x00000001>; ++ }; ++ ++ leds { ++ compatible = "gpio-leds"; ++ user { ++ label = "magicbox:red:user"; ++ gpios = <&GPIO0 2 1>; ++ }; ++ }; ++ }; ++ ++ EBC0: ebc { ++ compatible = "ibm,ebc-405ep", "ibm,ebc"; ++ dcr-reg = <0x012 0x002>; ++ #address-cells = <2>; ++ #size-cells = <1>; ++ /* The ranges property is supplied by the bootwrapper ++ * and is based on the firmware's configuration of the ++ * EBC bridge ++ */ ++ clock-frequency = <0>; /* Filled in by zImage */ ++ ++ cf_card@ff100000 { ++ compatible = "magicbox-cf", "pata-magicbox-cf"; ++ reg = <0x00000000 0xff100000 0x00001000 ++ 0x00000000 0xff200000 0x00001000>; ++ interrupt-parent = <&UIC0>; ++ interrupts = <0x19 0x1 /* IRQ_TYPE_EDGE_RISING */ >; ++ }; ++ ++ nor_flash@ffc00000 { ++ compatible = "cfi-flash"; ++ bank-width = <2>; ++ reg = <0x00000000 0xffc00000 0x00400000>; ++ #address-cells = <1>; ++ #size-cells = <1>; ++ partition0@0 { ++ label = "linux"; ++ reg = <0x0 0x160000>; ++ }; ++ partition1@120000 { ++ label = "rootfs"; ++ reg = <0x160000 0x260000>; ++ }; ++ partition2@3c0000 { ++ label = "u-boot"; ++ reg = <0x3c0000 0x30000>; ++ read-only; ++ }; ++ partition3@0 { ++ label = "firmware"; ++ reg = <0x0 0x3c0000>; ++ }; ++ }; ++ }; ++ ++ PCI0: pci@ec000000 { ++ device_type = "pci"; ++ #interrupt-cells = <1>; ++ #size-cells = <2>; ++ #address-cells = <3>; ++ compatible = "ibm,plb405ep-pci", "ibm,plb-pci"; ++ primary; ++ reg = <0xeec00000 0x00000008 /* Config space access */ ++ 0xeed80000 0x00000004 /* IACK */ ++ 0xeed80000 0x00000004 /* Special cycle */ ++ 0xef480000 0x00000040>; /* Internal registers */ ++ ++ /* Outbound ranges, one memory and one IO, ++ * later cannot be changed. Chip supports a second ++ * IO range but we don't use it for now ++ */ ++ ranges = <0x02000000 0x00000000 0x80000000 0x80000000 0x00000000 0x20000000 ++ 0x01000000 0x00000000 0x00000000 0xe8000000 0x00000000 0x00010000>; ++ ++ /* Inbound 2GB range starting at 0 */ ++ dma-ranges = <0x42000000 0x0 0x0 0x0 0x0 0x80000000>; ++ ++ interrupt-map-mask = <0xf800 0x0 0x0 0x0>; ++ interrupt-map = < ++ /* IDSEL 1 */ ++ 0x800 0x0 0x0 0x0 &UIC0 0x1c 0x8 ++ ++ /* IDSEL 2 */ ++ 0x1000 0x0 0x0 0x0 &UIC0 0x1d 0x8 ++ ++ /* IDSEL 3 */ ++ 0x1800 0x0 0x0 0x0 &UIC0 0x1e 0x8 ++ ++ /* IDSEL 4 */ ++ 0x2000 0x0 0x0 0x0 &UIC0 0x1f 0x8 ++ >; ++ }; ++ }; ++ ++ chosen { ++ linux,stdout-path = "/plb/opb/serial@ef600300"; ++ }; ++}; +--- a/arch/powerpc/boot/Makefile ++++ b/arch/powerpc/boot/Makefile +@@ -43,6 +43,7 @@ $(obj)/cuboot-hotfoot.o: BOOTCFLAGS += - + $(obj)/cuboot-taishan.o: BOOTCFLAGS += -mcpu=440 + $(obj)/cuboot-katmai.o: BOOTCFLAGS += -mcpu=440 + $(obj)/cuboot-acadia.o: BOOTCFLAGS += -mcpu=405 ++$(obj)/cuboot-magicbox.o: BOOTCFLAGS += -mcpu=405 + $(obj)/treeboot-walnut.o: BOOTCFLAGS += -mcpu=405 + $(obj)/treeboot-iss4xx.o: BOOTCFLAGS += -mcpu=405 + $(obj)/treeboot-currituck.o: BOOTCFLAGS += -mcpu=405 +@@ -78,7 +79,8 @@ src-plat-y := of.c + src-plat-$(CONFIG_40x) += fixed-head.S ep405.c cuboot-hotfoot.c \ + treeboot-walnut.c cuboot-acadia.c \ + cuboot-kilauea.c simpleboot.c \ +- virtex405-head.S virtex.c ++ virtex405-head.S virtex.c \ ++ cuboot-magicbox.c + src-plat-$(CONFIG_44x) += treeboot-ebony.c cuboot-ebony.c treeboot-bamboo.c \ + cuboot-bamboo.c cuboot-sam440ep.c \ + cuboot-sequoia.c cuboot-rainier.c \ +@@ -221,6 +223,7 @@ image-$(CONFIG_HOTFOOT) += cuImage.hot + image-$(CONFIG_WALNUT) += treeImage.walnut + image-$(CONFIG_ACADIA) += cuImage.acadia + image-$(CONFIG_OBS600) += uImage.obs600 ++image-$(CONFIG_MAGICBOX) += cuImage.magicbox + + # Board ports in arch/powerpc/platform/44x/Kconfig + image-$(CONFIG_EBONY) += treeImage.ebony cuImage.ebony +--- a/arch/powerpc/platforms/40x/Kconfig ++++ b/arch/powerpc/platforms/40x/Kconfig +@@ -37,6 +37,16 @@ config KILAUEA + help + This option enables support for the AMCC PPC405EX evaluation board. + ++config MAGICBOX ++ bool "Magicbox" ++ depends on 40x ++ default n ++ select PPC40x_SIMPLE ++ select 405EP ++ select PCI ++ help ++ This option enables support for the Magicbox boards. ++ + config MAKALU + bool "Makalu" + depends on 40x +--- a/arch/powerpc/platforms/40x/ppc40x_simple.c ++++ b/arch/powerpc/platforms/40x/ppc40x_simple.c +@@ -58,6 +58,7 @@ static const char * const board[] __init + "apm,klondike", + "est,hotfoot", + "plathome,obs600", ++ "magicbox", + NULL + }; + diff --git a/target/linux/ppc40x/patches-3.10/005-openrb.patch b/target/linux/ppc40x/patches-3.10/005-openrb.patch new file mode 100644 index 0000000000..ac0ef1b930 --- /dev/null +++ b/target/linux/ppc40x/patches-3.10/005-openrb.patch @@ -0,0 +1,447 @@ +--- /dev/null ++++ b/arch/powerpc/boot/cuboot-openrb.c +@@ -0,0 +1,94 @@ ++/* ++ * Old U-boot compatibility for OpenRB boards ++ * ++ * Author: Gabor Juhos <juhosg@openwrt.org> ++ * Imre Kaloz <kaloz@openwrt.org> ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include "ops.h" ++#include "io.h" ++#include "dcr.h" ++#include "stdio.h" ++#include "4xx.h" ++#include "44x.h" ++#include "cuboot.h" ++ ++#define TARGET_4xx ++#define TARGET_405EP ++#include "ppcboot.h" ++ ++static bd_t bd; ++ ++static void fixup_perwe(void) ++{ ++#define DCRN_CPC0_PCI_BASE 0xf9 ++ ++ /* Turn on PerWE instead of PCIINT */ ++ mtdcr(DCRN_CPC0_PCI_BASE, ++ mfdcr(DCRN_CPC0_PCI_BASE) | (0x80000000L >> 27)); ++ ++#undef DCRN_CPC0_PCI_BASE ++} ++ ++static void fixup_cf_card(void) ++{ ++#define CF_CS0_BASE 0xff100000 ++#define CF_CS1_BASE 0xff200000 ++ ++ /* PerCS1 (CF's CS0): base 0xff100000, 16-bit, rw */ ++ mtdcr(DCRN_EBC0_CFGADDR, EBC_B1CR); ++ mtdcr(DCRN_EBC0_CFGDATA, CF_CS0_BASE | EBC_BXCR_BS_1M | ++ EBC_BXCR_BU_RW | EBC_BXCR_BW_16); ++ mtdcr(DCRN_EBC0_CFGADDR, EBC_B1AP); ++ mtdcr(DCRN_EBC0_CFGDATA, 0x080bd800); ++ ++ /* PerCS2 (CF's CS1): base 0xff200000, 16-bit, rw */ ++ mtdcr(DCRN_EBC0_CFGADDR, EBC_B2CR); ++ mtdcr(DCRN_EBC0_CFGDATA, CF_CS1_BASE | EBC_BXCR_BS_1M | ++ EBC_BXCR_BU_RW | EBC_BXCR_BW_16); ++ mtdcr(DCRN_EBC0_CFGADDR, EBC_B2AP); ++ mtdcr(DCRN_EBC0_CFGDATA, 0x080bd800); ++ ++#undef CF_CS0_BASE ++#undef CF_CS1_BASE ++} ++ ++static void fixup_isp116x(void) ++{ ++#define ISP116X_CS_BASE 0xf0000000 ++ ++ /* PerCS3 (ISP1160's CS): base 0xf0000000, size 32MB, 16-bit, rw */ ++ mtdcr(DCRN_EBC0_CFGADDR, EBC_B3CR); ++ mtdcr(DCRN_EBC0_CFGDATA, ISP116X_CS_BASE | EBC_BXCR_BS_32M | ++ EBC_BXCR_BU_RW | EBC_BXCR_BW_16); ++ mtdcr(DCRN_EBC0_CFGADDR, EBC_B3AP); ++ mtdcr(DCRN_EBC0_CFGDATA, 0x03016600); ++ ++#undef ISP116X_CS_BASE ++} ++ ++static void openrb_fixups(void) ++{ ++ ibm405ep_fixup_clocks(bd.bi_procfreq / 8); ++ ibm4xx_sdram_fixup_memsize(); ++ ++ fixup_perwe(); ++ fixup_cf_card(); ++ fixup_isp116x(); ++ ++ dt_fixup_mac_addresses(&bd.bi_enetaddr, &bd.bi_enet1addr); ++} ++ ++void platform_init(unsigned long r3, unsigned long r4, unsigned long r5, ++ unsigned long r6, unsigned long r7) ++{ ++ CUBOOT_INIT(); ++ platform_ops.fixups = openrb_fixups; ++ platform_ops.exit = ibm40x_dbcr_reset; ++ fdt_init(_dtb_start); ++ serial_console_init(); ++} +--- /dev/null ++++ b/arch/powerpc/boot/dts/openrb.dts +@@ -0,0 +1,291 @@ ++/* ++ * Device Tree Source for OpenRB boards ++ * ++ * Copyright 2009 Gabor Juhos <juhosg@openwrt.org> ++ * Copyright 2009 Imre Kaloz <kaloz@openwrt.org> ++ * ++ * Based on walnut.dts ++ * ++ * This file is licensed under the terms of the GNU General Public ++ * License version 2. This program is licensed "as is" without ++ * any warranty of any kind, whether express or implied. ++ */ ++ ++/dts-v1/; ++ ++/ { ++ #address-cells = <1>; ++ #size-cells = <1>; ++ model = "openrb"; ++ compatible = "openrb"; ++ dcr-parent = <&{/cpus/cpu@0}>; ++ ++ aliases { ++ ethernet0 = &EMAC0; ++ ethernet1 = &EMAC1; ++ serial0 = &UART0; ++ serial1 = &UART1; ++ }; ++ ++ cpus { ++ #address-cells = <1>; ++ #size-cells = <0>; ++ ++ cpu@0 { ++ device_type = "cpu"; ++ model = "PowerPC,405EP"; ++ reg = <0x00000000>; ++ clock-frequency = <0>; /* Filled in by zImage */ ++ timebase-frequency = <0>; /* Filled in by zImage */ ++ i-cache-line-size = <0x20>; ++ d-cache-line-size = <0x20>; ++ i-cache-size = <0x4000>; ++ d-cache-size = <0x4000>; ++ dcr-controller; ++ dcr-access-method = "native"; ++ }; ++ }; ++ ++ memory { ++ device_type = "memory"; ++ reg = <0x00000000 0x00000000>; /* Filled in by zImage */ ++ }; ++ ++ UIC0: interrupt-controller { ++ compatible = "ibm,uic"; ++ interrupt-controller; ++ cell-index = <0>; ++ dcr-reg = <0x0c0 0x009>; ++ #address-cells = <0>; ++ #size-cells = <0>; ++ #interrupt-cells = <2>; ++ }; ++ ++ plb { ++ compatible = "ibm,plb3"; ++ #address-cells = <1>; ++ #size-cells = <1>; ++ ranges; ++ clock-frequency = <0>; /* Filled in by zImage */ ++ ++ SDRAM0: memory-controller { ++ compatible = "ibm,sdram-405ep"; ++ dcr-reg = <0x010 0x002>; ++ }; ++ ++ MAL: mcmal { ++ compatible = "ibm,mcmal-405ep", "ibm,mcmal"; ++ dcr-reg = <0x180 0x062>; ++ num-tx-chans = <4>; ++ num-rx-chans = <2>; ++ interrupt-parent = <&UIC0>; ++ interrupts = < ++ 0xb 0x4 /* TXEOB */ ++ 0xc 0x4 /* RXEOB */ ++ 0xa 0x4 /* SERR */ ++ 0xd 0x4 /* TXDE */ ++ 0xe 0x4 /* RXDE */>; ++ }; ++ ++ POB0: opb { ++ compatible = "ibm,opb-405ep", "ibm,opb"; ++ #address-cells = <1>; ++ #size-cells = <1>; ++ ranges = <0xef600000 0xef600000 0x00a00000>; ++ dcr-reg = <0x0a0 0x005>; ++ clock-frequency = <0>; /* Filled in by zImage */ ++ ++ UART0: serial@ef600300 { ++ device_type = "serial"; ++ compatible = "ns16550"; ++ reg = <0xef600300 0x00000008>; ++ virtual-reg = <0xef600300>; ++ clock-frequency = <0>; /* Filled in by zImage */ ++ current-speed = <115200>; ++ interrupt-parent = <&UIC0>; ++ interrupts = <0x0 0x4>; ++ }; ++ ++ UART1: serial@ef600400 { ++ device_type = "serial"; ++ compatible = "ns16550"; ++ reg = <0xef600400 0x00000008>; ++ virtual-reg = <0xef600400>; ++ clock-frequency = <0>; /* Filled in by zImage */ ++ current-speed = <115200>; ++ interrupt-parent = <&UIC0>; ++ interrupts = <0x1 0x4>; ++ }; ++ ++ IIC: i2c@ef600500 { ++ compatible = "ibm,iic-405ep", "ibm,iic"; ++ #address-cells = <1>; ++ #size-cells = <0>; ++ reg = <0xef600500 0x00000011>; ++ interrupt-parent = <&UIC0>; ++ interrupts = <0x2 0x4>; ++ ++ eeprom@50 { ++ compatible = "at24,24c16"; ++ reg = <0x50>; ++ }; ++ }; ++ ++ GPIO0: gpio-controller@ef600700 { ++ compatible = "ibm,ppc4xx-gpio"; ++ reg = <0xef600700 0x00000020>; ++ #gpio-cells = <2>; ++ gpio-controller; ++ }; ++ ++ EMAC0: ethernet@ef600800 { ++ linux,network-index = <0x0>; ++ device_type = "network"; ++ compatible = "ibm,emac-405ep", "ibm,emac"; ++ interrupt-parent = <&UIC0>; ++ interrupts = < ++ 0xf 0x4 /* Ethernet */ ++ 0x9 0x4 /* Ethernet Wake Up */>; ++ local-mac-address = [000000000000]; /* Filled in by zImage */ ++ reg = <0xef600800 0x00000070>; ++ mal-device = <&MAL>; ++ mal-tx-channel = <0>; ++ mal-rx-channel = <0>; ++ cell-index = <0>; ++ max-frame-size = <0x5dc>; ++ rx-fifo-size = <0x1000>; ++ tx-fifo-size = <0x800>; ++ phy-mode = "mii"; ++ phy-map = <0x00000000>; ++ }; ++ ++ EMAC1: ethernet@ef600900 { ++ linux,network-index = <0x1>; ++ device_type = "network"; ++ compatible = "ibm,emac-405ep", "ibm,emac"; ++ interrupt-parent = <&UIC0>; ++ interrupts = < ++ 0x11 0x4 /* Ethernet */ ++ 0x09 0x4 /* Ethernet Wake Up */>; ++ local-mac-address = [000000000000]; /* Filled in by zImage */ ++ reg = <0xef600900 0x00000070>; ++ mal-device = <&MAL>; ++ mal-tx-channel = <2>; ++ mal-rx-channel = <1>; ++ cell-index = <1>; ++ max-frame-size = <0x5dc>; ++ rx-fifo-size = <0x1000>; ++ tx-fifo-size = <0x800>; ++ mdio-device = <&EMAC0>; ++ phy-mode = "mii"; ++ phy-map = <0x00000001>; ++ }; ++ ++ leds { ++ compatible = "gpio-leds"; ++ user { ++ label = "openrb:green:user"; ++ gpios = <&GPIO0 2 1>; ++ }; ++ }; ++ }; ++ ++ EBC0: ebc { ++ compatible = "ibm,ebc-405ep", "ibm,ebc"; ++ dcr-reg = <0x012 0x002>; ++ #address-cells = <2>; ++ #size-cells = <1>; ++ /* The ranges property is supplied by the bootwrapper ++ * and is based on the firmware's configuration of the ++ * EBC bridge ++ */ ++ clock-frequency = <0>; /* Filled in by zImage */ ++ ++ isp116x@f0000000 { ++ compatible = "isp116x-hcd"; ++ oc_enable; ++ int_act_high; ++ int_edge_triggered; ++ reg = <0x00000000 0xf0000000 0x00000002 /* data */ ++ 0x00000000 0xf1000000 0x00000002 /* addr */ >; ++ interrupt-parent = <&UIC0>; ++ interrupts = <0x1b 0x1 /* IRQ_TYPE_EDGE_RISING */ >; ++ }; ++ ++ cf_card@ff100000 { ++ compatible = "magicbox-cf", "pata-magicbox-cf"; ++ reg = <0x00000000 0xff100000 0x00001000 ++ 0x00000000 0xff200000 0x00001000>; ++ interrupt-parent = <&UIC0>; ++ interrupts = <0x19 0x1 /* IRQ_TYPE_EDGE_RISING */ >; ++ }; ++ ++ nor_flash@ff800000 { ++ compatible = "cfi-flash"; ++ bank-width = <2>; ++ reg = <0x00000000 0xff800000 0x00800000>; ++ #address-cells = <1>; ++ #size-cells = <1>; ++ partition0@0 { ++ label = "linux"; ++ reg = <0x0 0x160000>; ++ }; ++ partition1@120000 { ++ label = "rootfs"; ++ reg = <0x160000 0x660000>; ++ }; ++ partition2@7c0000 { ++ label = "u-boot"; ++ reg = <0x7c0000 0x30000>; ++ read-only; ++ }; ++ partition3@0 { ++ label = "firmware"; ++ reg = <0x0 0x7c0000>; ++ }; ++ }; ++ }; ++ ++ PCI0: pci@ec000000 { ++ device_type = "pci"; ++ #interrupt-cells = <1>; ++ #size-cells = <2>; ++ #address-cells = <3>; ++ compatible = "ibm,plb405ep-pci", "ibm,plb-pci"; ++ primary; ++ reg = <0xeec00000 0x00000008 /* Config space access */ ++ 0xeed80000 0x00000004 /* IACK */ ++ 0xeed80000 0x00000004 /* Special cycle */ ++ 0xef480000 0x00000040>; /* Internal registers */ ++ ++ /* Outbound ranges, one memory and one IO, ++ * later cannot be changed. Chip supports a second ++ * IO range but we don't use it for now ++ */ ++ ranges = <0x02000000 0x00000000 0x80000000 0x80000000 0x00000000 0x20000000 ++ 0x01000000 0x00000000 0x00000000 0xe8000000 0x00000000 0x00010000>; ++ ++ /* Inbound 2GB range starting at 0 */ ++ dma-ranges = <0x42000000 0x0 0x0 0x0 0x0 0x80000000>; ++ ++ interrupt-map-mask = <0xf800 0x0 0x0 0x0>; ++ interrupt-map = < ++ /* IDSEL 1 */ ++ 0x800 0x0 0x0 0x0 &UIC0 0x1c 0x8 ++ ++ /* IDSEL 2 */ ++ 0x1000 0x0 0x0 0x0 &UIC0 0x1d 0x8 ++ ++ /* IDSEL 3 */ ++ 0x1800 0x0 0x0 0x0 &UIC0 0x1e 0x8 ++ ++ /* IDSEL 4 */ ++ 0x2000 0x0 0x0 0x0 &UIC0 0x1f 0x8 ++ >; ++ }; ++ }; ++ ++ chosen { ++ linux,stdout-path = "/plb/opb/serial@ef600300"; ++ }; ++}; +--- a/arch/powerpc/boot/Makefile ++++ b/arch/powerpc/boot/Makefile +@@ -44,6 +44,7 @@ $(obj)/cuboot-taishan.o: BOOTCFLAGS += - + $(obj)/cuboot-katmai.o: BOOTCFLAGS += -mcpu=440 + $(obj)/cuboot-acadia.o: BOOTCFLAGS += -mcpu=405 + $(obj)/cuboot-magicbox.o: BOOTCFLAGS += -mcpu=405 ++$(obj)/cuboot-openrb.o: BOOTCFLAGS += -mcpu=405 + $(obj)/treeboot-walnut.o: BOOTCFLAGS += -mcpu=405 + $(obj)/treeboot-iss4xx.o: BOOTCFLAGS += -mcpu=405 + $(obj)/treeboot-currituck.o: BOOTCFLAGS += -mcpu=405 +@@ -80,7 +81,7 @@ src-plat-$(CONFIG_40x) += fixed-head.S e + treeboot-walnut.c cuboot-acadia.c \ + cuboot-kilauea.c simpleboot.c \ + virtex405-head.S virtex.c \ +- cuboot-magicbox.c ++ cuboot-magicbox.c cuboot-openrb + src-plat-$(CONFIG_44x) += treeboot-ebony.c cuboot-ebony.c treeboot-bamboo.c \ + cuboot-bamboo.c cuboot-sam440ep.c \ + cuboot-sequoia.c cuboot-rainier.c \ +@@ -224,6 +225,7 @@ image-$(CONFIG_WALNUT) += treeImage.wa + image-$(CONFIG_ACADIA) += cuImage.acadia + image-$(CONFIG_OBS600) += uImage.obs600 + image-$(CONFIG_MAGICBOX) += cuImage.magicbox ++image-$(CONFIG_OPENRB) += cuImage.openrb + + # Board ports in arch/powerpc/platform/44x/Kconfig + image-$(CONFIG_EBONY) += treeImage.ebony cuImage.ebony +--- a/arch/powerpc/platforms/40x/Kconfig ++++ b/arch/powerpc/platforms/40x/Kconfig +@@ -47,6 +47,16 @@ config MAGICBOX + help + This option enables support for the Magicbox boards. + ++config OPENRB ++ bool "OpenRB" ++ depends on 40x ++ default n ++ select PPC40x_SIMPLE ++ select 405EP ++ select PCI ++ help ++ This option enables support for the OpenRB boards. ++ + config MAKALU + bool "Makalu" + depends on 40x +--- a/arch/powerpc/platforms/40x/ppc40x_simple.c ++++ b/arch/powerpc/platforms/40x/ppc40x_simple.c +@@ -59,6 +59,7 @@ static const char * const board[] __init + "est,hotfoot", + "plathome,obs600", + "magicbox", ++ "openrb", + NULL + }; + diff --git a/target/linux/ppc40x/patches-3.10/101-pata-magicbox-cf-driver.patch b/target/linux/ppc40x/patches-3.10/101-pata-magicbox-cf-driver.patch new file mode 100644 index 0000000000..e94ff31126 --- /dev/null +++ b/target/linux/ppc40x/patches-3.10/101-pata-magicbox-cf-driver.patch @@ -0,0 +1,433 @@ +--- a/drivers/ata/Kconfig ++++ b/drivers/ata/Kconfig +@@ -158,6 +158,16 @@ config PDC_ADMA + + If unsure, say N. + ++config PATA_MAGICBOX_CF ++ tristate "Magicbox/OpenRB Compact Flash support" ++ depends on MAGICBOX || OPENRB ++ help ++ This option enables support for a Compact Flash conected on ++ the ppc405ep expansion bus. This driver had been written for ++ the Magicbox v2 and OpenRB boards. ++ ++ If unsure, say N. ++ + config PATA_OCTEON_CF + tristate "OCTEON Boot Bus Compact Flash support" + depends on CPU_CAVIUM_OCTEON +--- a/drivers/ata/Makefile ++++ b/drivers/ata/Makefile +@@ -84,6 +84,7 @@ obj-$(CONFIG_PATA_AT91) += pata_at91.o + obj-$(CONFIG_PATA_CMD640_PCI) += pata_cmd640.o + obj-$(CONFIG_PATA_ISAPNP) += pata_isapnp.o + obj-$(CONFIG_PATA_IXP4XX_CF) += pata_ixp4xx_cf.o ++obj-$(CONFIG_PATA_MAGICBOX_CF) += pata_magicbox_cf.o + obj-$(CONFIG_PATA_MPIIX) += pata_mpiix.o + obj-$(CONFIG_PATA_NS87410) += pata_ns87410.o + obj-$(CONFIG_PATA_OPTI) += pata_opti.o +--- /dev/null ++++ b/drivers/ata/pata_magicbox_cf.c +@@ -0,0 +1,401 @@ ++/* ++ * PATA/CompactFlash driver for the MagicBox v2/OpenRB boards. ++ * ++ * Copyright (C) 2009,2012 Gabor Juhos <juhosg@openwrt.org> ++ * ++ * Based on the IDE driver by Wojtek Kaniewski <wojtekka@toxygen.net> ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include <linux/kernel.h> ++#include <linux/module.h> ++#include <linux/slab.h> ++#include <linux/types.h> ++#include <linux/ioport.h> ++#include <linux/libata.h> ++#include <linux/irq.h> ++//#include <linux/of.h> ++//#include <linux/of_device.h> ++#include <linux/of_platform.h> ++#include <scsi/scsi_host.h> ++ ++#define DRV_DESC "PATA/CompactFlash driver for Magicbox/OpenRB boards" ++#define DRV_NAME "pata_magicbox_cf" ++#define DRV_VERSION "0.1.0" ++ ++#define MAGICBOX_CF_REG_CMD (2 * ATA_REG_CMD) ++#define MAGICBOX_CF_REG_DATA (2 * ATA_REG_DATA) ++#define MAGICBOX_CF_REG_ERR (2 * ATA_REG_ERR) ++#define MAGICBOX_CF_REG_FEATURE (2 * ATA_REG_FEATURE) ++#define MAGICBOX_CF_REG_NSECT (2 * ATA_REG_NSECT) ++#define MAGICBOX_CF_REG_LBAL (2 * ATA_REG_LBAL) ++#define MAGICBOX_CF_REG_LBAM (2 * ATA_REG_LBAM) ++#define MAGICBOX_CF_REG_LBAH (2 * ATA_REG_LBAH) ++#define MAGICBOX_CF_REG_DEVICE (2 * ATA_REG_DEVICE) ++#define MAGICBOX_CF_REG_STATUS (2 * ATA_REG_STATUS) ++#define MAGICBOX_CF_REG_ALTSTATUS (2 * 6) ++#define MAGICBOX_CF_REG_CTL (2 * 6) ++ ++#define MAGICBOX_CF_MAXPORTS 1 ++ ++struct magicbox_cf_info { ++ void __iomem *base; ++ void __iomem *ctrl; ++}; ++ ++static inline u8 magicbox_cf_inb(void __iomem *port) ++{ ++ return (u8) (readw(port) >> 8) & 0xff; ++} ++ ++static inline void magicbox_cf_outb(void __iomem *port, u8 value) ++{ ++ writew(value << 8, port); ++} ++ ++static int magicbox_cf_set_mode(struct ata_link *link, ++ struct ata_device **error) ++{ ++ struct ata_device *dev; ++ ++ ata_for_each_dev(dev, link, ENABLED) { ++ ata_dev_printk(dev, KERN_INFO, "configured for PIO0\n"); ++ dev->pio_mode = XFER_PIO_0; ++ dev->xfer_mode = XFER_PIO_0; ++ dev->xfer_shift = ATA_SHIFT_PIO; ++ dev->flags |= ATA_DFLAG_PIO; ++ } ++ ++ return 0; ++} ++ ++static void magicbox_cf_exec_command(struct ata_port *ap, ++ const struct ata_taskfile *tf) ++{ ++ DPRINTK("ata%u: cmd 0x%X\n", ap->print_id, tf->command); ++ ++ magicbox_cf_outb(ap->ioaddr.command_addr, tf->command); ++ ata_sff_pause(ap); ++} ++ ++static u8 magicbox_cf_check_status(struct ata_port *ap) ++{ ++ u8 status; ++ ++ status = magicbox_cf_inb(ap->ioaddr.status_addr); ++ ++ DPRINTK("ata%u: status 0x%X, from %p\n", ap->print_id, status, ++ ap->ioaddr.status_addr); ++ ++ return status; ++} ++ ++static u8 magicbox_cf_check_altstatus(struct ata_port *ap) ++{ ++ u8 altstatus; ++ ++ altstatus = magicbox_cf_inb(ap->ioaddr.altstatus_addr); ++ ++ DPRINTK("ata%u: altstatus 0x%X, from %p\n", ap->print_id, ++ altstatus, ap->ioaddr.altstatus_addr); ++ ++ return altstatus; ++} ++ ++static void magicbox_cf_dev_select(struct ata_port *ap, unsigned int device) ++{ ++ /* Nothing to do. We are supporting one device only. */ ++} ++ ++static void magicbox_cf_tf_load(struct ata_port *ap, ++ const struct ata_taskfile *tf) ++{ ++ struct ata_ioports *ioaddr = &ap->ioaddr; ++ unsigned int is_addr = tf->flags & ATA_TFLAG_ISADDR; ++ ++ if (tf->ctl != ap->last_ctl) { ++ magicbox_cf_outb(ioaddr->ctl_addr, tf->ctl); ++ ap->last_ctl = tf->ctl; ++ ata_wait_idle(ap); ++ } ++ ++ if (is_addr && (tf->flags & ATA_TFLAG_LBA48)) { ++ magicbox_cf_outb(ioaddr->feature_addr, tf->hob_feature); ++ magicbox_cf_outb(ioaddr->nsect_addr, tf->hob_nsect); ++ magicbox_cf_outb(ioaddr->lbal_addr, tf->hob_lbal); ++ magicbox_cf_outb(ioaddr->lbam_addr, tf->hob_lbam); ++ magicbox_cf_outb(ioaddr->lbah_addr, tf->hob_lbah); ++ VPRINTK("hob: feat 0x%X nsect 0x%X, lba 0x%X 0x%X 0x%X\n", ++ tf->hob_feature, ++ tf->hob_nsect, ++ tf->hob_lbal, ++ tf->hob_lbam, ++ tf->hob_lbah); ++ } ++ ++ if (is_addr) { ++ magicbox_cf_outb(ioaddr->feature_addr, tf->feature); ++ magicbox_cf_outb(ioaddr->nsect_addr, tf->nsect); ++ magicbox_cf_outb(ioaddr->lbal_addr, tf->lbal); ++ magicbox_cf_outb(ioaddr->lbam_addr, tf->lbam); ++ magicbox_cf_outb(ioaddr->lbah_addr, tf->lbah); ++ VPRINTK("feat 0x%X nsect 0x%X lba 0x%X 0x%X 0x%X\n", ++ tf->feature, ++ tf->nsect, ++ tf->lbal, ++ tf->lbam, ++ tf->lbah); ++ } ++ ++ if (tf->flags & ATA_TFLAG_DEVICE) { ++ magicbox_cf_outb(ioaddr->device_addr, tf->device); ++ VPRINTK("device 0x%X\n", tf->device); ++ } ++ ++ ata_wait_idle(ap); ++} ++ ++static void magicbox_cf_tf_read(struct ata_port *ap, struct ata_taskfile *tf) ++{ ++ struct ata_ioports *ioaddr = &ap->ioaddr; ++ ++ tf->command = magicbox_cf_inb(ap->ioaddr.status_addr); ++ tf->feature = magicbox_cf_inb(ioaddr->error_addr); ++ tf->nsect = magicbox_cf_inb(ioaddr->nsect_addr); ++ tf->lbal = magicbox_cf_inb(ioaddr->lbal_addr); ++ tf->lbam = magicbox_cf_inb(ioaddr->lbam_addr); ++ tf->lbah = magicbox_cf_inb(ioaddr->lbah_addr); ++ tf->device = magicbox_cf_inb(ioaddr->device_addr); ++ VPRINTK("feat 0x%X nsect 0x%X lba 0x%X 0x%X 0x%X\n", ++ tf->feature, ++ tf->nsect, ++ tf->lbal, ++ tf->lbam, ++ tf->lbah); ++ ++ if (tf->flags & ATA_TFLAG_LBA48) { ++ magicbox_cf_outb(ioaddr->ctl_addr, tf->ctl | ATA_HOB); ++ tf->hob_feature = magicbox_cf_inb(ioaddr->error_addr); ++ tf->hob_nsect = magicbox_cf_inb(ioaddr->nsect_addr); ++ tf->hob_lbal = magicbox_cf_inb(ioaddr->lbal_addr); ++ tf->hob_lbam = magicbox_cf_inb(ioaddr->lbam_addr); ++ tf->hob_lbah = magicbox_cf_inb(ioaddr->lbah_addr); ++ magicbox_cf_outb(ioaddr->ctl_addr, tf->ctl); ++ ap->last_ctl = tf->ctl; ++ VPRINTK("hob: feat 0x%X nsect 0x%X lba 0x%X 0x%X 0x%X\n", ++ tf->feature, ++ tf->nsect, ++ tf->lbal, ++ tf->lbam, ++ tf->lbah); ++ } ++} ++ ++static unsigned int magicbox_cf_data_xfer(struct ata_device *dev, ++ unsigned char *buf, ++ unsigned int buflen, int rw) ++{ ++ struct ata_port *ap = dev->link->ap; ++ unsigned int words = buflen >> 1; ++ unsigned int i; ++ u16 *buf16 = (u16 *) buf; ++ void __iomem *mmio = ap->ioaddr.data_addr; ++ ++ /* Transfer multiple of 2 bytes */ ++ if (rw == READ) ++ for (i = 0; i < words; i++) ++ buf16[i] = readw(mmio); ++ else ++ for (i = 0; i < words; i++) ++ writew(buf16[i], mmio); ++ ++ /* Transfer trailing 1 byte, if any. */ ++ if (unlikely(buflen & 0x01)) { ++ u16 align_buf[1] = { 0 }; ++ unsigned char *trailing_buf = buf + buflen - 1; ++ ++ if (rw == READ) { ++ align_buf[0] = readw(mmio); ++ memcpy(trailing_buf, align_buf, 1); ++ } else { ++ memcpy(align_buf, trailing_buf, 1); ++ writew(align_buf[0], mmio); ++ } ++ words++; ++ } ++ ++ return words << 1; ++} ++ ++static void magicbox_cf_irq_on(struct ata_port *ap) ++{ ++ /* Nothing to do. */ ++} ++ ++static void magicbox_cf_irq_clear(struct ata_port *ap) ++{ ++ /* Nothing to do. */ ++} ++ ++static struct ata_port_operations magicbox_cf_port_ops = { ++ .inherits = &ata_sff_port_ops, ++ ++ .cable_detect = ata_cable_40wire, ++ .set_mode = magicbox_cf_set_mode, ++ ++ .sff_exec_command = magicbox_cf_exec_command, ++ .sff_check_status = magicbox_cf_check_status, ++ .sff_check_altstatus = magicbox_cf_check_altstatus, ++ .sff_dev_select = magicbox_cf_dev_select, ++ .sff_tf_load = magicbox_cf_tf_load, ++ .sff_tf_read = magicbox_cf_tf_read, ++ .sff_data_xfer = magicbox_cf_data_xfer, ++ ++ .sff_irq_on = magicbox_cf_irq_on, ++ .sff_irq_clear = magicbox_cf_irq_clear, ++ ++ .port_start = ATA_OP_NULL, ++}; ++ ++static struct scsi_host_template magicbox_cf_sht = { ++ ATA_PIO_SHT(DRV_NAME), ++}; ++ ++static inline void magicbox_cf_setup_port(struct ata_host *host) ++{ ++ struct magicbox_cf_info *info = host->private_data; ++ struct ata_port *ap; ++ ++ ap = host->ports[0]; ++ ++ ap->ops = &magicbox_cf_port_ops; ++ ap->pio_mask = ATA_PIO4; ++ ap->flags |= ATA_FLAG_NO_ATAPI; ++ ++ ap->ioaddr.cmd_addr = info->base + MAGICBOX_CF_REG_CMD; ++ ap->ioaddr.data_addr = info->base + MAGICBOX_CF_REG_DATA; ++ ap->ioaddr.error_addr = info->base + MAGICBOX_CF_REG_ERR; ++ ap->ioaddr.feature_addr = info->base + MAGICBOX_CF_REG_FEATURE; ++ ap->ioaddr.nsect_addr = info->base + MAGICBOX_CF_REG_NSECT; ++ ap->ioaddr.lbal_addr = info->base + MAGICBOX_CF_REG_LBAL; ++ ap->ioaddr.lbam_addr = info->base + MAGICBOX_CF_REG_LBAM; ++ ap->ioaddr.lbah_addr = info->base + MAGICBOX_CF_REG_LBAH; ++ ap->ioaddr.device_addr = info->base + MAGICBOX_CF_REG_DEVICE; ++ ap->ioaddr.status_addr = info->base + MAGICBOX_CF_REG_STATUS; ++ ap->ioaddr.command_addr = info->base + MAGICBOX_CF_REG_CMD; ++ ++ ap->ioaddr.altstatus_addr = info->ctrl + MAGICBOX_CF_REG_ALTSTATUS; ++ ap->ioaddr.ctl_addr = info->ctrl + MAGICBOX_CF_REG_CTL; ++ ++ ata_port_desc(ap, "cmd 0x%p ctl 0x%p", ap->ioaddr.cmd_addr, ++ ap->ioaddr.ctl_addr); ++} ++ ++static int magicbox_cf_of_probe(struct platform_device *op) ++{ ++ struct magicbox_cf_info *info; ++ struct ata_host *host; ++ int irq; ++ int ret = 0; ++ ++ info = kzalloc(sizeof(struct magicbox_cf_info), GFP_KERNEL); ++ if (info == NULL) { ++ ret = -ENOMEM; ++ goto err_exit; ++ } ++ ++ irq = irq_of_parse_and_map(op->dev.of_node, 0); ++ if (irq < 0) { ++ dev_err(&op->dev, "invalid irq\n"); ++ ret = -EINVAL; ++ goto err_free_info; ++ } ++ ++ info->base = of_iomap(op->dev.of_node, 0); ++ if (info->base == NULL) { ++ ret = -ENOMEM; ++ goto err_free_info; ++ } ++ ++ info->ctrl = of_iomap(op->dev.of_node, 1); ++ if (info->ctrl == NULL) { ++ ret = -ENOMEM; ++ goto err_unmap_base; ++ } ++ ++ host = ata_host_alloc(&op->dev, MAGICBOX_CF_MAXPORTS); ++ if (host == NULL) { ++ ret = -ENOMEM; ++ goto err_unmap_ctrl; ++ } ++ ++ host->private_data = info; ++ magicbox_cf_setup_port(host); ++ ++ ret = ata_host_activate(host, irq, ata_sff_interrupt, ++ IRQF_TRIGGER_RISING, &magicbox_cf_sht); ++ if (ret) ++ goto err_unmap_ctrl; ++ ++ dev_set_drvdata(&op->dev, host); ++ return 0; ++ ++ err_unmap_ctrl: ++ iounmap(info->ctrl); ++ err_unmap_base: ++ iounmap(info->base); ++ err_free_info: ++ kfree(info); ++ err_exit: ++ return ret; ++} ++ ++static int magicbox_cf_of_remove(struct platform_device *op) ++{ ++ struct ata_host *host = dev_get_drvdata(&op->dev); ++ struct magicbox_cf_info *info = host->private_data; ++ ++ ata_host_detach(host); ++ iounmap(info->ctrl); ++ iounmap(info->base); ++ kfree(info); ++ ++ return 0; ++} ++ ++static struct of_device_id magicbox_cf_of_match[] = { ++ { .compatible = "pata-magicbox-cf", }, ++ {}, ++}; ++ ++static struct platform_driver magicbox_cf_of_platform_driver = { ++ .probe = magicbox_cf_of_probe, ++ .remove = magicbox_cf_of_remove, ++ .driver = { ++ .name = DRV_NAME, ++ .owner = THIS_MODULE, ++ .of_match_table = magicbox_cf_of_match, ++ }, ++}; ++ ++static int __init magicbox_cf_init(void) ++{ ++ return platform_driver_register(&magicbox_cf_of_platform_driver); ++} ++ ++static void __exit magicbox_cf_exit(void) ++{ ++ platform_driver_unregister(&magicbox_cf_of_platform_driver); ++} ++ ++module_init(magicbox_cf_init); ++module_exit(magicbox_cf_exit); ++ ++MODULE_DESCRIPTION(DRV_DESC); ++MODULE_AUTHOR("Gabor Juhos <juhosg@openwrt.org>"); ++MODULE_LICENSE("GPL v2"); ++MODULE_VERSION(DRV_VERSION); ++MODULE_DEVICE_TABLE(of, magicbox_cf_of_match); diff --git a/target/linux/ppc40x/patches-3.10/110-kilauea_openwrt_flashmap.patch b/target/linux/ppc40x/patches-3.10/110-kilauea_openwrt_flashmap.patch new file mode 100644 index 0000000000..ab44a2d572 --- /dev/null +++ b/target/linux/ppc40x/patches-3.10/110-kilauea_openwrt_flashmap.patch @@ -0,0 +1,55 @@ +--- a/arch/powerpc/boot/dts/kilauea.dts ++++ b/arch/powerpc/boot/dts/kilauea.dts +@@ -102,8 +102,8 @@ + compatible = "ibm,sdram-405ex", "ibm,sdram-4xx-ddr2"; + dcr-reg = <0x010 0x002>; + interrupt-parent = <&UIC2>; +- interrupts = <0x5 0x4 /* ECC DED Error */ +- 0x6 0x4>; /* ECC SEC Error */ ++ interrupts = <0x5 0x4 /* ECC DED Error */ ++ 0x6 0x4>; /* ECC SEC Error */ + }; + + CRYPTO: crypto@ef700000 { +@@ -157,30 +157,30 @@ + reg = <0x00000000 0x00000000 0x04000000>; + #address-cells = <1>; + #size-cells = <1>; +- partition@0 { ++ partition0@0 { + label = "kernel"; + reg = <0x00000000 0x001e0000>; + }; +- partition@1e0000 { ++ partition1@1e0000 { + label = "dtb"; + reg = <0x001e0000 0x00020000>; + }; +- partition@200000 { +- label = "root"; +- reg = <0x00200000 0x00200000>; +- }; +- partition@400000 { +- label = "user"; +- reg = <0x00400000 0x03b60000>; ++ partition2@200000 { ++ label = "rootfs"; ++ reg = <0x00200000 0x03d60000>; + }; +- partition@3f60000 { ++ partition3@3f60000 { + label = "env"; + reg = <0x03f60000 0x00040000>; + }; +- partition@3fa0000 { ++ partition4@3fa0000 { + label = "u-boot"; + reg = <0x03fa0000 0x00060000>; + }; ++ partition5@0 { ++ label = "firmware"; ++ reg = <0x00000000 0x03f60000>; ++ }; + }; + + ndfc@1,0 { diff --git a/target/linux/ppc40x/patches-3.10/120-usb-isp116x-hcd-add-of-binding.patch b/target/linux/ppc40x/patches-3.10/120-usb-isp116x-hcd-add-of-binding.patch new file mode 100644 index 0000000000..41b69f02b2 --- /dev/null +++ b/target/linux/ppc40x/patches-3.10/120-usb-isp116x-hcd-add-of-binding.patch @@ -0,0 +1,290 @@ +--- a/drivers/usb/host/isp116x-hcd.c ++++ b/drivers/usb/host/isp116x-hcd.c +@@ -1534,6 +1534,7 @@ static struct hc_driver isp116x_hc_drive + + /*----------------------------------------------------------------*/ + ++#ifdef CONFIG_USB_ISP116X_HCD_PLATFORM + static int isp116x_remove(struct platform_device *pdev) + { + struct usb_hcd *hcd = platform_get_drvdata(pdev); +@@ -1710,4 +1711,251 @@ static struct platform_driver isp116x_dr + }, + }; + +-module_platform_driver(isp116x_driver); ++static inline int isp116x_platform_register(void) ++{ ++ return platform_driver_register(&isp116x_driver); ++} ++ ++static inline void isp116x_platform_unregister(void) ++{ ++ platform_driver_unregister(&isp116x_driver); ++} ++#else ++static inline int isp116x_platform_register(void) { return 0; }; ++static void isp116x_platform_unregister(void) {}; ++#endif /* CONFIG_USB_ISP116X_PLATFORM */ ++ ++/*-----------------------------------------------------------------*/ ++ ++#ifdef CONFIG_USB_ISP116X_HCD_OF ++ ++/* TODO: rework platform probe instead of using a separate probe */ ++ ++#include <linux/of_platform.h> ++ ++#ifdef USE_PLATFORM_DELAY ++static void isp116x_of_delay(struct device *ddev, int delay) ++{ ++ ndelay(delay); ++} ++#else ++#define isp116x_of_delay NULL ++#endif ++ ++static int isp116x_of_probe(struct platform_device *op) ++{ ++ struct device_node *dn = op->dev.of_node; ++ struct usb_hcd *hcd; ++ struct isp116x *isp116x; ++ struct resource addr, data; ++ struct isp116x_platform_data *board; ++ void __iomem *addr_reg; ++ void __iomem *data_reg; ++ int irq; ++ int ret = 0; ++ unsigned long irqflags; ++ ++ ret = of_address_to_resource(dn, 0, &data); ++ if (ret) ++ return ret; ++ ++ ret = of_address_to_resource(dn, 1, &addr); ++ if (ret) ++ return ret; ++ ++ board = kzalloc(sizeof(struct isp116x_platform_data), GFP_KERNEL); ++ if (board == NULL) ++ return -ENOMEM; ++ ++ if (!request_mem_region(addr.start, resource_size(&addr), hcd_name)) { ++ ret = -EBUSY; ++ goto err_free_board; ++ } ++ ++ addr_reg = ioremap_nocache(addr.start, resource_size(&addr)); ++ if (addr_reg == NULL) { ++ ret = -ENOMEM; ++ goto err_release_addr; ++ } ++ ++ if (!request_mem_region(data.start, resource_size(&data), hcd_name)) { ++ ret = -EBUSY; ++ goto err_unmap_addr; ++ } ++ ++ data_reg = ioremap_nocache(data.start, resource_size(&data)); ++ if (data_reg == NULL) { ++ ret = -ENOMEM; ++ goto err_release_data; ++ } ++ ++ irq = irq_of_parse_and_map(dn, 0); ++ if (irq == NO_IRQ) { ++ ret = -EINVAL; ++ goto err_unmap_data; ++ } ++ ++ /* allocate and initialize hcd */ ++ hcd = usb_create_hcd(&isp116x_hc_driver, &op->dev, dev_name(&op->dev)); ++ if (!hcd) { ++ ret = -ENOMEM; ++ goto err_irq_dispose; ++ } ++ ++ /* this rsrc_start is bogus */ ++ hcd->rsrc_start = addr.start; ++ isp116x = hcd_to_isp116x(hcd); ++ isp116x->data_reg = data_reg; ++ isp116x->addr_reg = addr_reg; ++ isp116x->board = board; ++ spin_lock_init(&isp116x->lock); ++ INIT_LIST_HEAD(&isp116x->async); ++ ++ board->delay = isp116x_of_delay; ++ if (of_get_property(dn, "sel15Kres", NULL)) ++ board->sel15Kres = 1; ++ if (of_get_property(dn, "oc_enable", NULL)) ++ board->oc_enable = 1; ++ if (of_get_property(dn, "remote_wakeup_enable", NULL)) ++ board->remote_wakeup_enable = 1; ++ ++ if (of_get_property(dn, "int_act_high", NULL)) ++ board->int_act_high = 1; ++ if (of_get_property(dn, "int_edge_triggered", NULL)) ++ board->int_edge_triggered = 1; ++ ++ if (board->int_edge_triggered) ++ irqflags = board->int_act_high ? IRQF_TRIGGER_RISING : ++ IRQF_TRIGGER_FALLING; ++ else ++ irqflags = board->int_act_high ? IRQF_TRIGGER_HIGH : ++ IRQF_TRIGGER_LOW; ++ ++ ret = usb_add_hcd(hcd, irq, irqflags | IRQF_DISABLED); ++ if (ret) ++ goto err_put_hcd; ++ ++ ret = create_debug_file(isp116x); ++ if (ret) { ++ ERR("Couldn't create debugfs entry\n"); ++ goto err_remove_hcd; ++ } ++ ++ return 0; ++ ++ err_remove_hcd: ++ usb_remove_hcd(hcd); ++ err_put_hcd: ++ usb_put_hcd(hcd); ++ err_irq_dispose: ++ irq_dispose_mapping(irq); ++ err_unmap_data: ++ iounmap(data_reg); ++ err_release_data: ++ release_mem_region(data.start, resource_size(&data)); ++ err_unmap_addr: ++ iounmap(addr_reg); ++ err_release_addr: ++ release_mem_region(addr.start, resource_size(&addr)); ++ err_free_board: ++ kfree(board); ++ return ret; ++} ++ ++static int isp116x_of_remove(struct platform_device *op) ++{ ++ struct usb_hcd *hcd = dev_get_drvdata(&op->dev); ++ struct isp116x *isp116x; ++ struct resource res; ++ ++ if (!hcd) ++ return 0; ++ ++ dev_set_drvdata(&op->dev, NULL); ++ ++ isp116x = hcd_to_isp116x(hcd); ++ remove_debug_file(isp116x); ++ usb_remove_hcd(hcd); ++ ++ irq_dispose_mapping(hcd->irq); ++ ++ iounmap(isp116x->data_reg); ++ (void) of_address_to_resource(op->dev.of_node, 0, &res); ++ release_mem_region(res.start, resource_size(&res)); ++ ++ iounmap(isp116x->addr_reg); ++ (void) of_address_to_resource(op->dev.of_node, 1, &res); ++ release_mem_region(res.start, resource_size(&res)); ++ ++ kfree(isp116x->board); ++ usb_put_hcd(hcd); ++ ++ return 0; ++} ++ ++static struct of_device_id isp116x_of_match[] = { ++ { .compatible = "isp116x-hcd", }, ++ {}, ++}; ++ ++static struct platform_driver isp116x_of_platform_driver = { ++ .probe = isp116x_of_probe, ++ .remove = isp116x_of_remove, ++ .driver = { ++ .name = "isp116x-hcd-of", ++ .owner = THIS_MODULE, ++ .of_match_table = isp116x_of_match, ++ }, ++}; ++ ++static int __init isp116x_of_register(void) ++{ ++ return platform_driver_register(&isp116x_of_platform_driver); ++} ++ ++static void __exit isp116x_of_unregister(void) ++{ ++ platform_driver_unregister(&isp116x_of_platform_driver); ++} ++ ++MODULE_DEVICE_TABLE(of, isp116x_of_match); ++ ++#else ++static inline int isp116x_of_register(void) { return 0; }; ++static void isp116x_of_unregister(void) {}; ++#endif /* CONFIG_USB_ISP116X_HCD_OF */ ++ ++/*-----------------------------------------------------------------*/ ++ ++static int __init isp116x_init(void) ++{ ++ int ret; ++ ++ if (usb_disabled()) ++ return -ENODEV; ++ ++ INFO("driver %s, %s\n", hcd_name, DRIVER_VERSION); ++ ret = isp116x_platform_register(); ++ if (ret) ++ return ret; ++ ++ ret = isp116x_of_register(); ++ if (ret) ++ goto err_platform_unregister; ++ ++ return 0; ++ ++ err_platform_unregister: ++ isp116x_platform_unregister(); ++ return ret; ++} ++ ++module_init(isp116x_init); ++ ++static void __exit isp116x_cleanup(void) ++{ ++ isp116x_of_unregister(); ++ isp116x_platform_unregister(); ++} ++ ++module_exit(isp116x_cleanup); +--- a/drivers/usb/host/Kconfig ++++ b/drivers/usb/host/Kconfig +@@ -320,6 +320,24 @@ config USB_ISP116X_HCD + To compile this driver as a module, choose M here: the + module will be called isp116x-hcd. + ++config USB_ISP116X_HCD_PLATFORM ++ bool "ISP116X support for controllers on platform bus" ++ depends on USB_ISP116X_HCD ++ default n if PPC_OF ++ default y ++ ---help--- ++ Enables support for the ISP116x USB controller present on the ++ platform bus. ++ ++config USB_ISP116X_HCD_OF ++ bool "ISP116X support for controllers on OF platform bus" ++ depends on USB_ISP116X_HCD && PPC_OF ++ default y if PPC_OF ++ default n ++ ---help--- ++ Enables support for the ISP116x USB controller present on the ++ OpenFirmware platform bus. ++ + config USB_ISP1760_HCD + tristate "ISP 1760 HCD support" + ---help--- diff --git a/target/linux/ppc40x/patches-3.10/121-usb-isp116x-hcd-ppc405-register-access.patch b/target/linux/ppc40x/patches-3.10/121-usb-isp116x-hcd-ppc405-register-access.patch new file mode 100644 index 0000000000..e124e06746 --- /dev/null +++ b/target/linux/ppc40x/patches-3.10/121-usb-isp116x-hcd-ppc405-register-access.patch @@ -0,0 +1,111 @@ +--- a/drivers/usb/host/isp116x.h ++++ b/drivers/usb/host/isp116x.h +@@ -364,22 +364,64 @@ struct isp116x_ep { + #define IRQ_TEST() do{}while(0) + #endif + ++#ifdef CONFIG_PPC ++static inline void isp116x_writew(u16 val, void __iomem *addr) ++{ ++ writew(cpu_to_le16(val), addr); ++} ++ ++static inline u16 isp116x_readw(void __iomem *addr) ++{ ++ return le16_to_cpu(readw(addr)); ++} ++ ++static inline void isp116x_raw_writew(u16 val, void __iomem *addr) ++{ ++ writew(cpu_to_le16(val), addr); ++} ++ ++static inline u16 isp116x_raw_readw(void __iomem *addr) ++{ ++ return le16_to_cpu(readw(addr)); ++} ++#else ++static inline void isp116x_writew(u16 val, void __iomem *addr) ++{ ++ writew(val, addr); ++} ++ ++static inline u16 isp116x_readw(void __iomem *addr) ++{ ++ return readw(addr); ++} ++ ++static inline void isp116x_raw_writew(u16 val, void __iomem *addr) ++{ ++ __raw_writew(val, addr); ++} ++ ++static inline u16 isp116x_raw_readw(void __iomem *addr) ++{ ++ return __raw_readw(addr); ++} ++#endif ++ + static inline void isp116x_write_addr(struct isp116x *isp116x, unsigned reg) + { + IRQ_TEST(); +- writew(reg & 0xff, isp116x->addr_reg); ++ isp116x_writew(reg & 0xff, isp116x->addr_reg); + isp116x_delay(isp116x, 300); + } + + static inline void isp116x_write_data16(struct isp116x *isp116x, u16 val) + { +- writew(val, isp116x->data_reg); ++ isp116x_writew(val, isp116x->data_reg); + isp116x_delay(isp116x, 150); + } + + static inline void isp116x_raw_write_data16(struct isp116x *isp116x, u16 val) + { +- __raw_writew(val, isp116x->data_reg); ++ isp116x_raw_writew(val, isp116x->data_reg); + isp116x_delay(isp116x, 150); + } + +@@ -387,7 +429,7 @@ static inline u16 isp116x_read_data16(st + { + u16 val; + +- val = readw(isp116x->data_reg); ++ val = isp116x_readw(isp116x->data_reg); + isp116x_delay(isp116x, 150); + return val; + } +@@ -396,16 +438,16 @@ static inline u16 isp116x_raw_read_data1 + { + u16 val; + +- val = __raw_readw(isp116x->data_reg); ++ val = isp116x_raw_readw(isp116x->data_reg); + isp116x_delay(isp116x, 150); + return val; + } + + static inline void isp116x_write_data32(struct isp116x *isp116x, u32 val) + { +- writew(val & 0xffff, isp116x->data_reg); ++ isp116x_writew(val & 0xffff, isp116x->data_reg); + isp116x_delay(isp116x, 150); +- writew(val >> 16, isp116x->data_reg); ++ isp116x_writew(val >> 16, isp116x->data_reg); + isp116x_delay(isp116x, 150); + } + +@@ -413,9 +455,9 @@ static inline u32 isp116x_read_data32(st + { + u32 val; + +- val = (u32) readw(isp116x->data_reg); ++ val = (u32) isp116x_readw(isp116x->data_reg); + isp116x_delay(isp116x, 150); +- val |= ((u32) readw(isp116x->data_reg)) << 16; ++ val |= ((u32) isp116x_readw(isp116x->data_reg)) << 16; + isp116x_delay(isp116x, 150); + return val; + } |