From 2099172d61abda1b793b499bb8edcaac4de2cdae Mon Sep 17 00:00:00 2001 From: David Gibson Date: Fri, 7 Sep 2007 13:23:53 +1000 Subject: [POWERPC] Document and implement an improved flash device binding for powerpc This replaces the binding for flash chips in booting-without-of.txt with an clarified and improved version. It also makes drivers/mtd/maps/physmap_of.c recognize this new binding. Finally it revises the Ebony device tree source to use the new binding as an example. Signed-off-by: David Gibson Acked-by: Segher Boessenkool Signed-off-by: Paul Mackerras --- Documentation/powerpc/booting-without-of.txt | 92 ++++++++++++++++++---------- 1 file changed, 58 insertions(+), 34 deletions(-) (limited to 'Documentation/powerpc') diff --git a/Documentation/powerpc/booting-without-of.txt b/Documentation/powerpc/booting-without-of.txt index 76733a3962f..20e0e6cb034 100644 --- a/Documentation/powerpc/booting-without-of.txt +++ b/Documentation/powerpc/booting-without-of.txt @@ -50,7 +50,7 @@ Table of Contents g) Freescale SOC SEC Security Engines h) Board Control and Status (BCSR) i) Freescale QUICC Engine module (QE) - j) Flash chip nodes + j) CFI or JEDEC memory-mapped NOR flash k) Global Utilities Block VII - Specifying interrupt information for devices @@ -1757,45 +1757,69 @@ platforms are moved over to use the flattened-device-tree model. }; }; - j) Flash chip nodes + j) CFI or JEDEC memory-mapped NOR flash Flash chips (Memory Technology Devices) are often used for solid state file systems on embedded devices. - Required properties: + - compatible : should contain the specific model of flash chip(s) + used, if known, followed by either "cfi-flash" or "jedec-flash" + - reg : Address range of the flash chip + - bank-width : Width (in bytes) of the flash bank. Equal to the + device width times the number of interleaved chips. + - device-width : (optional) Width of a single flash chip. If + omitted, assumed to be equal to 'bank-width'. + - #address-cells, #size-cells : Must be present if the flash has + sub-nodes representing partitions (see below). In this case + both #address-cells and #size-cells must be equal to 1. + + For JEDEC compatible devices, the following additional properties + are defined: + + - vendor-id : Contains the flash chip's vendor id (1 byte). + - device-id : Contains the flash chip's device id (1 byte). + + In addition to the information on the flash bank itself, the + device tree may optionally contain additional information + describing partitions of the flash address space. This can be + used on platforms which have strong conventions about which + portions of the flash are used for what purposes, but which don't + use an on-flash partition table such as RedBoot. + + Each partition is represented as a sub-node of the flash device. + Each node's name represents the name of the corresponding + partition of the flash device. + + Flash partitions + - reg : The partition's offset and size within the flash bank. + - label : (optional) The label / name for this flash partition. + If omitted, the label is taken from the node name (excluding + the unit address). + - read-only : (optional) This parameter, if present, is a hint to + Linux that this flash partition should only be mounted + read-only. This is usually used for flash partitions + containing early-boot firmware images or data which should not + be clobbered. - - device_type : has to be "rom" - - compatible : Should specify what this flash device is compatible with. - Currently, this is most likely to be "direct-mapped" (which - corresponds to the MTD physmap mapping driver). - - reg : Offset and length of the register set (or memory mapping) for - the device. - - bank-width : Width of the flash data bus in bytes. Required - for the NOR flashes (compatible == "direct-mapped" and others) ONLY. - - Recommended properties : - - - partitions : Several pairs of 32-bit values where the first value is - partition's offset from the start of the device and the second one is - partition size in bytes with LSB used to signify a read only - partition (so, the partition size should always be an even number). - - partition-names : The list of concatenated zero terminated strings - representing the partition names. - - probe-type : The type of probe which should be done for the chip - (JEDEC vs CFI actually). Valid ONLY for NOR flashes. - - Example: + Example: - flash@ff000000 { - device_type = "rom"; - compatible = "direct-mapped"; - probe-type = "CFI"; - reg = ; - bank-width = <4>; - partitions = <00000000 00f80000 - 00f80000 00080001>; - partition-names = "fs\0firmware"; - }; + flash@ff000000 { + compatible = "amd,am29lv128ml", "cfi-flash"; + reg = ; + bank-width = <4>; + device-width = <1>; + #address-cells = <1>; + #size-cells = <1>; + fs@0 { + label = "fs"; + reg = <0 f80000>; + }; + firmware@f80000 { + label ="firmware"; + reg = ; + read-only; + }; + }; k) Global Utilities Block -- cgit v1.2.3-70-g09d2 From e631ae3b164158fbf486fbed5adb597696c4f0e5 Mon Sep 17 00:00:00 2001 From: Scott Wood Date: Fri, 14 Sep 2007 13:04:54 -0500 Subject: [POWERPC] Introduce new CPM device bindings. This introduces a new device binding for the CPM and other devices on these boards. Some of the changes include: 1. Proper namespace scoping for Freescale compatibles and properties. 2. Use compatible rather than things like device_type and model to determine which particular variant of a device is present. 3. Give the drivers the relevant CPM command word directly, rather than requiring it to have a lookup table based on device-id, SCC v. SMC, and CPM version. 4. Specify the CPCR and the usable DPRAM region in the CPM's reg property. Boards that do not require the legacy bindings should select CONFIG_PPC_CPM_NEW_BINDING to enable the of_platform CPM devices. Once all existing boards are converted and tested, the config option can become default y to prevent new boards from using the old model. Once arch/ppc is gone, the config option can be removed altogether. Signed-off-by: Scott Wood Acked-by: David Gibson Signed-off-by: Kumar Gala --- Documentation/powerpc/booting-without-of.txt | 171 ++++++++++++++++++++++++++- arch/powerpc/platforms/Kconfig | 11 ++ arch/powerpc/sysdev/fsl_soc.c | 2 + 3 files changed, 183 insertions(+), 1 deletion(-) (limited to 'Documentation/powerpc') diff --git a/Documentation/powerpc/booting-without-of.txt b/Documentation/powerpc/booting-without-of.txt index 20e0e6cb034..a599f1a8a14 100644 --- a/Documentation/powerpc/booting-without-of.txt +++ b/Documentation/powerpc/booting-without-of.txt @@ -1510,7 +1510,10 @@ platforms are moved over to use the flattened-device-tree model. i) Freescale QUICC Engine module (QE) This represents qe module that is installed on PowerQUICC II Pro. - Hopefully it will merge backward compatibility with CPM/CPM2. + + NOTE: This is an interim binding; it should be updated to fit + in with the CPM binding later in this document. + Basically, it is a bus of devices, that could act more or less as a complete entity (UCC, USB etc ). All of them should be siblings on the "root" qe node, using the common properties from there. @@ -1848,6 +1851,172 @@ platforms are moved over to use the flattened-device-tree model. fsl,has-rstcr; }; + l) Freescale Communications Processor Module + + NOTE: This is an interim binding, and will likely change slightly, + as more devices are supported. The QE bindings especially are + incomplete. + + i) Root CPM node + + Properties: + - compatible : "fsl,cpm1", "fsl,cpm2", or "fsl,qe". + - reg : The first resource is a 48-byte region beginning with + CPCR. The second is the available general-purpose + DPRAM. + + Example: + cpm@119c0 { + #address-cells = <1>; + #size-cells = <1>; + #interrupt-cells = <2>; + compatible = "fsl,mpc8272-cpm", "fsl,cpm2"; + reg = <119c0 30 0 2000>; + } + + ii) Properties common to mulitple CPM/QE devices + + - fsl,cpm-command : This value is ORed with the opcode and command flag + to specify the device on which a CPM command operates. + + - fsl,cpm-brg : Indicates which baud rate generator the device + is associated with. If absent, an unused BRG + should be dynamically allocated. If zero, the + device uses an external clock rather than a BRG. + + - reg : Unless otherwise specified, the first resource represents the + scc/fcc/ucc registers, and the second represents the device's + parameter RAM region (if it has one). + + iii) Serial + + Currently defined compatibles: + - fsl,cpm1-smc-uart + - fsl,cpm2-smc-uart + - fsl,cpm1-scc-uart + - fsl,cpm2-scc-uart + - fsl,qe-uart + + Example: + + serial@11a00 { + device_type = "serial"; + compatible = "fsl,mpc8272-scc-uart", + "fsl,cpm2-scc-uart"; + reg = <11a00 20 8000 100>; + interrupts = <28 8>; + interrupt-parent = <&PIC>; + fsl,cpm-brg = <1>; + fsl,cpm-command = <00800000>; + }; + + iii) Network + + Currently defined compatibles: + - fsl,cpm1-scc-enet + - fsl,cpm2-scc-enet + - fsl,cpm1-fec-enet + - fsl,cpm2-fcc-enet (third resource is GFEMR) + - fsl,qe-enet + + Example: + + ethernet@11300 { + device_type = "network"; + compatible = "fsl,mpc8272-fcc-enet", + "fsl,cpm2-fcc-enet"; + reg = <11300 20 8400 100 11390 1>; + local-mac-address = [ 00 00 00 00 00 00 ]; + interrupts = <20 8>; + interrupt-parent = <&PIC>; + phy-handle = <&PHY0>; + linux,network-index = <0>; + fsl,cpm-command = <12000300>; + }; + + iv) MDIO + + Currently defined compatibles: + fsl,pq1-fec-mdio (reg is same as first resource of FEC device) + fsl,cpm2-mdio-bitbang (reg is port C registers) + + Properties for fsl,cpm2-mdio-bitbang: + fsl,mdio-pin : pin of port C controlling mdio data + fsl,mdc-pin : pin of port C controlling mdio clock + + Example: + + mdio@10d40 { + device_type = "mdio"; + compatible = "fsl,mpc8272ads-mdio-bitbang", + "fsl,mpc8272-mdio-bitbang", + "fsl,cpm2-mdio-bitbang"; + reg = <10d40 14>; + #address-cells = <1>; + #size-cells = <0>; + fsl,mdio-pin = <12>; + fsl,mdc-pin = <13>; + }; + + v) Baud Rate Generators + + Currently defined compatibles: + fsl,cpm-brg + fsl,cpm1-brg + fsl,cpm2-brg + + Properties: + - reg : There may be an arbitrary number of reg resources; BRG + numbers are assigned to these in order. + - clock-frequency : Specifies the base frequency driving + the BRG. + + Example: + + brg@119f0 { + compatible = "fsl,mpc8272-brg", + "fsl,cpm2-brg", + "fsl,cpm-brg"; + reg = <119f0 10 115f0 10>; + clock-frequency = ; + }; + + vi) Interrupt Controllers + + Currently defined compatibles: + - fsl,cpm1-pic + - only one interrupt cell + - fsl,pq1-pic + - fsl,cpm2-pic + - second interrupt cell is level/sense: + - 2 is falling edge + - 8 is active low + + Example: + + interrupt-controller@10c00 { + #interrupt-cells = <2>; + interrupt-controller; + reg = <10c00 80>; + compatible = "mpc8272-pic", "fsl,cpm2-pic"; + }; + + vii) USB (Universal Serial Bus Controller) + + Properties: + - compatible : "fsl,cpm1-usb", "fsl,cpm2-usb", "fsl,qe-usb" + + Example: + usb@11bc0 { + #address-cells = <1>; + #size-cells = <0>; + compatible = "fsl,cpm2-usb"; + reg = <11b60 18 8b00 100>; + interrupts = ; + interrupt-parent = <&PIC>; + fsl,cpm-command = <2e600000>; + }; + More devices will be defined as this spec matures. VII - Specifying interrupt information for devices diff --git a/arch/powerpc/platforms/Kconfig b/arch/powerpc/platforms/Kconfig index 92fcd6e35b5..8a62ca533b3 100644 --- a/arch/powerpc/platforms/Kconfig +++ b/arch/powerpc/platforms/Kconfig @@ -279,6 +279,17 @@ config CPM2 you wish to build a kernel for a machine with a CPM2 coprocessor on it (826x, 827x, 8560). +config PPC_CPM_NEW_BINDING + bool + depends on CPM1 || CPM2 + help + Select this if your board has been converted to use the new + device tree bindings for CPM, and no longer needs the + ioport callbacks or the platform device glue code. + + The fs_enet and cpm_uart drivers will be built as + of_platform devices. + config AXON_RAM tristate "Axon DDR2 memory device driver" depends on PPC_IBM_CELL_BLADE diff --git a/arch/powerpc/sysdev/fsl_soc.c b/arch/powerpc/sysdev/fsl_soc.c index 30523667df4..b465b30c954 100644 --- a/arch/powerpc/sysdev/fsl_soc.c +++ b/arch/powerpc/sysdev/fsl_soc.c @@ -665,6 +665,7 @@ err: arch_initcall(fsl_usb_of_init); +#ifndef CONFIG_PPC_CPM_NEW_BINDING #ifdef CONFIG_CPM2 extern void init_scc_ioports(struct fs_uart_platform_info*); @@ -1204,6 +1205,7 @@ err: arch_initcall(cpm_smc_uart_of_init); #endif /* CONFIG_8xx */ +#endif /* CONFIG_PPC_CPM_NEW_BINDING */ int __init fsl_spi_init(struct spi_board_info *board_infos, unsigned int num_board_infos, -- cgit v1.2.3-70-g09d2 From 96fca1dea8f32e96668d55727d66416fdd67360b Mon Sep 17 00:00:00 2001 From: Scott Wood Date: Fri, 14 Sep 2007 13:24:02 -0500 Subject: [POWERPC] Document local bus nodes in the device tree, and update cuboot-pq2. The localbus node is used to describe devices that are connected via a chip select or similar mechanism. The advantages over placing the devices under the root node are that it can be probed without probing other random things under the root, and that the description of which chip select a given device uses can be used to set up mappings if the firmware failed to do so in a useful manner. cuboot-pq2 is updated to match the binding; previously, it called itself chipselect rather than localbus, and used phandle linkage between the actual bus node and the control node (the current agreement is to simply use the fully-qualified address of the control registers, and ignore the overlap with the IMMR node). Signed-off-by: Scott Wood Signed-off-by: Kumar Gala --- Documentation/powerpc/booting-without-of.txt | 38 ++++++++++++++++++++++++++++ arch/powerpc/boot/cuboot-pq2.c | 29 ++++++--------------- 2 files changed, 46 insertions(+), 21 deletions(-) (limited to 'Documentation/powerpc') diff --git a/Documentation/powerpc/booting-without-of.txt b/Documentation/powerpc/booting-without-of.txt index a599f1a8a14..c36dcd2fbdc 100644 --- a/Documentation/powerpc/booting-without-of.txt +++ b/Documentation/powerpc/booting-without-of.txt @@ -2017,6 +2017,44 @@ platforms are moved over to use the flattened-device-tree model. fsl,cpm-command = <2e600000>; }; + m) Chipselect/Local Bus + + Properties: + - name : Should be localbus + - #address-cells : Should be either two or three. The first cell is the + chipselect number, and the remaining cells are the + offset into the chipselect. + - #size-cells : Either one or two, depending on how large each chipselect + can be. + - ranges : Each range corresponds to a single chipselect, and cover + the entire access window as configured. + + Example: + localbus@f0010100 { + compatible = "fsl,mpc8272ads-localbus", + "fsl,mpc8272-localbus", + "fsl,pq2-localbus"; + #address-cells = <2>; + #size-cells = <1>; + reg = ; + + ranges = <0 0 fe000000 02000000 + 1 0 f4500000 00008000>; + + flash@0,0 { + compatible = "jedec-flash"; + reg = <0 0 2000000>; + bank-width = <4>; + device-width = <1>; + }; + + board-control@1,0 { + reg = <1 0 20>; + compatible = "fsl,mpc8272ads-bcsr"; + }; + }; + + More devices will be defined as this spec matures. VII - Specifying interrupt information for devices diff --git a/arch/powerpc/boot/cuboot-pq2.c b/arch/powerpc/boot/cuboot-pq2.c index 470ffacb837..61574f3272d 100644 --- a/arch/powerpc/boot/cuboot-pq2.c +++ b/arch/powerpc/boot/cuboot-pq2.c @@ -44,22 +44,21 @@ struct pci_range pci_ranges_buf[MAX_PROP_LEN / sizeof(struct pci_range)]; * some don't set up the PCI PIC at all, so we assume the device tree is * sane and update the BRx registers appropriately. * - * For any node defined as compatible with fsl,pq2-chipselect, - * #address/#size must be 2/1 for chipselect bus, 1/1 for parent bus, - * and ranges must be for whole chip selects. + * For any node defined as compatible with fsl,pq2-localbus, + * #address/#size must be 2/1 for the localbus, and 1/1 for the parent bus. + * Ranges must be for whole chip selects. */ static void update_cs_ranges(void) { - u32 ctrl_ph; - void *ctrl_node, *bus_node, *parent_node; + void *bus_node, *parent_node; u32 *ctrl_addr; unsigned long ctrl_size; u32 naddr, nsize; int len; int i; - bus_node = finddevice("/chipselect"); - if (!bus_node || !dt_is_compatible(bus_node, "fsl,pq2-chipselect")) + bus_node = finddevice("/localbus"); + if (!bus_node || !dt_is_compatible(bus_node, "fsl,pq2-localbus")) return; dt_get_reg_format(bus_node, &naddr, &nsize); @@ -74,19 +73,7 @@ static void update_cs_ranges(void) if (naddr != 1 || nsize != 1) goto err; - len = getprop(bus_node, "fsl,ctrl", &ctrl_ph, 4); - if (len != 4) - goto err; - - ctrl_node = find_node_by_prop_value(NULL, "linux,phandle", - (char *)&ctrl_ph, 4); - if (!ctrl_node) - goto err; - - if (!dt_is_compatible(ctrl_node, "fsl,pq2-chipselect-ctrl")) - goto err; - - if (!dt_xlate_reg(ctrl_node, 0, (unsigned long *)&ctrl_addr, + if (!dt_xlate_reg(bus_node, 0, (unsigned long *)&ctrl_addr, &ctrl_size)) goto err; @@ -123,7 +110,7 @@ static void update_cs_ranges(void) return; err: - printf("Bad /chipselect or fsl,pq2-chipselect-ctrl node\r\n"); + printf("Bad /localbus node\r\n"); } /* Older u-boots don't set PCI up properly. Update the hardware to match -- cgit v1.2.3-70-g09d2 From 15f8c604a79c4840ed76eecf3af5d88b7c1dee9e Mon Sep 17 00:00:00 2001 From: Scott Wood Date: Fri, 28 Sep 2007 14:06:16 -0500 Subject: [POWERPC] cpm: Describe multi-user ram in its own device node. The way the current CPM binding describes available multi-user (a.k.a. dual-ported) RAM doesn't work well when there are multiple free regions, and it doesn't work at all if the region doesn't begin at the start of the muram area (as the hardware needs to be programmed with offsets into this area). The latter situation can happen with SMC UARTs on CPM2, as its parameter RAM is relocatable, u-boot puts it at zero, and the kernel doesn't support moving it. It is now described with a muram node, similar to QE. The current CPM binding is sufficiently recent (i.e. never appeared in an official release) that compatibility with existing device trees is not an issue. The code supporting the new binding is shared between cpm1 and cpm2, rather than remain separated. QE should be able to use this code as well, once minor fixes are made to its device trees. Signed-off-by: Scott Wood Signed-off-by: Kumar Gala --- Documentation/powerpc/booting-without-of.txt | 40 ++++++- arch/powerpc/Kconfig.debug | 6 +- arch/powerpc/boot/cpm-serial.c | 44 ++++++-- arch/powerpc/boot/dts/ep88xc.dts | 13 ++- arch/powerpc/boot/dts/mpc8272ads.dts | 11 ++ arch/powerpc/boot/dts/mpc885ads.dts | 13 ++- arch/powerpc/boot/dts/pq2fads.dts | 13 ++- arch/powerpc/sysdev/commproc.c | 11 +- arch/powerpc/sysdev/cpm2_common.c | 35 ++---- arch/powerpc/sysdev/cpm_common.c | 159 +++++++++++++++++++++++++++ drivers/serial/cpm_uart/cpm_uart_cpm2.c | 4 +- include/asm-powerpc/commproc.h | 12 ++ include/asm-powerpc/cpm.h | 14 +++ include/asm-powerpc/cpm2.h | 10 ++ 14 files changed, 337 insertions(+), 48 deletions(-) create mode 100644 include/asm-powerpc/cpm.h (limited to 'Documentation/powerpc') diff --git a/Documentation/powerpc/booting-without-of.txt b/Documentation/powerpc/booting-without-of.txt index c36dcd2fbdc..ce5d67f5cb5 100644 --- a/Documentation/powerpc/booting-without-of.txt +++ b/Documentation/powerpc/booting-without-of.txt @@ -1861,9 +1861,7 @@ platforms are moved over to use the flattened-device-tree model. Properties: - compatible : "fsl,cpm1", "fsl,cpm2", or "fsl,qe". - - reg : The first resource is a 48-byte region beginning with - CPCR. The second is the available general-purpose - DPRAM. + - reg : A 48-byte region beginning with CPCR. Example: cpm@119c0 { @@ -1871,7 +1869,7 @@ platforms are moved over to use the flattened-device-tree model. #size-cells = <1>; #interrupt-cells = <2>; compatible = "fsl,mpc8272-cpm", "fsl,cpm2"; - reg = <119c0 30 0 2000>; + reg = <119c0 30>; } ii) Properties common to mulitple CPM/QE devices @@ -2017,6 +2015,40 @@ platforms are moved over to use the flattened-device-tree model. fsl,cpm-command = <2e600000>; }; + viii) Multi-User RAM (MURAM) + + The multi-user/dual-ported RAM is expressed as a bus under the CPM node. + + Ranges must be set up subject to the following restrictions: + + - Children's reg nodes must be offsets from the start of all muram, even + if the user-data area does not begin at zero. + - If multiple range entries are used, the difference between the parent + address and the child address must be the same in all, so that a single + mapping can cover them all while maintaining the ability to determine + CPM-side offsets with pointer subtraction. It is recommended that + multiple range entries not be used. + - A child address of zero must be translatable, even if no reg resources + contain it. + + A child "data" node must exist, compatible with "fsl,cpm-muram-data", to + indicate the portion of muram that is usable by the OS for arbitrary + purposes. The data node may have an arbitrary number of reg resources, + all of which contribute to the allocatable muram pool. + + Example, based on mpc8272: + + muram@0 { + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0 10000>; + + data@0 { + compatible = "fsl,cpm-muram-data"; + reg = <0 2000 9800 800>; + }; + }; + m) Chipselect/Local Bus Properties: diff --git a/arch/powerpc/Kconfig.debug b/arch/powerpc/Kconfig.debug index f4e5d22312a..464f9b4b316 100644 --- a/arch/powerpc/Kconfig.debug +++ b/arch/powerpc/Kconfig.debug @@ -245,9 +245,9 @@ config PPC_EARLY_DEBUG_44x_PHYSHIGH config PPC_EARLY_DEBUG_CPM_ADDR hex "CPM UART early debug transmit descriptor address" depends on PPC_EARLY_DEBUG_CPM - default "0xfa202808" if PPC_EP88XC - default "0xf0000808" if CPM2 - default "0xff002808" if CPM1 + default "0xfa202008" if PPC_EP88XC + default "0xf0000008" if CPM2 + default "0xff002008" if CPM1 help This specifies the address of the transmit descriptor used for early debug output. Because it is needed before diff --git a/arch/powerpc/boot/cpm-serial.c b/arch/powerpc/boot/cpm-serial.c index fcb8b5e956b..28296facb2a 100644 --- a/arch/powerpc/boot/cpm-serial.c +++ b/arch/powerpc/boot/cpm-serial.c @@ -56,7 +56,8 @@ static struct cpm_smc *smc; static struct cpm_scc *scc; struct cpm_bd *tbdf, *rbdf; static u32 cpm_cmd; -static u8 *dpram_start; +static u8 *muram_start; +static u32 muram_offset; static void (*do_cmd)(int op); static void (*enable_port)(void); @@ -114,13 +115,12 @@ static void scc_enable_port(void) static int cpm_serial_open(void) { - int dpaddr = 0x800; disable_port(); out_8(¶m->rfcr, 0x10); out_8(¶m->tfcr, 0x10); - rbdf = (struct cpm_bd *)(dpram_start + dpaddr); + rbdf = (struct cpm_bd *)muram_start; rbdf->addr = (u8 *)(rbdf + 2); rbdf->sc = 0xa000; rbdf->len = 1; @@ -131,8 +131,8 @@ static int cpm_serial_open(void) tbdf->len = 1; sync(); - out_be16(¶m->rbase, dpaddr); - out_be16(¶m->tbase, dpaddr + sizeof(struct cpm_bd)); + out_be16(¶m->rbase, muram_offset); + out_be16(¶m->tbase, muram_offset + sizeof(struct cpm_bd)); do_cmd(CPM_CMD_INIT_RX_TX); @@ -178,7 +178,7 @@ int cpm_console_init(void *devp, struct serial_console_data *scdp) void *reg_virt[2]; int is_smc = 0, is_cpm2 = 0, n; unsigned long reg_phys; - void *parent; + void *parent, *muram; if (dt_is_compatible(devp, "fsl,cpm1-smc-uart")) { is_smc = 1; @@ -229,16 +229,36 @@ int cpm_console_init(void *devp, struct serial_console_data *scdp) n = getprop(parent, "virtual-reg", reg_virt, sizeof(reg_virt)); if (n < (int)sizeof(reg_virt)) { - for (n = 0; n < 2; n++) { - if (!dt_xlate_reg(parent, n, ®_phys, NULL)) - return -1; + if (!dt_xlate_reg(parent, 0, ®_phys, NULL)) + return -1; - reg_virt[n] = (void *)reg_phys; - } + reg_virt[0] = (void *)reg_phys; } cpcr = reg_virt[0]; - dpram_start = reg_virt[1]; + + muram = finddevice("/soc/cpm/muram/data"); + if (!muram) + return -1; + + /* For bootwrapper-compatible device trees, we assume that the first + * entry has at least 18 bytes, and that #address-cells/#data-cells + * is one for both parent and child. + */ + + n = getprop(muram, "virtual-reg", reg_virt, sizeof(reg_virt)); + if (n < (int)sizeof(reg_virt)) { + if (!dt_xlate_reg(muram, 0, ®_phys, NULL)) + return -1; + + reg_virt[0] = (void *)reg_phys; + } + + muram_start = reg_virt[0]; + + n = getprop(muram, "reg", &muram_offset, 4); + if (n < 4) + return -1; scdp->open = cpm_serial_open; scdp->putc = cpm_serial_putc; diff --git a/arch/powerpc/boot/dts/ep88xc.dts b/arch/powerpc/boot/dts/ep88xc.dts index 0406fc50b2a..02705f29979 100644 --- a/arch/powerpc/boot/dts/ep88xc.dts +++ b/arch/powerpc/boot/dts/ep88xc.dts @@ -142,9 +142,20 @@ command-proc = <9c0>; interrupts = <0>; // cpm error interrupt interrupt-parent = <&CPM_PIC>; - reg = <9c0 40 2000 1c00>; + reg = <9c0 40>; ranges; + muram@2000 { + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 2000 2000>; + + data@0 { + compatible = "fsl,cpm-muram-data"; + reg = <0 1c00>; + }; + }; + brg@9f0 { compatible = "fsl,mpc885-brg", "fsl,cpm1-brg", diff --git a/arch/powerpc/boot/dts/mpc8272ads.dts b/arch/powerpc/boot/dts/mpc8272ads.dts index 3fe991d4cb0..188179df084 100644 --- a/arch/powerpc/boot/dts/mpc8272ads.dts +++ b/arch/powerpc/boot/dts/mpc8272ads.dts @@ -124,6 +124,17 @@ reg = <119c0 30 0 2000>; ranges; + muram@0 { + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0 10000>; + + data@0 { + compatible = "fsl,cpm-muram-data"; + reg = <0 2000 9800 800>; + }; + }; + brg@119f0 { compatible = "fsl,mpc8272-brg", "fsl,cpm2-brg", diff --git a/arch/powerpc/boot/dts/mpc885ads.dts b/arch/powerpc/boot/dts/mpc885ads.dts index cbcd16f74c4..8848e637293 100644 --- a/arch/powerpc/boot/dts/mpc885ads.dts +++ b/arch/powerpc/boot/dts/mpc885ads.dts @@ -148,9 +148,20 @@ command-proc = <9c0>; interrupts = <0>; // cpm error interrupt interrupt-parent = <&CPM_PIC>; - reg = <9c0 40 2000 1c00>; + reg = <9c0 40>; ranges; + muram@2000 { + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 2000 2000>; + + data@0 { + compatible = "fsl,cpm-muram-data"; + reg = <0 1c00>; + }; + }; + brg@9f0 { compatible = "fsl,mpc885-brg", "fsl,cpm1-brg", diff --git a/arch/powerpc/boot/dts/pq2fads.dts b/arch/powerpc/boot/dts/pq2fads.dts index 54e8bd1ae22..2d564921897 100644 --- a/arch/powerpc/boot/dts/pq2fads.dts +++ b/arch/powerpc/boot/dts/pq2fads.dts @@ -119,9 +119,20 @@ #size-cells = <1>; #interrupt-cells = <2>; compatible = "fsl,mpc8280-cpm", "fsl,cpm2"; - reg = <119c0 30 0 2000>; + reg = <119c0 30>; ranges; + muram@0 { + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0 10000>; + + data@0 { + compatible = "fsl,cpm-muram-data"; + reg = <0 2000 9800 800>; + }; + }; + brg@119f0 { compatible = "fsl,mpc8280-brg", "fsl,cpm2-brg", diff --git a/arch/powerpc/sysdev/commproc.c b/arch/powerpc/sysdev/commproc.c index 428eb8c151b..f6a63780bbd 100644 --- a/arch/powerpc/sysdev/commproc.c +++ b/arch/powerpc/sysdev/commproc.c @@ -39,12 +39,15 @@ #include #include #include +#include #include #define CPM_MAP_SIZE (0x4000) +#ifndef CONFIG_PPC_CPM_NEW_BINDING static void m8xx_cpm_dpinit(void); +#endif static uint host_buffer; /* One page of host buffer */ static uint host_end; /* end + 1 */ cpm8xx_t __iomem *cpmp; /* Pointer to comm processor space */ @@ -193,7 +196,7 @@ end: return sirq; } -void cpm_reset(void) +void __init cpm_reset(void) { sysconf8xx_t __iomem *siu_conf; @@ -229,8 +232,12 @@ void cpm_reset(void) out_be32(&siu_conf->sc_sdcr, 1); immr_unmap(siu_conf); +#ifdef CONFIG_PPC_CPM_NEW_BINDING + cpm_muram_init(); +#else /* Reclaim the DP memory for our use. */ m8xx_cpm_dpinit(); +#endif } /* We used to do this earlier, but have to postpone as long as possible @@ -296,6 +303,7 @@ cpm_setbrg(uint brg, uint rate) CPM_BRG_EN | CPM_BRG_DIV16); } +#ifndef CONFIG_PPC_CPM_NEW_BINDING /* * dpalloc / dpfree bits. */ @@ -397,6 +405,7 @@ uint cpm_dpram_phys(u8 *addr) return (dpram_pbase + (uint)(addr - dpram_vbase)); } EXPORT_SYMBOL(cpm_dpram_phys); +#endif /* !CONFIG_PPC_CPM_NEW_BINDING */ struct cpm_ioport16 { __be16 dir, par, sor, dat, intr; diff --git a/arch/powerpc/sysdev/cpm2_common.c b/arch/powerpc/sysdev/cpm2_common.c index fc4c9956538..859362fecb7 100644 --- a/arch/powerpc/sysdev/cpm2_common.c +++ b/arch/powerpc/sysdev/cpm2_common.c @@ -46,7 +46,10 @@ #include +#ifndef CONFIG_PPC_CPM_NEW_BINDING static void cpm2_dpinit(void); +#endif + cpm_cpm2_t __iomem *cpmp; /* Pointer to comm processor space */ /* We allocate this here because it is used almost exclusively for @@ -69,7 +72,11 @@ cpm2_reset(void) /* Reclaim the DP memory for our use. */ +#ifdef CONFIG_PPC_CPM_NEW_BINDING + cpm_muram_init(); +#else cpm2_dpinit(); +#endif /* Tell everyone where the comm processor resides. */ @@ -316,6 +323,7 @@ int cpm2_smc_clk_setup(enum cpm_clk_target target, int clock) return ret; } +#ifndef CONFIG_PPC_CPM_NEW_BINDING /* * dpalloc / dpfree bits. */ @@ -328,28 +336,6 @@ static u8 __iomem *im_dprambase; static void cpm2_dpinit(void) { - struct resource r; - -#ifdef CONFIG_PPC_CPM_NEW_BINDING - struct device_node *np; - - np = of_find_compatible_node(NULL, NULL, "fsl,cpm2"); - if (!np) - panic("Cannot find CPM2 node"); - - if (of_address_to_resource(np, 1, &r)) - panic("Cannot get CPM2 resource 1"); - - of_node_put(np); -#else - r.start = CPM_MAP_ADDR; - r.end = r.start + CPM_DATAONLY_BASE + CPM_DATAONLY_SIZE - 1; -#endif - - im_dprambase = ioremap(r.start, r.end - r.start + 1); - if (!im_dprambase) - panic("Cannot map DPRAM"); - spin_lock_init(&cpm_dpmem_lock); /* initialize the info header */ @@ -358,13 +344,15 @@ static void cpm2_dpinit(void) sizeof(cpm_boot_dpmem_rh_block[0]), cpm_boot_dpmem_rh_block); + im_dprambase = cpm2_immr; + /* Attach the usable dpmem area */ /* XXX: This is actually crap. CPM_DATAONLY_BASE and * CPM_DATAONLY_SIZE is only a subset of the available dpram. It * varies with the processor and the microcode patches activated. * But the following should be at least safe. */ - rh_attach_region(&cpm_dpmem_info, 0, r.end - r.start + 1); + rh_attach_region(&cpm_dpmem_info, CPM_DATAONLY_BASE, CPM_DATAONLY_SIZE); } /* This function returns an index into the DPRAM area. @@ -422,6 +410,7 @@ void *cpm_dpram_addr(unsigned long offset) return (void *)(im_dprambase + offset); } EXPORT_SYMBOL(cpm_dpram_addr); +#endif /* !CONFIG_PPC_CPM_NEW_BINDING */ struct cpm2_ioports { u32 dir, par, sor, odr, dat; diff --git a/arch/powerpc/sysdev/cpm_common.c b/arch/powerpc/sysdev/cpm_common.c index 9daa6ac6767..66c8ad4cfce 100644 --- a/arch/powerpc/sysdev/cpm_common.c +++ b/arch/powerpc/sysdev/cpm_common.c @@ -5,15 +5,27 @@ * * Copyright 2007 Freescale Semiconductor, Inc. * + * Some parts derived from commproc.c/cpm2_common.c, which is: + * Copyright (c) 1997 Dan error_act (dmalek@jlc.net) + * Copyright (c) 1999-2001 Dan Malek + * Copyright (c) 2000 MontaVista Software, Inc (source@mvista.com) + * 2006 (c) MontaVista Software, Inc. + * Vitaly Bordug + * * This program is free software; you can redistribute it and/or modify * it under the terms of version 2 of the GNU General Public License as * published by the Free Software Foundation. */ #include +#include + #include #include #include +#include +#include + #include #ifdef CONFIG_PPC_EARLY_DEBUG_CPM @@ -41,6 +53,153 @@ void __init udbg_init_cpm(void) setbat(1, 0xf0000000, 0xf0000000, 1024*1024, _PAGE_IO); #endif udbg_putc = udbg_putc_cpm; + udbg_putc('X'); } } #endif + +#ifdef CONFIG_PPC_CPM_NEW_BINDING +static spinlock_t cpm_muram_lock; +static rh_block_t cpm_boot_muram_rh_block[16]; +static rh_info_t cpm_muram_info; +static u8 __iomem *muram_vbase; +static phys_addr_t muram_pbase; + +/* Max address size we deal with */ +#define OF_MAX_ADDR_CELLS 4 + +int __init cpm_muram_init(void) +{ + struct device_node *np; + struct resource r; + u32 zero[OF_MAX_ADDR_CELLS] = {}; + resource_size_t max = 0; + int i = 0; + int ret = 0; + + printk("cpm_muram_init\n"); + + spin_lock_init(&cpm_muram_lock); + /* initialize the info header */ + rh_init(&cpm_muram_info, 1, + sizeof(cpm_boot_muram_rh_block) / + sizeof(cpm_boot_muram_rh_block[0]), + cpm_boot_muram_rh_block); + + np = of_find_compatible_node(NULL, NULL, "fsl,cpm-muram-data"); + if (!np) { + printk(KERN_ERR "Cannot find CPM muram data node"); + ret = -ENODEV; + goto out; + } + + muram_pbase = of_translate_address(np, zero); + if (muram_pbase == (phys_addr_t)OF_BAD_ADDR) { + printk(KERN_ERR "Cannot translate zero through CPM muram node"); + ret = -ENODEV; + goto out; + } + + while (of_address_to_resource(np, i++, &r) == 0) { + if (r.end > max) + max = r.end; + + rh_attach_region(&cpm_muram_info, r.start - muram_pbase, + r.end - r.start + 1); + } + + muram_vbase = ioremap(muram_pbase, max - muram_pbase + 1); + if (!muram_vbase) { + printk(KERN_ERR "Cannot map CPM muram"); + ret = -ENOMEM; + } + +out: + of_node_put(np); + return ret; +} + +/** + * cpm_muram_alloc - allocate the requested size worth of multi-user ram + * @size: number of bytes to allocate + * @align: requested alignment, in bytes + * + * This function returns an offset into the muram area. + * Use cpm_dpram_addr() to get the virtual address of the area. + * Use cpm_muram_free() to free the allocation. + */ +unsigned long cpm_muram_alloc(unsigned long size, unsigned long align) +{ + unsigned long start; + unsigned long flags; + + spin_lock_irqsave(&cpm_muram_lock, flags); + cpm_muram_info.alignment = align; + start = rh_alloc(&cpm_muram_info, size, "commproc"); + spin_unlock_irqrestore(&cpm_muram_lock, flags); + + return start; +} +EXPORT_SYMBOL(cpm_muram_alloc); + +/** + * cpm_muram_free - free a chunk of multi-user ram + * @offset: The beginning of the chunk as returned by cpm_muram_alloc(). + */ +int cpm_muram_free(unsigned long offset) +{ + int ret; + unsigned long flags; + + spin_lock_irqsave(&cpm_muram_lock, flags); + ret = rh_free(&cpm_muram_info, offset); + spin_unlock_irqrestore(&cpm_muram_lock, flags); + + return ret; +} +EXPORT_SYMBOL(cpm_muram_free); + +/** + * cpm_muram_alloc_fixed - reserve a specific region of multi-user ram + * @offset: the offset into the muram area to reserve + * @size: the number of bytes to reserve + * + * This function returns "start" on success, -ENOMEM on failure. + * Use cpm_dpram_addr() to get the virtual address of the area. + * Use cpm_muram_free() to free the allocation. + */ +unsigned long cpm_muram_alloc_fixed(unsigned long offset, unsigned long size) +{ + unsigned long start; + unsigned long flags; + + spin_lock_irqsave(&cpm_muram_lock, flags); + cpm_muram_info.alignment = 1; + start = rh_alloc_fixed(&cpm_muram_info, offset, size, "commproc"); + spin_unlock_irqrestore(&cpm_muram_lock, flags); + + return start; +} +EXPORT_SYMBOL(cpm_muram_alloc_fixed); + +/** + * cpm_muram_addr - turn a muram offset into a virtual address + * @offset: muram offset to convert + */ +void __iomem *cpm_muram_addr(unsigned long offset) +{ + return muram_vbase + offset; +} +EXPORT_SYMBOL(cpm_muram_addr); + +/** + * cpm_muram_phys - turn a muram virtual address into a DMA address + * @offset: virtual address from cpm_muram_addr() to convert + */ +dma_addr_t cpm_muram_dma(void __iomem *addr) +{ + return muram_pbase + ((u8 __iomem *)addr - muram_vbase); +} +EXPORT_SYMBOL(cpm_muram_dma); + +#endif /* CONFIG_PPC_CPM_NEW_BINDING */ diff --git a/drivers/serial/cpm_uart/cpm_uart_cpm2.c b/drivers/serial/cpm_uart/cpm_uart_cpm2.c index 5bd4508ce3c..882dbc17d59 100644 --- a/drivers/serial/cpm_uart/cpm_uart_cpm2.c +++ b/drivers/serial/cpm_uart/cpm_uart_cpm2.c @@ -235,7 +235,7 @@ void scc4_lineif(struct uart_cpm_port *pinfo) int cpm_uart_allocbuf(struct uart_cpm_port *pinfo, unsigned int is_con) { int dpmemsz, memsz; - u8 *dp_mem; + u8 __iomem *dp_mem; unsigned long dp_offset; u8 *mem_addr; dma_addr_t dma_addr = 0; @@ -278,7 +278,7 @@ int cpm_uart_allocbuf(struct uart_cpm_port *pinfo, unsigned int is_con) pinfo->tx_buf = pinfo->rx_buf + L1_CACHE_ALIGN(pinfo->rx_nrfifos * pinfo->rx_fifosize); - pinfo->rx_bd_base = (cbd_t __iomem __force *)dp_mem; + pinfo->rx_bd_base = (cbd_t __iomem *)dp_mem; pinfo->tx_bd_base = pinfo->rx_bd_base + pinfo->rx_nrfifos; return 0; diff --git a/include/asm-powerpc/commproc.h b/include/asm-powerpc/commproc.h index 5dec32404fa..0307c84a5c1 100644 --- a/include/asm-powerpc/commproc.h +++ b/include/asm-powerpc/commproc.h @@ -19,6 +19,7 @@ #include #include +#include /* CPM Command register. */ @@ -54,6 +55,7 @@ #define mk_cr_cmd(CH, CMD) ((CMD << 8) | (CH << 4)) +#ifndef CONFIG_PPC_CPM_NEW_BINDING /* The dual ported RAM is multi-functional. Some areas can be (and are * being) used for microcode. There is an area that can only be used * as data ram for buffer descriptors, which is all we use right now. @@ -62,17 +64,27 @@ #define CPM_DATAONLY_BASE ((uint)0x0800) #define CPM_DATAONLY_SIZE ((uint)0x0700) #define CPM_DP_NOSPACE ((uint)0x7fffffff) +#endif /* Export the base address of the communication processor registers * and dual port ram. */ extern cpm8xx_t __iomem *cpmp; /* Pointer to comm processor */ + +#ifdef CONFIG_PPC_CPM_NEW_BINDING +#define cpm_dpalloc cpm_muram_alloc +#define cpm_dpfree cpm_muram_free +#define cpm_dpram_addr cpm_muram_addr +#define cpm_dpram_phys cpm_muram_dma +#else extern unsigned long cpm_dpalloc(uint size, uint align); extern int cpm_dpfree(unsigned long offset); extern unsigned long cpm_dpalloc_fixed(unsigned long offset, uint size, uint align); extern void cpm_dpdump(void); extern void *cpm_dpram_addr(unsigned long offset); extern uint cpm_dpram_phys(u8* addr); +#endif + extern void cpm_setbrg(uint brg, uint rate); extern uint m8xx_cpm_hostalloc(uint size); diff --git a/include/asm-powerpc/cpm.h b/include/asm-powerpc/cpm.h new file mode 100644 index 00000000000..48df9f330e7 --- /dev/null +++ b/include/asm-powerpc/cpm.h @@ -0,0 +1,14 @@ +#ifndef __CPM_H +#define __CPM_H + +#include +#include + +int cpm_muram_init(void); +unsigned long cpm_muram_alloc(unsigned long size, unsigned long align); +int cpm_muram_free(unsigned long offset); +unsigned long cpm_muram_alloc_fixed(unsigned long offset, unsigned long size); +void __iomem *cpm_muram_addr(unsigned long offset); +dma_addr_t cpm_muram_dma(void __iomem *addr); + +#endif diff --git a/include/asm-powerpc/cpm2.h b/include/asm-powerpc/cpm2.h index d7b57ac5589..e698b1d09dc 100644 --- a/include/asm-powerpc/cpm2.h +++ b/include/asm-powerpc/cpm2.h @@ -11,6 +11,7 @@ #define __CPM2__ #include +#include /* CPM Command register. */ @@ -82,6 +83,7 @@ #define mk_cr_cmd(PG, SBC, MCN, OP) \ ((PG << 26) | (SBC << 21) | (MCN << 6) | OP) +#ifndef CONFIG_PPC_CPM_NEW_BINDING /* Dual Port RAM addresses. The first 16K is available for almost * any CPM use, so we put the BDs there. The first 128 bytes are * used for SMC1 and SMC2 parameter RAM, so we start allocating @@ -97,6 +99,7 @@ #define CPM_DATAONLY_SIZE ((uint)(16 * 1024) - CPM_DATAONLY_BASE) #define CPM_FCC_SPECIAL_BASE ((uint)0x0000b000) #endif +#endif /* The number of pages of host memory we allocate for CPM. This is * done early in kernel initialization to get physically contiguous @@ -109,11 +112,18 @@ */ extern cpm_cpm2_t __iomem *cpmp; /* Pointer to comm processor */ +#ifdef CONFIG_PPC_CPM_NEW_BINDING +#define cpm_dpalloc cpm_muram_alloc +#define cpm_dpfree cpm_muram_free +#define cpm_dpram_addr cpm_muram_addr +#else extern unsigned long cpm_dpalloc(uint size, uint align); extern int cpm_dpfree(unsigned long offset); extern unsigned long cpm_dpalloc_fixed(unsigned long offset, uint size, uint align); extern void cpm_dpdump(void); extern void *cpm_dpram_addr(unsigned long offset); +#endif + extern void cpm_setbrg(uint brg, uint rate); extern void cpm2_fastbrg(uint brg, uint rate, int div16); extern void cpm2_reset(void); -- cgit v1.2.3-70-g09d2 From f023dc769c47b9158d897ee8a0278bdfe39b0115 Mon Sep 17 00:00:00 2001 From: Peter Korsgaard Date: Wed, 3 Oct 2007 18:29:09 +0200 Subject: [POWERPC] spi: mode should be "cpu-qe" instead of "qe" Mode should be "cpu-qe" for QE in CPU mode. "qe" should be reserved for native QE mode. Signed-off-by: Peter Korsgaard Signed-off-by: Kumar Gala --- Documentation/powerpc/booting-without-of.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation/powerpc') diff --git a/Documentation/powerpc/booting-without-of.txt b/Documentation/powerpc/booting-without-of.txt index ce5d67f5cb5..7a6c5f2f3b0 100644 --- a/Documentation/powerpc/booting-without-of.txt +++ b/Documentation/powerpc/booting-without-of.txt @@ -1551,7 +1551,7 @@ platforms are moved over to use the flattened-device-tree model. Required properties: - device_type : should be "spi". - compatible : should be "fsl_spi". - - mode : the SPI operation mode, it can be "cpu" or "qe". + - mode : the SPI operation mode, it can be "cpu" or "cpu-qe". - reg : Offset and length of the register set for the device - interrupts : where a is the interrupt number and b is a field that represents an encoding of the sense and level -- cgit v1.2.3-70-g09d2