]> git.kernelconcepts.de Git - karo-tx-linux.git/commitdiff
Merge tag 'armsoc-soc' into test-merge
authorKevin Hilman <khilman@linaro.org>
Thu, 25 Jun 2015 04:32:13 +0000 (21:32 -0700)
committerKevin Hilman <khilman@linaro.org>
Thu, 25 Jun 2015 04:32:13 +0000 (21:32 -0700)
ARM: SoC: platform support for v4.2

Our SoC branch usually contains expanded support for new SoCs and
other core platform code. Some highlights from this round:

- sunxi: SMP support for A23 SoC
- socpga: big-endian support
- pxa: conversion to common clock framework
- bcm: SMP support for BCM63138
- imx: support new I.MX7D SoC
- zte: basic support for ZX296702 SoC

 Conflicts:
arch/arm/mach-socfpga/core.h

Trivial remove/remove conflict with our cleanup branch.
Resolution: remove both sides

# gpg: Signature made Wed Jun 24 21:32:12 2015 PDT using RSA key ID D3FBC665
# gpg: Good signature from "Kevin Hilman <khilman@deeprootsystems.com>"
# gpg:                 aka "Kevin Hilman <khilman@linaro.org>"
# gpg:                 aka "Kevin Hilman <khilman@kernel.org>"

# Conflicts:
# arch/arm/mach-socfpga/core.h

225 files changed:
Documentation/arm/stm32/overview.txt [new file with mode: 0644]
Documentation/arm/stm32/stm32f429-overview.txt [new file with mode: 0644]
Documentation/devicetree/bindings/arm/cpus.txt
Documentation/devicetree/bindings/arm/exynos/power_domain.txt
Documentation/devicetree/bindings/arm/fsl.txt
Documentation/devicetree/bindings/arm/zte.txt [new file with mode: 0644]
Documentation/devicetree/bindings/clock/zx296702-clk.txt [new file with mode: 0644]
Documentation/devicetree/bindings/serial/pl011.txt
Documentation/devicetree/bindings/vendor-prefixes.txt
MAINTAINERS
arch/arm/Kconfig
arch/arm/Kconfig.debug
arch/arm/Makefile
arch/arm/boot/dts/Makefile
arch/arm/boot/dts/zx296702-ad1.dts [new file with mode: 0644]
arch/arm/boot/dts/zx296702.dtsi [new file with mode: 0644]
arch/arm/configs/efm32_defconfig
arch/arm/configs/zx_defconfig [new file with mode: 0644]
arch/arm/include/asm/firmware.h
arch/arm/include/asm/vfp.h
arch/arm/include/debug/8250.S
arch/arm/include/debug/efm32.S
arch/arm/include/debug/imx-uart.h
arch/arm/include/debug/pl01x.S
arch/arm/kernel/debug.S
arch/arm/mach-bcm/Kconfig
arch/arm/mach-bcm/Makefile
arch/arm/mach-bcm/bcm63xx_headsmp.S [new file with mode: 0644]
arch/arm/mach-bcm/bcm63xx_pmb.c [new file with mode: 0644]
arch/arm/mach-bcm/bcm63xx_smp.c [new file with mode: 0644]
arch/arm/mach-bcm/bcm63xx_smp.h [new file with mode: 0644]
arch/arm/mach-bcm/bcm_5301x.c
arch/arm/mach-bcm/board_bcm2835.c
arch/arm/mach-ep93xx/simone.c
arch/arm/mach-exynos/common.h
arch/arm/mach-exynos/exynos.c
arch/arm/mach-exynos/firmware.c
arch/arm/mach-exynos/platsmp.c
arch/arm/mach-exynos/pm.c
arch/arm/mach-exynos/pm_domains.c
arch/arm/mach-exynos/pmu.c
arch/arm/mach-exynos/suspend.c
arch/arm/mach-imx/Kconfig
arch/arm/mach-imx/Makefile
arch/arm/mach-imx/Makefile.boot [new file with mode: 0644]
arch/arm/mach-imx/anatop.c
arch/arm/mach-imx/common.h
arch/arm/mach-imx/cpu.c
arch/arm/mach-imx/cpuidle-imx6q.c
arch/arm/mach-imx/cpuidle-imx6sl.c
arch/arm/mach-imx/cpuidle-imx6sx.c
arch/arm/mach-imx/gpc.c
arch/arm/mach-imx/hardware.h
arch/arm/mach-imx/iomux-imx31.c
arch/arm/mach-imx/mach-imx6q.c
arch/arm/mach-imx/mach-imx6sl.c
arch/arm/mach-imx/mach-imx6sx.c
arch/arm/mach-imx/mach-imx7d.c [new file with mode: 0644]
arch/arm/mach-imx/mach-vf610.c
arch/arm/mach-imx/mmdc.c
arch/arm/mach-imx/mx27.h
arch/arm/mach-imx/mx3x.h
arch/arm/mach-imx/mxc.h
arch/arm/mach-imx/pm-imx5.c
arch/arm/mach-imx/pm-imx6.c
arch/arm/mach-imx/suspend-imx53.S [new file with mode: 0644]
arch/arm/mach-imx/time.c [deleted file]
arch/arm/mach-lpc18xx/Makefile [new file with mode: 0644]
arch/arm/mach-lpc18xx/Makefile.boot [new file with mode: 0644]
arch/arm/mach-lpc18xx/board-dt.c [new file with mode: 0644]
arch/arm/mach-omap1/ams-delta-fiq-handler.S
arch/arm/mach-omap1/board-ams-delta.c
arch/arm/mach-omap1/board-fsample.c
arch/arm/mach-omap1/board-generic.c
arch/arm/mach-omap1/board-h2.c
arch/arm/mach-omap1/board-h3-mmc.c
arch/arm/mach-omap1/board-h3.c
arch/arm/mach-omap1/board-htcherald.c
arch/arm/mach-omap1/board-innovator.c
arch/arm/mach-omap1/board-nokia770.c
arch/arm/mach-omap1/board-osk.c
arch/arm/mach-omap1/board-palmte.c
arch/arm/mach-omap1/board-palmtt.c
arch/arm/mach-omap1/board-palmz71.c
arch/arm/mach-omap1/board-perseus2.c
arch/arm/mach-omap1/board-sx1.c
arch/arm/mach-omap1/board-voiceblue.c
arch/arm/mach-omap1/common.h
arch/arm/mach-omap1/dma.c
arch/arm/mach-omap1/gpio16xx.c
arch/arm/mach-omap1/gpio7xx.c
arch/arm/mach-omap1/i2c.c
arch/arm/mach-omap1/include/mach/entry-macro.S [deleted file]
arch/arm/mach-omap1/include/mach/irqs.h
arch/arm/mach-omap1/include/mach/memory.h
arch/arm/mach-omap1/include/mach/serial.h
arch/arm/mach-omap1/include/mach/soc.h
arch/arm/mach-omap1/irq.c
arch/arm/mach-omap1/mux.c
arch/arm/mach-omap1/pm.c
arch/arm/mach-omap1/serial.c
arch/arm/mach-omap1/timer.c
arch/arm/mach-omap2/omap_device.c
arch/arm/mach-omap2/omap_hwmod.c
arch/arm/mach-omap2/omap_hwmod.h
arch/arm/mach-omap2/omap_hwmod_2xxx_ipblock_data.c
arch/arm/mach-omap2/omap_hwmod_33xx_43xx_common_data.h
arch/arm/mach-omap2/omap_hwmod_33xx_43xx_ipblock_data.c
arch/arm/mach-omap2/omap_hwmod_33xx_data.c
arch/arm/mach-omap2/omap_hwmod_3xxx_data.c
arch/arm/mach-omap2/omap_hwmod_43xx_data.c
arch/arm/mach-omap2/omap_hwmod_44xx_data.c
arch/arm/mach-omap2/omap_hwmod_7xx_data.c
arch/arm/mach-omap2/omap_hwmod_81xx_data.c
arch/arm/mach-omap2/prcm43xx.h
arch/arm/mach-pxa/Makefile
arch/arm/mach-pxa/clock-pxa2xx.c [deleted file]
arch/arm/mach-pxa/clock-pxa3xx.c [deleted file]
arch/arm/mach-pxa/clock.c [deleted file]
arch/arm/mach-pxa/clock.h [deleted file]
arch/arm/mach-pxa/eseries.c
arch/arm/mach-pxa/generic.c
arch/arm/mach-pxa/generic.h
arch/arm/mach-pxa/irq.c
arch/arm/mach-pxa/lubbock.c
arch/arm/mach-pxa/pxa25x.c
arch/arm/mach-pxa/pxa27x.c
arch/arm/mach-pxa/pxa300.c
arch/arm/mach-pxa/pxa320.c
arch/arm/mach-pxa/pxa3xx.c
arch/arm/mach-pxa/raumfeld.c
arch/arm/mach-pxa/tosa.c
arch/arm/mach-shmobile/Kconfig
arch/arm/mach-socfpga/Kconfig
arch/arm/mach-socfpga/Makefile
arch/arm/mach-socfpga/core.h
arch/arm/mach-socfpga/headsmp.S
arch/arm/mach-socfpga/platsmp.c
arch/arm/mach-socfpga/pm.c [new file with mode: 0644]
arch/arm/mach-socfpga/self-refresh.S [new file with mode: 0644]
arch/arm/mach-socfpga/socfpga.c
arch/arm/mach-stm32/Makefile [new file with mode: 0644]
arch/arm/mach-stm32/Makefile.boot [new file with mode: 0644]
arch/arm/mach-stm32/board-dt.c [new file with mode: 0644]
arch/arm/mach-sunxi/platsmp.c
arch/arm/mach-tegra/cpuidle-tegra20.c
arch/arm/mach-tegra/reset-handler.S
arch/arm/mach-tegra/reset.h
arch/arm/mach-tegra/sleep-tegra20.S
arch/arm/mach-tegra/sleep.h
arch/arm/mach-tegra/tegra.c
arch/arm/mach-uniphier/Kconfig [new file with mode: 0644]
arch/arm/mach-uniphier/Makefile [new file with mode: 0644]
arch/arm/mach-uniphier/platsmp.c [new file with mode: 0644]
arch/arm/mach-uniphier/uniphier.c [new file with mode: 0644]
arch/arm/mach-zx/Kconfig [new file with mode: 0644]
arch/arm/mach-zx/Makefile [new file with mode: 0644]
arch/arm/mach-zx/core.h [new file with mode: 0644]
arch/arm/mach-zx/headsmp.S [new file with mode: 0644]
arch/arm/mach-zx/platsmp.c [new file with mode: 0644]
arch/arm/mach-zx/zx296702.c [new file with mode: 0644]
arch/arm/mach-zynq/common.c
arch/arm/mach-zynq/common.h
arch/arm/mach-zynq/slcr.c
arch/arm/plat-omap/dma.c
arch/arm/plat-samsung/adc.c
arch/arm/vfp/vfpmodule.c
arch/arm64/Kconfig
arch/arm64/configs/defconfig
drivers/bus/brcmstb_gisb.c
drivers/clk/Makefile
drivers/clk/imx/Makefile [new file with mode: 0644]
drivers/clk/imx/clk-busy.c [moved from arch/arm/mach-imx/clk-busy.c with 100% similarity]
drivers/clk/imx/clk-cpu.c [moved from arch/arm/mach-imx/clk-cpu.c with 99% similarity]
drivers/clk/imx/clk-fixup-div.c [moved from arch/arm/mach-imx/clk-fixup-div.c with 100% similarity]
drivers/clk/imx/clk-fixup-mux.c [moved from arch/arm/mach-imx/clk-fixup-mux.c with 100% similarity]
drivers/clk/imx/clk-gate-exclusive.c [moved from arch/arm/mach-imx/clk-gate-exclusive.c with 100% similarity]
drivers/clk/imx/clk-gate2.c [moved from arch/arm/mach-imx/clk-gate2.c with 100% similarity]
drivers/clk/imx/clk-imx1.c [moved from arch/arm/mach-imx/clk-imx1.c with 91% similarity]
drivers/clk/imx/clk-imx21.c [moved from arch/arm/mach-imx/clk-imx21.c with 95% similarity]
drivers/clk/imx/clk-imx25.c [moved from arch/arm/mach-imx/clk-imx25.c with 98% similarity]
drivers/clk/imx/clk-imx27.c [moved from arch/arm/mach-imx/clk-imx27.c with 97% similarity]
drivers/clk/imx/clk-imx31.c [moved from arch/arm/mach-imx/clk-imx31.c with 91% similarity]
drivers/clk/imx/clk-imx35.c [moved from arch/arm/mach-imx/clk-imx35.c with 94% similarity]
drivers/clk/imx/clk-imx51-imx53.c [moved from arch/arm/mach-imx/clk-imx51-imx53.c with 99% similarity]
drivers/clk/imx/clk-imx6q.c [moved from arch/arm/mach-imx/clk-imx6q.c with 98% similarity]
drivers/clk/imx/clk-imx6sl.c [moved from arch/arm/mach-imx/clk-imx6sl.c with 99% similarity]
drivers/clk/imx/clk-imx6sx.c [moved from arch/arm/mach-imx/clk-imx6sx.c with 99% similarity]
drivers/clk/imx/clk-imx7d.c [new file with mode: 0644]
drivers/clk/imx/clk-pfd.c [moved from arch/arm/mach-imx/clk-pfd.c with 100% similarity]
drivers/clk/imx/clk-pllv1.c [moved from arch/arm/mach-imx/clk-pllv1.c with 75% similarity]
drivers/clk/imx/clk-pllv2.c [moved from arch/arm/mach-imx/clk-pllv2.c with 100% similarity]
drivers/clk/imx/clk-pllv3.c [moved from arch/arm/mach-imx/clk-pllv3.c with 96% similarity]
drivers/clk/imx/clk-vf610.c [moved from arch/arm/mach-imx/clk-vf610.c with 98% similarity]
drivers/clk/imx/clk.c [moved from arch/arm/mach-imx/clk.c with 100% similarity]
drivers/clk/imx/clk.h [moved from arch/arm/mach-imx/clk.h with 94% similarity]
drivers/clk/pxa/clk-pxa27x.c
drivers/clk/zte/Makefile [new file with mode: 0644]
drivers/clk/zte/clk-pll.c [new file with mode: 0644]
drivers/clk/zte/clk-zx296702.c [new file with mode: 0644]
drivers/clk/zte/clk.h [new file with mode: 0644]
drivers/clocksource/Kconfig
drivers/clocksource/Makefile
drivers/clocksource/timer-imx-gpt.c [new file with mode: 0644]
drivers/irqchip/Kconfig
drivers/irqchip/irq-nvic.c
drivers/irqchip/irq-vf610-mscm-ir.c
drivers/memory/Kconfig
drivers/memory/omap-gpmc.c
drivers/soc/tegra/fuse/fuse-tegra20.c
drivers/soc/tegra/pmc.c
drivers/watchdog/bcm2835_wdt.c
include/dt-bindings/clock/imx7d-clock.h [new file with mode: 0644]
include/dt-bindings/clock/vf610-clock.h
include/dt-bindings/clock/zx296702-clock.h [new file with mode: 0644]
include/linux/irq.h
include/linux/irqdomain.h
include/linux/reset/bcm63xx_pmb.h [new file with mode: 0644]
include/soc/imx/revision.h [new file with mode: 0644]
include/soc/imx/timer.h [new file with mode: 0644]
include/soc/tegra/pmc.h
include/uapi/linux/serial_reg.h
kernel/irq/chip.c
kernel/irq/generic-chip.c
kernel/irq/irqdomain.c

diff --git a/Documentation/arm/stm32/overview.txt b/Documentation/arm/stm32/overview.txt
new file mode 100644 (file)
index 0000000..09aed55
--- /dev/null
@@ -0,0 +1,32 @@
+                       STM32 ARM Linux Overview
+                       ========================
+
+Introduction
+------------
+
+  The STMicroelectronics family of Cortex-M based MCUs are supported by the
+  'STM32' platform of ARM Linux. Currently only the STM32F429 is supported.
+
+
+Configuration
+-------------
+
+  A generic configuration is provided for STM32 family, and can be used as the
+  default by
+       make stm32_defconfig
+
+Layout
+------
+
+  All the files for multiple machine families are located in the platform code
+  contained in arch/arm/mach-stm32
+
+  There is a generic board board-dt.c in the mach folder which support
+  Flattened Device Tree, which means, it works with any compatible board with
+  Device Trees.
+
+
+Document Author
+---------------
+
+  Maxime Coquelin <mcoquelin.stm32@gmail.com>
diff --git a/Documentation/arm/stm32/stm32f429-overview.txt b/Documentation/arm/stm32/stm32f429-overview.txt
new file mode 100644 (file)
index 0000000..5206822
--- /dev/null
@@ -0,0 +1,22 @@
+                       STM32F429 Overview
+                       ==================
+
+  Introduction
+  ------------
+       The STM32F429 is a Cortex-M4 MCU aimed at various applications.
+       It features:
+       - ARM Cortex-M4 up to 180MHz with FPU
+       - 2MB internal Flash Memory
+       - External memory support through FMC controller (PSRAM, SDRAM, NOR, NAND)
+       - I2C, SPI, SAI, CAN, USB OTG, Ethernet controllers
+       - LCD controller & Camera interface
+       - Cryptographic processor
+
+  Resources
+  ---------
+       Datasheet and reference manual are publicly available on ST website:
+       - http://www.st.com/web/en/catalog/mmc/FM141/SC1169/SS1577/LN1806?ecmp=stm32f429-439_pron_pr-ces2014_nov2013
+
+  Document Author
+  ---------------
+       Maxime Coquelin <mcoquelin.stm32@gmail.com>
index 6aa331d11c5e3e042ff2e0ec495d39e26fe0681c..d6b794cef0b8b9907ab5a055a6502180b4350148 100644 (file)
@@ -188,6 +188,7 @@ nodes to be present and contain the properties described below.
                        # On ARM 32-bit systems this property is optional and
                          can be one of:
                            "allwinner,sun6i-a31"
+                           "allwinner,sun8i-a23"
                            "arm,psci"
                            "brcm,brahma-b15"
                            "marvell,armada-375-smp"
index 5da38c5ed476ee2248432314c0bf886305f6cc13..e151057d92f0804fd577a471d937df688e61f6c9 100644 (file)
@@ -19,9 +19,10 @@ Optional Properties:
        domains.
 - clock-names: The following clocks can be specified:
        - oscclk: Oscillator clock.
-       - pclkN, clkN: Pairs of parent of input clock and input clock to the
-               devices in this power domain. Maximum of 4 pairs (N = 0 to 3)
-               are supported currently.
+       - clkN: Input clocks to the devices in this power domain. These clocks
+               will be reparented to oscclk before swithing power domain off.
+               Their original parent will be brought back after turning on
+               the domain. Maximum of 4 clocks (N = 0 to 3) are supported.
        - asbN: Clocks required by asynchronous bridges (ASB) present in
                the power domain. These clock should be enabled during power
                domain on/off operations.
index a5462b6b3c30d8bea1a63f9368379ce5c268b0eb..2a3ba73f0c5cc3da965315c1aa0f49acb1a7541a 100644 (file)
@@ -81,12 +81,15 @@ Freescale Vybrid Platform Device Tree Bindings
 For the Vybrid SoC familiy all variants with DDR controller are supported,
 which is the VF5xx and VF6xx series. Out of historical reasons, in most
 places the kernel uses vf610 to refer to the whole familiy.
+The compatible string "fsl,vf610m4" is used for the secondary Cortex-M4
+core support.
 
 Required root node compatible property (one of them):
     - compatible = "fsl,vf500";
     - compatible = "fsl,vf510";
     - compatible = "fsl,vf600";
     - compatible = "fsl,vf610";
+    - compatible = "fsl,vf610m4";
 
 Freescale LS1021A Platform Device Tree Bindings
 ------------------------------------------------
diff --git a/Documentation/devicetree/bindings/arm/zte.txt b/Documentation/devicetree/bindings/arm/zte.txt
new file mode 100644 (file)
index 0000000..3ff5c9e
--- /dev/null
@@ -0,0 +1,15 @@
+ZTE platforms device tree bindings
+---------------------------------------
+
+-  ZX296702 board:
+    Required root node properties:
+      - compatible = "zte,zx296702-ad1", "zte,zx296702"
+
+System management required properties:
+      - compatible = "zte,sysctrl"
+
+Low power management required properties:
+      - compatible = "zte,zx296702-pcu"
+
+Bus matrix required properties:
+      - compatible = "zte,zx-bus-matrix"
diff --git a/Documentation/devicetree/bindings/clock/zx296702-clk.txt b/Documentation/devicetree/bindings/clock/zx296702-clk.txt
new file mode 100644 (file)
index 0000000..750442b
--- /dev/null
@@ -0,0 +1,35 @@
+Device Tree Clock bindings for ZTE zx296702
+
+This binding uses the common clock binding[1].
+
+[1] Documentation/devicetree/bindings/clock/clock-bindings.txt
+
+Required properties:
+- compatible : shall be one of the following:
+       "zte,zx296702-topcrm-clk":
+               zx296702 top clock selection, divider and gating
+
+       "zte,zx296702-lsp0crpm-clk" and
+       "zte,zx296702-lsp1crpm-clk":
+               zx296702 device level clock selection and gating
+
+- reg: Address and length of the register set
+
+The clock consumer should specify the desired clock by having the clock
+ID in its "clocks" phandle cell. See include/dt-bindings/clock/zx296702-clock.h
+for the full list of zx296702 clock IDs.
+
+
+topclk: topcrm@0x09800000 {
+        compatible = "zte,zx296702-topcrm-clk";
+        reg = <0x09800000 0x1000>;
+        #clock-cells = <1>;
+};
+
+uart0: serial@0x09405000 {
+        compatible = "zte,zx296702-uart";
+        reg = <0x09405000 0x1000>;
+        interrupts = <GIC_SPI 37 IRQ_TYPE_LEVEL_HIGH>;
+        clocks = <&lsp1clk ZX296702_UART0_PCLK>;
+        status = "disabled";
+};
index ba3ecb8cb5a1855465d69e42ea812fc7e28518fb..cbae3d9a0278076873e5274f47b4881a92b51c0b 100644 (file)
@@ -1,7 +1,7 @@
 * ARM AMBA Primecell PL011 serial UART
 
 Required properties:
-- compatible: must be "arm,primecell", "arm,pl011"
+- compatible: must be "arm,primecell", "arm,pl011", "zte,zx296702-uart"
 - reg: exactly one register range with length 0x1000
 - interrupts: exactly one interrupt specifier
 
index 80339192c93e2626f81eed30fe97ff147c86d746..717ffd5a3563396b341045457d98d5ceac845e8f 100644 (file)
@@ -211,3 +211,4 @@ xillybus    Xillybus Ltd.
 xlnx   Xilinx
 zyxel  ZyXEL Communications Corp.
 zarlink        Zarlink Semiconductor
+zte    ZTE Corp.
index d8afd29536786b0907c795afeb8cd5aa3ff2d3b6..beed9810569509741c74158da9bcea50ccb7c4c6 100644 (file)
@@ -1035,7 +1035,7 @@ F:        arch/arm/include/asm/hardware/dec21285.h
 F:     arch/arm/mach-footbridge/
 
 ARM/FREESCALE IMX / MXC ARM ARCHITECTURE
-M:     Shawn Guo <shawn.guo@linaro.org>
+M:     Shawn Guo <shawnguo@kernel.org>
 M:     Sascha Hauer <kernel@pengutronix.de>
 L:     linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
 S:     Maintained
@@ -1044,9 +1044,11 @@ F:       arch/arm/mach-imx/
 F:     arch/arm/mach-mxs/
 F:     arch/arm/boot/dts/imx*
 F:     arch/arm/configs/imx*_defconfig
+F:     drivers/clk/imx/
+F:     include/soc/imx/
 
 ARM/FREESCALE VYBRID ARM ARCHITECTURE
-M:     Shawn Guo <shawn.guo@linaro.org>
+M:     Shawn Guo <shawnguo@kernel.org>
 M:     Sascha Hauer <kernel@pengutronix.de>
 R:     Stefan Agner <stefan@agner.ch>
 L:     linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
@@ -1189,6 +1191,12 @@ M:       Lennert Buytenhek <kernel@wantstofly.org>
 L:     linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
 S:     Maintained
 
+ARM/LPC18XX ARCHITECTURE
+M:     Joachim Eastwood <manabian@gmail.com>
+L:     linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
+S:     Maintained
+N:     lpc18xx
+
 ARM/MAGICIAN MACHINE SUPPORT
 M:     Philipp Zabel <philipp.zabel@gmail.com>
 S:     Maintained
@@ -1385,6 +1393,7 @@ L:        linux-samsung-soc@vger.kernel.org (moderated for non-subscribers)
 S:     Maintained
 F:     arch/arm/boot/dts/s3c*
 F:     arch/arm/boot/dts/exynos*
+F:     arch/arm64/boot/dts/exynos/
 F:     arch/arm/plat-samsung/
 F:     arch/arm/mach-s3c24*/
 F:     arch/arm/mach-s3c64xx/
@@ -1494,6 +1503,14 @@ F:       drivers/usb/host/ehci-st.c
 F:     drivers/usb/host/ohci-st.c
 F:     drivers/ata/ahci_st.c
 
+ARM/STM32 ARCHITECTURE
+M:     Maxime Coquelin <mcoquelin.stm32@gmail.com>
+L:     linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
+S:     Maintained
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/mcoquelin/stm32.git
+N:     stm32
+F:     drivers/clocksource/armv7m_systick.c
+
 ARM/TECHNOLOGIC SYSTEMS TS7250 MACHINE SUPPORT
 M:     Lennert Buytenhek <kernel@wantstofly.org>
 L:     linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
@@ -1540,6 +1557,13 @@ F:       drivers/rtc/rtc-ab3100.c
 F:     drivers/rtc/rtc-coh901331.c
 T:     git git://git.kernel.org/pub/scm/linux/kernel/git/linusw/linux-stericsson.git
 
+ARM/UNIPHIER ARCHITECTURE
+M:     Masahiro Yamada <yamada.masahiro@socionext.com>
+L:     linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
+S:     Maintained
+F:     arch/arm/mach-uniphier/
+N:     uniphier
+
 ARM/Ux500 ARM ARCHITECTURE
 M:     Linus Walleij <linus.walleij@linaro.org>
 L:     linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
@@ -1617,6 +1641,15 @@ S:       Maintained
 F:     arch/arm/mach-pxa/z2.c
 F:     arch/arm/mach-pxa/include/mach/z2.h
 
+ARM/ZTE ARCHITECTURE
+M:     Jun Nie <jun.nie@linaro.org>
+L:     linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
+S:     Maintained
+F:     arch/arm/mach-zx/
+F:     drivers/clk/zte/
+F:     Documentation/devicetree/bindings/arm/zte.txt
+F:     Documentation/devicetree/bindings/clock/zx296702-clk.txt
+
 ARM/ZYNQ ARCHITECTURE
 M:     Michal Simek <michal.simek@xilinx.com>
 R:     Sören Brinkmann <soren.brinkmann@xilinx.com>
@@ -2193,6 +2226,7 @@ S:        Maintained
 F:     arch/arm/mach-bcm/*brcmstb*
 F:     arch/arm/boot/dts/bcm7*.dts*
 F:     drivers/bus/brcmstb_gisb.c
+N:     brcmstb
 
 BROADCOM BMIPS MIPS ARCHITECTURE
 M:     Kevin Cernekee <cernekee@gmail.com>
index 45df48ba0b128dd408e2275687b1757c87e0ca74..72c4273de0039bc9cd3753be6dec323f6bf34581 100644 (file)
@@ -329,6 +329,20 @@ config ARCH_MULTIPLATFORM
        select SPARSE_IRQ
        select USE_OF
 
+config ARM_SINGLE_ARMV7M
+       bool "ARMv7-M based platforms (Cortex-M0/M3/M4)"
+       depends on !MMU
+       select ARCH_WANT_OPTIONAL_GPIOLIB
+       select ARM_NVIC
+       select AUTO_ZRELADDR
+       select CLKSRC_OF
+       select COMMON_CLK
+       select CPU_V7M
+       select GENERIC_CLOCKEVENTS
+       select NO_IOPORT_MAP
+       select SPARSE_IRQ
+       select USE_OF
+
 config ARCH_REALVIEW
        bool "ARM Ltd. RealView family"
        select ARCH_WANT_OPTIONAL_GPIOLIB
@@ -398,24 +412,6 @@ config ARCH_EBSA110
          Ethernet interface, two PCMCIA sockets, two serial ports and a
          parallel port.
 
-config ARCH_EFM32
-       bool "Energy Micro efm32"
-       depends on !MMU
-       select ARCH_REQUIRE_GPIOLIB
-       select ARM_NVIC
-       select AUTO_ZRELADDR
-       select CLKSRC_OF
-       select COMMON_CLK
-       select CPU_V7M
-       select GENERIC_CLOCKEVENTS
-       select NO_DMA
-       select NO_IOPORT_MAP
-       select SPARSE_IRQ
-       select USE_OF
-       help
-         Support for Energy Micro's (now Silicon Labs) efm32 Giant Gecko
-         processors.
-
 config ARCH_EP93XX
        bool "EP93xx-based"
        select ARCH_HAS_HOLES_MEMORYMODEL
@@ -606,6 +602,7 @@ config ARCH_PXA
        select ARCH_REQUIRE_GPIOLIB
        select ARM_CPU_SUSPEND if PM
        select AUTO_ZRELADDR
+       select COMMON_CLK
        select CLKDEV_LOOKUP
        select CLKSRC_MMIO
        select CLKSRC_OF
@@ -752,8 +749,10 @@ config ARCH_OMAP1
        select GENERIC_IRQ_CHIP
        select HAVE_IDE
        select IRQ_DOMAIN
+       select MULTI_IRQ_HANDLER
        select NEED_MACH_IO_H if PCCARD
        select NEED_MACH_MEMORY_H
+       select SPARSE_IRQ
        help
          Support for older TI OMAP1 (omap7xx, omap15xx or omap16xx)
 
@@ -937,6 +936,8 @@ source "arch/arm/mach-tegra/Kconfig"
 
 source "arch/arm/mach-u300/Kconfig"
 
+source "arch/arm/mach-uniphier/Kconfig"
+
 source "arch/arm/mach-ux500/Kconfig"
 
 source "arch/arm/mach-versatile/Kconfig"
@@ -948,8 +949,40 @@ source "arch/arm/mach-vt8500/Kconfig"
 
 source "arch/arm/mach-w90x900/Kconfig"
 
+source "arch/arm/mach-zx/Kconfig"
+
 source "arch/arm/mach-zynq/Kconfig"
 
+# ARMv7-M architecture
+config ARCH_EFM32
+       bool "Energy Micro efm32"
+       depends on ARM_SINGLE_ARMV7M
+       select ARCH_REQUIRE_GPIOLIB
+       help
+         Support for Energy Micro's (now Silicon Labs) efm32 Giant Gecko
+         processors.
+
+config ARCH_LPC18XX
+       bool "NXP LPC18xx/LPC43xx"
+       depends on ARM_SINGLE_ARMV7M
+       select ARCH_HAS_RESET_CONTROLLER
+       select ARM_AMBA
+       select CLKSRC_LPC32XX
+       select PINCTRL
+       help
+         Support for NXP's LPC18xx Cortex-M3 and LPC43xx Cortex-M4
+         high performance microcontrollers.
+
+config ARCH_STM32
+       bool "STMicrolectronics STM32"
+       depends on ARM_SINGLE_ARMV7M
+       select ARCH_HAS_RESET_CONTROLLER
+       select ARMV7M_SYSTICK
+       select CLKSRC_STM32
+       select RESET_CONTROLLER
+       help
+         Support for STMicroelectronics STM32 processors.
+
 # Definitions to make life easier
 config ARCH_ACORN
        bool
@@ -1477,7 +1510,8 @@ config ARM_PSCI
 # selected platforms.
 config ARCH_NR_GPIO
        int
-       default 1024 if ARCH_SHMOBILE || ARCH_TEGRA || ARCH_ZYNQ
+       default 1024 if ARCH_BRCMSTB || ARCH_SHMOBILE || ARCH_TEGRA || \
+               ARCH_ZYNQ
        default 512 if ARCH_EXYNOS || ARCH_KEYSTONE || SOC_OMAP5 || \
                SOC_DRA7XX || ARCH_S3C24XX || ARCH_S3C64XX || ARCH_S5PV210
        default 416 if ARCH_SUNXI
index 0c12ffb155a23c604c9bbb9b849a913d359e34ae..a6b5d0e35968e66793a95814dfca0e4415084958 100644 (file)
@@ -410,6 +410,13 @@ choice
                  Say Y here if you want kernel low-level debugging support
                  on i.MX6SX.
 
+       config DEBUG_IMX7D_UART
+               bool "i.MX7D Debug UART"
+               depends on SOC_IMX7D
+               help
+                 Say Y here if you want kernel low-level debugging support
+                 on i.MX7D.
+
        config DEBUG_KEYSTONE_UART0
                bool "Kernel low-level debugging on KEYSTONE2 using UART0"
                depends on ARCH_KEYSTONE
@@ -433,6 +440,14 @@ choice
                  Say Y here if you want kernel low-level debugging support
                  on KS8695.
 
+       config DEBUG_LPC18XX_UART0
+               bool "Kernel low-level debugging via LPC18xx/43xx UART0"
+               depends on ARCH_LPC18XX
+               select DEBUG_UART_8250
+               help
+                 Say Y here if you want kernel low-level debugging support
+                 on NXP LPC18xx/43xx UART0.
+
        config DEBUG_MESON_UARTAO
                bool "Kernel low-level debugging via Meson6 UARTAO"
                depends on ARCH_MESON
@@ -908,13 +923,22 @@ choice
                  on SA-11x0 UART ports. The kernel will check for the first
                  enabled UART in a sequence 3-1-2.
 
-       config DEBUG_SOCFPGA_UART
+       config DEBUG_SOCFPGA_UART0
+               depends on ARCH_SOCFPGA
+               bool "Use SOCFPGA UART0 for low-level debug"
+               select DEBUG_UART_8250
+               help
+                 Say Y here if you want kernel low-level debugging support
+                 on SOCFPGA(Cyclone 5 and Arria 5) based platforms.
+
+       config DEBUG_SOCFPGA_UART1
                depends on ARCH_SOCFPGA
-               bool "Use SOCFPGA UART for low-level debug"
+               bool "Use SOCFPGA UART1 for low-level debug"
                select DEBUG_UART_8250
                help
                  Say Y here if you want kernel low-level debugging support
-                 on SOCFPGA based platforms.
+                 on SOCFPGA(Arria 10) based platforms.
+
 
        config DEBUG_SUN9I_UART0
                bool "Kernel low-level debugging messages via sun9i UART0"
@@ -1157,6 +1181,18 @@ choice
                  For more details about semihosting, please see
                  chapter 8 of DUI0203I_rvct_developer_guide.pdf from ARM Ltd.
 
+       config DEBUG_ZTE_ZX
+               bool "Use ZTE ZX UART"
+               select DEBUG_UART_PL01X
+               depends on ARCH_ZX
+               help
+                 Say Y here if you are enabling ZTE ZX296702 SOC and need
+                 debug uart support.
+
+                 This option is preferred over the platform specific
+                 options; the platform specific options are deprecated
+                 and will be soon removed.
+
        config DEBUG_LL_UART_8250
                bool "Kernel low-level debugging via 8250 UART"
                help
@@ -1231,7 +1267,8 @@ config DEBUG_IMX_UART_PORT
                                                DEBUG_IMX53_UART || \
                                                DEBUG_IMX6Q_UART || \
                                                DEBUG_IMX6SL_UART || \
-                                               DEBUG_IMX6SX_UART
+                                               DEBUG_IMX6SX_UART || \
+                                               DEBUG_IMX7D_UART
        default 1
        depends on ARCH_MXC
        help
@@ -1281,7 +1318,8 @@ config DEBUG_LL_INCLUDE
                                 DEBUG_IMX53_UART ||\
                                 DEBUG_IMX6Q_UART || \
                                 DEBUG_IMX6SL_UART || \
-                                DEBUG_IMX6SX_UART
+                                DEBUG_IMX6SX_UART || \
+                                DEBUG_IMX7D_UART
        default "debug/ks8695.S" if DEBUG_KS8695_UART
        default "debug/msm.S" if DEBUG_QCOM_UARTDM
        default "debug/netx.S" if DEBUG_NETX_UART
@@ -1337,6 +1375,7 @@ config DEBUG_UART_PHYS
        default 0x02531000 if DEBUG_KEYSTONE_UART1
        default 0x03010fe0 if ARCH_RPC
        default 0x07000000 if DEBUG_SUN9I_UART0
+       default 0x09405000 if DEBUG_ZTE_ZX
        default 0x10009000 if DEBUG_REALVIEW_STD_PORT || \
                                DEBUG_VEXPRESS_UART0_CA9
        default 0x1010c000 if DEBUG_REALVIEW_PB1176_PORT
@@ -1359,6 +1398,7 @@ config DEBUG_UART_PHYS
        default 0x20201000 if DEBUG_BCM2835
        default 0x3e000000 if DEBUG_BCM_KONA_UART
        default 0x4000e400 if DEBUG_LL_UART_EFM32
+       default 0x40081000 if DEBUG_LPC18XX_UART0
        default 0x40090000 if ARCH_LPC32XX
        default 0x40100000 if DEBUG_PXA_UART1
        default 0x42000000 if ARCH_GEMINI
@@ -1407,7 +1447,8 @@ config DEBUG_UART_PHYS
        default 0xfd883000 if DEBUG_ALPINE_UART0
        default 0xfe800000 if ARCH_IOP32X
        default 0xff690000 if DEBUG_RK32_UART2
-       default 0xffc02000 if DEBUG_SOCFPGA_UART
+       default 0xffc02000 if DEBUG_SOCFPGA_UART0
+       default 0xffc02100 if DEBUG_SOCFPGA_UART1
        default 0xffd82340 if ARCH_IOP13XX
        default 0xffe40000 if DEBUG_RCAR_GEN1_SCIF0
        default 0xffe42000 if DEBUG_RCAR_GEN1_SCIF2
@@ -1466,6 +1507,7 @@ config DEBUG_UART_VIRT
        default 0xfb009000 if DEBUG_REALVIEW_STD_PORT
        default 0xfb10c000 if DEBUG_REALVIEW_PB1176_PORT
        default 0xfc40ab00 if DEBUG_BRCMSTB_UART
+       default 0xfc705000 if DEBUG_ZTE_ZX
        default 0xfcfe8600 if DEBUG_UART_BCM63XX
        default 0xfd000000 if ARCH_SPEAR3XX || ARCH_SPEAR6XX
        default 0xfd000000 if ARCH_SPEAR13XX
@@ -1485,7 +1527,8 @@ config DEBUG_UART_VIRT
        default 0xfeb26000 if DEBUG_RK3X_UART1
        default 0xfeb30c00 if DEBUG_KEYSTONE_UART0
        default 0xfeb31000 if DEBUG_KEYSTONE_UART1
-       default 0xfec02000 if DEBUG_SOCFPGA_UART
+       default 0xfec02000 if DEBUG_SOCFPGA_UART0
+       default 0xfec02100 if DEBUG_SOCFPGA_UART1
        default 0xfec12000 if DEBUG_MVEBU_UART0 || DEBUG_MVEBU_UART0_ALTERNATE
        default 0xfec12100 if DEBUG_MVEBU_UART1_ALTERNATE
        default 0xfec10000 if DEBUG_SIRFATLAS7_UART0
@@ -1530,8 +1573,9 @@ config DEBUG_UART_8250_WORD
        bool "Use 32-bit accesses for 8250 UART"
        depends on DEBUG_LL_UART_8250 || DEBUG_UART_8250
        depends on DEBUG_UART_8250_SHIFT >= 2
-       default y if DEBUG_PICOXCELL_UART || DEBUG_SOCFPGA_UART || \
-               ARCH_KEYSTONE || DEBUG_ALPINE_UART0 || \
+       default y if DEBUG_PICOXCELL_UART || DEBUG_SOCFPGA_UART0 || \
+               DEBUG_SOCFPGA_UART1 || ARCH_KEYSTONE || \
+               DEBUG_ALPINE_UART0 || \
                DEBUG_DAVINCI_DMx_UART0 || DEBUG_DAVINCI_DA8XX_UART1 || \
                DEBUG_DAVINCI_DA8XX_UART2 || \
                DEBUG_BCM_KONA_UART || DEBUG_RK32_UART2 || \
@@ -1544,7 +1588,7 @@ config DEBUG_UART_8250_FLOW_CONTROL
 
 config DEBUG_UNCOMPRESS
        bool
-       depends on ARCH_MULTIPLATFORM || PLAT_SAMSUNG
+       depends on ARCH_MULTIPLATFORM || PLAT_SAMSUNG || ARM_SINGLE_ARMV7M
        default y if DEBUG_LL && !DEBUG_OMAP2PLUS_UART && \
                     (!DEBUG_TEGRA_UART || !ZBOOT_ROM)
        help
@@ -1561,7 +1605,7 @@ config DEBUG_UNCOMPRESS
 config UNCOMPRESS_INCLUDE
        string
        default "debug/uncompress.h" if ARCH_MULTIPLATFORM || ARCH_MSM || \
-                                       PLAT_SAMSUNG || ARCH_EFM32 || \
+                                       PLAT_SAMSUNG || ARM_SINGLE_ARMV7M || \
                                        ARCH_SHMOBILE_LEGACY
        default "mach/uncompress.h"
 
index 985227cbbd1bd797546c36099dcd7cc17c0efc4f..2a4fae7e9c44b4d647fa0c2222673edbdecded13 100644 (file)
@@ -167,6 +167,7 @@ machine-$(CONFIG_ARCH_IOP33X)               += iop33x
 machine-$(CONFIG_ARCH_IXP4XX)          += ixp4xx
 machine-$(CONFIG_ARCH_KEYSTONE)                += keystone
 machine-$(CONFIG_ARCH_KS8695)          += ks8695
+machine-$(CONFIG_ARCH_LPC18XX)         += lpc18xx
 machine-$(CONFIG_ARCH_LPC32XX)         += lpc32xx
 machine-$(CONFIG_ARCH_MESON)           += meson
 machine-$(CONFIG_ARCH_MMP)             += mmp
@@ -196,14 +197,17 @@ machine-$(CONFIG_ARCH_SHMOBILE)   += shmobile
 machine-$(CONFIG_ARCH_SIRF)            += prima2
 machine-$(CONFIG_ARCH_SOCFPGA)         += socfpga
 machine-$(CONFIG_ARCH_STI)             += sti
+machine-$(CONFIG_ARCH_STM32)           += stm32
 machine-$(CONFIG_ARCH_SUNXI)           += sunxi
 machine-$(CONFIG_ARCH_TEGRA)           += tegra
 machine-$(CONFIG_ARCH_U300)            += u300
 machine-$(CONFIG_ARCH_U8500)           += ux500
+machine-$(CONFIG_ARCH_UNIPHIER)                += uniphier
 machine-$(CONFIG_ARCH_VERSATILE)       += versatile
 machine-$(CONFIG_ARCH_VEXPRESS)                += vexpress
 machine-$(CONFIG_ARCH_VT8500)          += vt8500
 machine-$(CONFIG_ARCH_W90X900)         += w90x900
+machine-$(CONFIG_ARCH_ZX)              += zx
 machine-$(CONFIG_ARCH_ZYNQ)            += zynq
 machine-$(CONFIG_PLAT_SPEAR)           += spear
 
index 992736b5229ba7bd06497feb35ecff5fc36ab232..c52002c802f8c2039786f2f770d31b9919171c3b 100644 (file)
@@ -660,6 +660,7 @@ dtb-$(CONFIG_ARCH_MEDIATEK) += \
        mt6592-evb.dtb \
        mt8127-moose.dtb \
        mt8135-evbp1.dtb
+dtb-$(CONFIG_ARCH_ZX) += zx296702-ad1.dtb
 endif
 
 always         := $(dtb-y)
diff --git a/arch/arm/boot/dts/zx296702-ad1.dts b/arch/arm/boot/dts/zx296702-ad1.dts
new file mode 100644 (file)
index 0000000..081f980
--- /dev/null
@@ -0,0 +1,48 @@
+
+/dts-v1/;
+
+#include "zx296702.dtsi"
+
+/ {
+       model = "ZTE ZX296702 AD1 Board";
+       compatible = "zte,zx296702-ad1", "zte,zx296702";
+
+       aliases {
+               serial0 = &uart0;
+               serial1 = &uart1;
+       };
+
+       memory {
+               reg = <0x50000000 0x20000000>;
+       };
+};
+
+&mmc0 {
+       num-slots = <1>;
+       supports-highspeed;
+       non-removable;
+       disable-wp;
+       status = "okay";
+
+       slot@0 {
+               reg = <0>;
+               bus-width = <4>;
+       };
+};
+
+&mmc1 {
+       num-slots = <1>;
+       supports-highspeed;
+       non-removable;
+       disable-wp;
+       status = "okay";
+
+       slot@0 {
+               reg = <0>;
+               bus-width = <8>;
+       };
+};
+
+&uart0 {
+       status = "okay";
+};
diff --git a/arch/arm/boot/dts/zx296702.dtsi b/arch/arm/boot/dts/zx296702.dtsi
new file mode 100644 (file)
index 0000000..d45c8fc
--- /dev/null
@@ -0,0 +1,139 @@
+
+#include "skeleton.dtsi"
+#include <dt-bindings/clock/zx296702-clock.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+
+/ {
+       cpus {
+               #address-cells = <1>;
+               #size-cells = <0>;
+               enable-method = "zte,zx296702-smp";
+
+               cpu@0 {
+                       compatible = "arm,cortex-a9";
+                       device_type = "cpu";
+                       next-level-cache = <&l2cc>;
+                       reg = <0>;
+               };
+
+               cpu@1 {
+                       compatible = "arm,cortex-a9";
+                       device_type = "cpu";
+                       next-level-cache = <&l2cc>;
+                       reg = <1>;
+               };
+       };
+
+
+       soc {
+               #address-cells = <1>;
+               #size-cells = <1>;
+               compatible = "simple-bus";
+               interrupt-parent = <&intc>;
+               ranges;
+
+               matrix: bus-matrix@400000 {
+                       compatible = "zte,zx-bus-matrix";
+                       reg = <0x00400000 0x1000>;
+               };
+
+               intc: interrupt-controller@00801000 {
+                       compatible = "arm,cortex-a9-gic";
+                       #interrupt-cells = <3>;
+                       #address-cells = <1>;
+                       #size-cells = <1>;
+                       interrupt-controller;
+                       reg = <0x00801000 0x1000>,
+                             <0x00800100 0x100>;
+               };
+
+               global_timer: timer@008000200 {
+                       compatible = "arm,cortex-a9-global-timer";
+                       reg = <0x00800200 0x20>;
+                       interrupts = <GIC_PPI 11 IRQ_TYPE_LEVEL_HIGH>;
+                       interrupt-parent = <&intc>;
+                       clocks = <&topclk ZX296702_A9_PERIPHCLK>;
+               };
+
+               l2cc: l2-cache-controller@0x00c00000 {
+                       compatible = "arm,pl310-cache";
+                       reg = <0x00c00000 0x1000>;
+                       cache-unified;
+                       cache-level = <2>;
+                       arm,data-latency = <1 1 1>;
+                       arm,tag-latency = <1 1 1>;
+                       arm,double-linefill = <1>;
+                       arm,double-linefill-incr = <0>;
+               };
+
+               pcu: pcu@0xa0008000 {
+                       compatible = "zte,zx296702-pcu";
+                       reg = <0xa0008000 0x1000>;
+               };
+
+               topclk: topclk@0x09800000 {
+                       compatible = "zte,zx296702-topcrm-clk";
+                       reg = <0x09800000 0x1000>;
+                       #clock-cells = <1>;
+               };
+
+               lsp1clk: lsp1clk@0x09400000 {
+                       compatible = "zte,zx296702-lsp1crpm-clk";
+                       reg = <0x09400000 0x1000>;
+                       #clock-cells = <1>;
+               };
+
+               lsp0clk: lsp0clk@0x0b000000 {
+                       compatible = "zte,zx296702-lsp0crpm-clk";
+                       reg = <0x0b000000 0x1000>;
+                       #clock-cells = <1>;
+               };
+
+               uart0: serial@0x09405000 {
+                       compatible = "zte,zx296702-uart";
+                       reg = <0x09405000 0x1000>;
+                       interrupts = <GIC_SPI 37 IRQ_TYPE_LEVEL_HIGH>;
+                       clocks = <&lsp1clk ZX296702_UART0_WCLK>;
+                       status = "disabled";
+               };
+
+               uart1: serial@0x09406000 {
+                       compatible = "zte,zx296702-uart";
+                       reg = <0x09406000 0x1000>;
+                       interrupts = <GIC_SPI 38 IRQ_TYPE_LEVEL_HIGH>;
+                       clocks = <&lsp1clk ZX296702_UART1_WCLK>;
+                       status = "disabled";
+               };
+
+               mmc0: mmc@0x09408000 {
+                       compatible = "snps,dw-mshc";
+                       #address-cells = <1>;
+                       #size-cells = <0>;
+                       reg = <0x09408000 0x1000>;
+                       interrupts = <GIC_SPI 40 IRQ_TYPE_LEVEL_HIGH>;
+                       fifo-depth = <32>;
+                       clocks = <&lsp1clk ZX296702_SDMMC0_PCLK>,
+                                <&lsp1clk ZX296702_SDMMC0_WCLK>;
+                       clock-names = "biu", "ciu";
+                       status = "disabled";
+               };
+
+               mmc1: mmc@0x0b003000 {
+                       compatible = "snps,dw-mshc";
+                       #address-cells = <1>;
+                       #size-cells = <0>;
+                       reg = <0x0b003000 0x1000>;
+                       interrupts = <GIC_SPI 20 IRQ_TYPE_LEVEL_HIGH>;
+                       fifo-depth = <32>;
+                       clocks = <&lsp0clk ZX296702_SDMMC1_PCLK>,
+                                <&lsp0clk ZX296702_SDMMC1_WCLK>;
+                       clock-names = "biu", "ciu";
+                       status = "disabled";
+               };
+
+               sysctrl: sysctrl@0xa0007000 {
+                       compatible = "zte,sysctrl", "syscon";
+                       reg = <0xa0007000 0x1000>;
+               };
+       };
+};
index c4c17e3a8e1aa32694b6b8950b67b2daba5b50d5..e969f7884deb0ce18c0d46d515c80ce9b8d2d3a1 100644 (file)
@@ -16,6 +16,7 @@ CONFIG_EMBEDDED=y
 # CONFIG_IOSCHED_DEADLINE is not set
 # CONFIG_IOSCHED_CFQ is not set
 # CONFIG_MMU is not set
+CONFIG_ARM_SINGLE_ARMV7M=y
 CONFIG_ARCH_EFM32=y
 CONFIG_SET_MEM_PARAM=y
 CONFIG_DRAM_BASE=0x88000000
diff --git a/arch/arm/configs/zx_defconfig b/arch/arm/configs/zx_defconfig
new file mode 100644 (file)
index 0000000..b200bb0
--- /dev/null
@@ -0,0 +1,129 @@
+CONFIG_EXPERIMENTAL=y
+CONFIG_SYSVIPC=y
+CONFIG_NO_HZ=y
+CONFIG_HIGH_RES_TIMERS=y
+CONFIG_LOG_BUF_SHIFT=14
+CONFIG_CGROUPS=y
+CONFIG_CGROUP_DEBUG=y
+CONFIG_CGROUP_FREEZER=y
+CONFIG_CGROUP_CPUACCT=y
+CONFIG_RESOURCE_COUNTERS=y
+CONFIG_CGROUP_SCHED=y
+CONFIG_RT_GROUP_SCHED=y
+CONFIG_NAMESPACES=y
+CONFIG_USER_NS=y
+CONFIG_BLK_DEV_INITRD=y
+CONFIG_SYSCTL_SYSCALL=y
+CONFIG_KALLSYMS_ALL=y
+CONFIG_EMBEDDED=y
+CONFIG_PERF_EVENTS=y
+CONFIG_SLAB=y
+# CONFIG_BLK_DEV_BSG is not set
+# CONFIG_IOSCHED_CFQ is not set
+CONFIG_ARCH_ZX=y
+CONFIG_SOC_ZX296702=y
+# CONFIG_SWP_EMULATE is not set
+CONFIG_ARM_ERRATA_754322=y
+CONFIG_ARM_ERRATA_775420=y
+CONFIG_SMP=y
+CONFIG_VMSPLIT_2G=y
+CONFIG_PREEMPT=y
+CONFIG_AEABI=y
+CONFIG_KSM=y
+# CONFIG_IOMMU_SUPPORT is not set
+CONFIG_VFP=y
+CONFIG_NEON=y
+CONFIG_KERNEL_MODE_NEON=y
+# CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set
+CONFIG_HIBERNATION=y
+CONFIG_PM_RUNTIME=y
+CONFIG_PM_DEBUG=y
+CONFIG_SUSPEND_TIME=y
+CONFIG_ZBOOT_ROM_TEXT=0x0
+CONFIG_ZBOOT_ROM_BSS=0x0
+CONFIG_CMDLINE="console=ttyAMA0,115200 debug earlyprintk root=/dev/ram rw rootwait"
+#CONFIG_NET is not set
+CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug"
+CONFIG_DEVTMPFS=y
+CONFIG_DEVTMPFS_MOUNT=y
+CONFIG_DMA_CMA=y
+CONFIG_CMA_SIZE_MBYTES=192
+CONFIG_BLK_DEV_LOOP=y
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_COUNT=1
+CONFIG_BLK_DEV_RAM_SIZE=8192
+CONFIG_UID_STAT=y
+CONFIG_SCSI=y
+CONFIG_BLK_DEV_SD=y
+CONFIG_CHR_DEV_SG=y
+CONFIG_CHR_DEV_SCH=y
+CONFIG_SCSI_MULTI_LUN=y
+CONFIG_MD=y
+CONFIG_BLK_DEV_DM=y
+CONFIG_DM_CRYPT=y
+CONFIG_DM_UEVENT=y
+CONFIG_DM_VERITY=y
+CONFIG_NETDEVICES=y
+# CONFIG_INPUT_MOUSE is not set
+CONFIG_SERIO=y
+CONFIG_SERIO_LIBPS2=y
+CONFIG_SPI=y
+CONFIG_LOGO=y
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_CONSOLE_POLL=y
+CONFIG_SERIAL_AMBA_PL011=y
+CONFIG_SERIAL_AMBA_PL011_CONSOLE=y
+CONFIG_SERIAL_OF_PLATFORM=y
+# CONFIG_LEGACY_PTYS is not set
+# CONFIG_HW_RANDOM is not set
+# CONFIG_HWMON is not set
+# CONFIG_USB_SUPPORT is not set
+CONFIG_MMC=y
+CONFIG_MMC_UNSAFE_RESUME=y
+CONFIG_MMC_BLOCK_MINORS=16
+CONFIG_MMC_DW=y
+CONFIG_MMC_DW_IDMAC=y
+CONFIG_EXT2_FS=y
+CONFIG_EXT4_FS=y
+CONFIG_EXT4_FS_POSIX_ACL=y
+CONFIG_EXT4_FS_SECURITY=y
+CONFIG_EXT4_DEBUG=y
+CONFIG_FUSE_FS=y
+CONFIG_MSDOS_FS=y
+CONFIG_VFAT_FS=y
+CONFIG_FAT_DEFAULT_CODEPAGE=936
+CONFIG_TMPFS=y
+CONFIG_TMPFS_POSIX_ACL=y
+#CONFIG_NFS_FS is not set
+CONFIG_NLS_CODEPAGE_936=y
+CONFIG_NLS_ISO8859_1=y
+CONFIG_NLS_UTF8=y
+CONFIG_PRINTK_TIME=y
+CONFIG_MAGIC_SYSRQ=y
+CONFIG_DEBUG_KERNEL=y
+CONFIG_DEBUG_INFO=y
+CONFIG_FRAME_WARN=4096
+CONFIG_DEBUG_FS=y
+CONFIG_DEBUG_MEMORY_INIT=y
+CONFIG_PANIC_TIMEOUT=5
+# CONFIG_SCHED_DEBUG is not set
+CONFIG_SCHEDSTATS=y
+CONFIG_TIMER_STATS=y
+CONFIG_DEBUG_RT_MUTEXES=y
+CONFIG_DEBUG_SPINLOCK=y
+CONFIG_DEBUG_MUTEXES=y
+CONFIG_RCU_CPU_STALL_TIMEOUT=60
+# CONFIG_FTRACE is not set
+CONFIG_KGDB=y
+CONFIG_KGDB_KDB=y
+# CONFIG_ARM_UNWIND is not set
+CONFIG_DEBUG_PREEMPT=y
+CONFIG_DEBUG_USER=y
+CONFIG_DEBUG_LL=y
+CONFIG_DYNAMIC_DEBUG=y
+CONFIG_STACKTRACE=y
+CONFIG_DEBUG_ZTE_ZX=y
+CONFIG_EARLY_PRINTK=y
+CONFIG_CRYPTO_LZO=y
+CONFIG_GPIOLIB=y
index 89aefe10d66b78102919d05860eb89715d01f85d..34c1d96ef46df68f0f354c111c121f9cee1067ca 100644 (file)
@@ -33,6 +33,10 @@ struct firmware_ops {
         * Sets boot address of specified physical CPU
         */
        int (*set_cpu_boot_addr)(int cpu, unsigned long boot_addr);
+       /*
+        * Gets boot address of specified physical CPU
+        */
+       int (*get_cpu_boot_addr)(int cpu, unsigned long *boot_addr);
        /*
         * Boots specified physical CPU
         */
index ee5f3084243cfa5c341a8da1320fe5ad21757cde..22e414056a8c253822012c18d389122317fdbfc1 100644 (file)
@@ -5,6 +5,9 @@
  * First, the standard VFP set.
  */
 
+#ifndef __ASM_VFP_H
+#define __ASM_VFP_H
+
 #define FPSID                  cr0
 #define FPSCR                  cr1
 #define MVFR1                  cr6
@@ -87,3 +90,9 @@
 #define VFPOPDESC_UNUSED_BIT   (24)
 #define VFPOPDESC_UNUSED_MASK  (0xFF << VFPOPDESC_UNUSED_BIT)
 #define VFPOPDESC_OPDESC_MASK  (~(VFPOPDESC_LENGTH_MASK | VFPOPDESC_UNUSED_MASK))
+
+#ifndef __ASSEMBLY__
+void vfp_disable(void);
+#endif
+
+#endif /* __ASM_VFP_H */
index 7a2baf913aa0bd669f58b12d028e6c86cb9dcda4..7f7446f6f8060e446c7dc8fe81d3b1a501a04f1f 100644 (file)
 
 #ifdef CONFIG_DEBUG_UART_8250_WORD
                .macro  store, rd, rx:vararg
+        ARM_BE8(rev \rd, \rd)
                str     \rd, \rx
+        ARM_BE8(rev \rd, \rd)
                .endm
 
                .macro  load, rd, rx:vararg
                ldr     \rd, \rx
+       ARM_BE8(rev \rd, \rd)
                .endm
 #else
                .macro  store, rd, rx:vararg
index 2265a199280ca2e40dab1e22d87bb02f7fb66e54..660fa1e4b77beb87bd47b4fc8c4f8fa31d19eaa5 100644 (file)
@@ -16,7 +16,7 @@
 
 #define        UARTn_TXDATA            0x0034
 
-               .macro  addruart, rx, tmp
+               .macro  addruart, rx, tmp, tmp2
                ldr     \rx, =(CONFIG_DEBUG_UART_PHYS)
 
                /*
index 032a316eb802231c7b661e85b9d4d303389d1242..66f736f746841dc6a6ad4fa935647bb7b6173484 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2012 Freescale Semiconductor, Inc.
+ * Copyright (C) 2012-2015 Freescale Semiconductor, Inc.
  *
  * 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
 #define IMX6SX_UART_BASE_ADDR(n) IMX6SX_UART##n##_BASE_ADDR
 #define IMX6SX_UART_BASE(n)    IMX6SX_UART_BASE_ADDR(n)
 
+#define IMX7D_UART1_BASE_ADDR  0x30860000
+#define IMX7D_UART2_BASE_ADDR  0x30890000
+#define IMX7D_UART3_BASE_ADDR  0x30880000
+#define IMX7D_UART4_BASE_ADDR  0x30a60000
+#define IMX7D_UART5_BASE_ADDR  0x30a70000
+#define IMX7D_UART6_BASE_ADDR  0x30a80000
+#define IMX7D_UART7_BASE_ADDR  0x30a90000
+#define IMX7D_UART_BASE_ADDR(n) IMX7D_UART##n##_BASE_ADDR
+#define IMX7D_UART_BASE(n)     IMX7D_UART_BASE_ADDR(n)
+
 #define IMX_DEBUG_UART_BASE(soc) soc##_UART_BASE(CONFIG_DEBUG_IMX_UART_PORT)
 
 #ifdef CONFIG_DEBUG_IMX1_UART
 #define UART_PADDR     IMX_DEBUG_UART_BASE(IMX6SL)
 #elif defined(CONFIG_DEBUG_IMX6SX_UART)
 #define UART_PADDR     IMX_DEBUG_UART_BASE(IMX6SX)
+#elif defined(CONFIG_DEBUG_IMX7D_UART)
+#define UART_PADDR     IMX_DEBUG_UART_BASE(IMX7D)
+
 #endif
 
 #endif /* __DEBUG_IMX_UART_H */
index 92ef808a23377275124a59550b6ab86f3e163486..f7d8323cefccf8d7beacc79b9d99805efd967060 100644 (file)
 */
 #include <linux/amba/serial.h>
 
+#ifdef CONFIG_DEBUG_ZTE_ZX
+#undef UART01x_DR
+#undef UART01x_FR
+#define UART01x_DR     0x04
+#define UART01x_FR     0x14
+#endif
+
 #ifdef CONFIG_DEBUG_UART_PHYS
                .macro  addruart, rp, rv, tmp
                ldr     \rp, =CONFIG_DEBUG_UART_PHYS
index 78c91b5f97d4943e896b4d566f71d491f9e17b22..ea9646cc2a0ed7eba2fa4f7f7638c0802642edcc 100644 (file)
@@ -35,7 +35,7 @@
 
 #else /* !CONFIG_MMU */
                .macro  addruart_current, rx, tmp1, tmp2
-               addruart        \rx, \tmp1
+               addruart        \rx, \tmp1, \tmp2
                .endm
 
 #endif /* CONFIG_MMU */
index 8b11f44bb36e5a3dcfe59cf331e18730e71c9ec5..e9184feffc4e5b55d46008be3f3587d2756ea6e3 100644 (file)
@@ -19,6 +19,7 @@ config ARCH_BCM_IPROC
        select ARCH_REQUIRE_GPIOLIB
        select ARM_AMBA
        select PINCTRL
+       select MTD_NAND_BRCMNAND
        help
          This enables support for systems based on Broadcom IPROC architected SoCs.
          The IPROC complex contains one or more ARM CPUs along with common
@@ -144,6 +145,7 @@ config ARCH_BRCMSTB
        select BRCMSTB_GISB_ARB
        select BRCMSTB_L2_IRQ
        select BCM7120_L2_IRQ
+       select ARCH_WANT_OPTIONAL_GPIOLIB
        help
          Say Y if you intend to run the kernel on a Broadcom ARM-based STB
          chipset.
index 54d274da7ccba181c8ede133a6138c597ad3fa1a..4fb0da458e9171e929f303e40a8ccc114666c8cd 100644 (file)
@@ -38,7 +38,12 @@ obj-$(CONFIG_ARCH_BCM2835)   += board_bcm2835.o
 obj-$(CONFIG_ARCH_BCM_5301X)   += bcm_5301x.o
 
 # BCM63XXx
-obj-$(CONFIG_ARCH_BCM_63XX)    := bcm63xx.o
+ifeq ($(CONFIG_ARCH_BCM_63XX),y)
+CFLAGS_bcm63xx_headsmp.o       += -march=armv7-a
+obj-y                          += bcm63xx.o
+obj-$(CONFIG_SMP)              += bcm63xx_smp.o bcm63xx_headsmp.o \
+                                  bcm63xx_pmb.o
+endif
 
 ifeq ($(CONFIG_ARCH_BRCMSTB),y)
 CFLAGS_platsmp-brcmstb.o       += -march=armv7-a
diff --git a/arch/arm/mach-bcm/bcm63xx_headsmp.S b/arch/arm/mach-bcm/bcm63xx_headsmp.S
new file mode 100644 (file)
index 0000000..c7af397
--- /dev/null
@@ -0,0 +1,23 @@
+/*
+ *  Copyright (C) 2015, Broadcom Corporation
+ *  All Rights Reserved
+ *
+ * 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/linkage.h>
+#include <linux/init.h>
+#include <asm/assembler.h>
+
+ENTRY(bcm63138_secondary_startup)
+ ARM_BE8(setend        be)
+       /*
+        * L1 cache does have unpredictable contents at power-up clean its
+        * contents without flushing
+        */
+       bl      v7_invalidate_l1
+       nop
+
+       b       secondary_startup
+ENDPROC(bcm63138_secondary_startup)
diff --git a/arch/arm/mach-bcm/bcm63xx_pmb.c b/arch/arm/mach-bcm/bcm63xx_pmb.c
new file mode 100644 (file)
index 0000000..de061ec
--- /dev/null
@@ -0,0 +1,221 @@
+/*
+ * Broadcom BCM63138 PMB initialization for secondary CPU(s)
+ *
+ * Copyright (C) 2015 Broadcom Corporation
+ * Author: Florian Fainelli <f.fainelli@gmail.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ */
+#include <linux/kernel.h>
+#include <linux/io.h>
+#include <linux/spinlock.h>
+#include <linux/reset/bcm63xx_pmb.h>
+#include <linux/of.h>
+#include <linux/of_address.h>
+
+#include "bcm63xx_smp.h"
+
+/* ARM Control register definitions */
+#define CORE_PWR_CTRL_SHIFT    0
+#define CORE_PWR_CTRL_MASK     0x3
+#define PLL_PWR_ON             BIT(8)
+#define PLL_LDO_PWR_ON         BIT(9)
+#define PLL_CLAMP_ON           BIT(10)
+#define CPU_RESET_N(x)         BIT(13 + (x))
+#define NEON_RESET_N           BIT(15)
+#define PWR_CTRL_STATUS_SHIFT  28
+#define PWR_CTRL_STATUS_MASK   0x3
+#define PWR_DOWN_SHIFT         30
+#define PWR_DOWN_MASK          0x3
+
+/* CPU Power control register definitions */
+#define MEM_PWR_OK             BIT(0)
+#define MEM_PWR_ON             BIT(1)
+#define MEM_CLAMP_ON           BIT(2)
+#define MEM_PWR_OK_STATUS      BIT(4)
+#define MEM_PWR_ON_STATUS      BIT(5)
+#define MEM_PDA_SHIFT          8
+#define MEM_PDA_MASK           0xf
+#define  MEM_PDA_CPU_MASK      0x1
+#define  MEM_PDA_NEON_MASK     0xf
+#define CLAMP_ON               BIT(15)
+#define PWR_OK_SHIFT           16
+#define PWR_OK_MASK            0xf
+#define PWR_ON_SHIFT           20
+#define  PWR_CPU_MASK          0x03
+#define  PWR_NEON_MASK         0x01
+#define PWR_ON_MASK            0xf
+#define PWR_OK_STATUS_SHIFT    24
+#define PWR_OK_STATUS_MASK     0xf
+#define PWR_ON_STATUS_SHIFT    28
+#define PWR_ON_STATUS_MASK     0xf
+
+#define ARM_CONTROL            0x30
+#define ARM_PWR_CONTROL_BASE   0x34
+#define ARM_PWR_CONTROL(x)     (ARM_PWR_CONTROL_BASE + (x) * 0x4)
+#define ARM_NEON_L2            0x3c
+
+/* Perform a value write, then spin until the value shifted by
+ * shift is seen, masked with mask and is different from cond.
+ */
+static int bpcm_wr_rd_mask(void __iomem *master,
+                          unsigned int addr, u32 off, u32 *val,
+                          u32 shift, u32 mask, u32 cond)
+{
+       int ret;
+
+       ret = bpcm_wr(master, addr, off, *val);
+       if (ret)
+               return ret;
+
+       do {
+               ret = bpcm_rd(master, addr, off, val);
+               if (ret)
+                       return ret;
+
+               cpu_relax();
+       } while (((*val >> shift) & mask) != cond);
+
+       return ret;
+}
+
+/* Global lock to serialize accesses to the PMB registers while we
+ * are bringing up the secondary CPU
+ */
+static DEFINE_SPINLOCK(pmb_lock);
+
+static int bcm63xx_pmb_get_resources(struct device_node *dn,
+                                    void __iomem **base,
+                                    unsigned int *cpu,
+                                    unsigned int *addr)
+{
+       struct device_node *pmb_dn;
+       struct of_phandle_args args;
+       int ret;
+
+       ret = of_property_read_u32(dn, "reg", cpu);
+       if (ret) {
+               pr_err("CPU is missing a reg node\n");
+               return ret;
+       }
+
+       ret = of_parse_phandle_with_args(dn, "resets", "#reset-cells",
+                                        0, &args);
+       if (ret) {
+               pr_err("CPU is missing a resets phandle\n");
+               return ret;
+       }
+
+       pmb_dn = args.np;
+       if (args.args_count != 2) {
+               pr_err("reset-controller does not conform to reset-cells\n");
+               return -EINVAL;
+       }
+
+       *base = of_iomap(args.np, 0);
+       if (!*base) {
+               pr_err("failed remapping PMB register\n");
+               return -ENOMEM;
+       }
+
+       /* We do not need the number of zones */
+       *addr = args.args[0];
+
+       return 0;
+}
+
+int bcm63xx_pmb_power_on_cpu(struct device_node *dn)
+{
+       void __iomem *base;
+       unsigned int cpu, addr;
+       unsigned long flags;
+       u32 val, ctrl;
+       int ret;
+
+       ret = bcm63xx_pmb_get_resources(dn, &base, &cpu, &addr);
+       if (ret)
+               return ret;
+
+       /* We would not know how to enable a third and greater CPU */
+       WARN_ON(cpu > 1);
+
+       spin_lock_irqsave(&pmb_lock, flags);
+
+       /* Check if the CPU is already on and save the ARM_CONTROL register
+        * value since we will use it later for CPU de-assert once done with
+        * the CPU-specific power sequence
+        */
+       ret = bpcm_rd(base, addr, ARM_CONTROL, &ctrl);
+       if (ret)
+               goto out;
+
+       if (ctrl & CPU_RESET_N(cpu)) {
+               pr_info("PMB: CPU%d is already powered on\n", cpu);
+               ret = 0;
+               goto out;
+       }
+
+       /* Power on PLL */
+       ret = bpcm_rd(base, addr, ARM_PWR_CONTROL(cpu), &val);
+       if (ret)
+               goto out;
+
+       val |= (PWR_CPU_MASK << PWR_ON_SHIFT);
+
+       ret = bpcm_wr_rd_mask(base, addr, ARM_PWR_CONTROL(cpu), &val,
+                       PWR_ON_STATUS_SHIFT, PWR_CPU_MASK, PWR_CPU_MASK);
+       if (ret)
+               goto out;
+
+       val |= (PWR_CPU_MASK << PWR_OK_SHIFT);
+
+       ret = bpcm_wr_rd_mask(base, addr, ARM_PWR_CONTROL(cpu), &val,
+                       PWR_OK_STATUS_SHIFT, PWR_CPU_MASK, PWR_CPU_MASK);
+       if (ret)
+               goto out;
+
+       val &= ~CLAMP_ON;
+
+       ret = bpcm_wr(base, addr, ARM_PWR_CONTROL(cpu), val);
+       if (ret)
+               goto out;
+
+       /* Power on CPU<N> RAM */
+       val &= ~(MEM_PDA_MASK << MEM_PDA_SHIFT);
+
+       ret = bpcm_wr(base, addr, ARM_PWR_CONTROL(cpu), val);
+       if (ret)
+               goto out;
+
+       val |= MEM_PWR_ON;
+
+       ret = bpcm_wr_rd_mask(base, addr, ARM_PWR_CONTROL(cpu), &val,
+                       0, MEM_PWR_ON_STATUS, MEM_PWR_ON_STATUS);
+       if (ret)
+               goto out;
+
+       val |= MEM_PWR_OK;
+
+       ret = bpcm_wr_rd_mask(base, addr, ARM_PWR_CONTROL(cpu), &val,
+                       0, MEM_PWR_OK_STATUS, MEM_PWR_OK_STATUS);
+       if (ret)
+               goto out;
+
+       val &= ~MEM_CLAMP_ON;
+
+       ret = bpcm_wr(base, addr, ARM_PWR_CONTROL(cpu), val);
+       if (ret)
+               goto out;
+
+       /* De-assert CPU reset */
+       ctrl |= CPU_RESET_N(cpu);
+
+       ret = bpcm_wr(base, addr, ARM_CONTROL, ctrl);
+out:
+       spin_unlock_irqrestore(&pmb_lock, flags);
+       iounmap(base);
+       return ret;
+}
diff --git a/arch/arm/mach-bcm/bcm63xx_smp.c b/arch/arm/mach-bcm/bcm63xx_smp.c
new file mode 100644 (file)
index 0000000..3f014f1
--- /dev/null
@@ -0,0 +1,169 @@
+/*
+ * Broadcom BCM63138 DSL SoCs SMP support code
+ *
+ * Copyright (C) 2015, Broadcom Corporation
+ *
+ * Licensed under the terms of the GPLv2
+ */
+
+#include <linux/delay.h>
+#include <linux/init.h>
+#include <linux/smp.h>
+#include <linux/io.h>
+#include <linux/of.h>
+#include <linux/of_address.h>
+
+#include <asm/cacheflush.h>
+#include <asm/smp_scu.h>
+#include <asm/smp_plat.h>
+#include <asm/vfp.h>
+
+#include "bcm63xx_smp.h"
+
+/* Size of mapped Cortex A9 SCU address space */
+#define CORTEX_A9_SCU_SIZE     0x58
+
+/*
+ * Enable the Cortex A9 Snoop Control Unit
+ *
+ * By the time this is called we already know there are multiple
+ * cores present.  We assume we're running on a Cortex A9 processor,
+ * so any trouble getting the base address register or getting the
+ * SCU base is a problem.
+ *
+ * Return 0 if successful or an error code otherwise.
+ */
+static int __init scu_a9_enable(void)
+{
+       unsigned long config_base;
+       void __iomem *scu_base;
+       unsigned int i, ncores;
+
+       if (!scu_a9_has_base()) {
+               pr_err("no configuration base address register!\n");
+               return -ENXIO;
+       }
+
+       /* Config base address register value is zero for uniprocessor */
+       config_base = scu_a9_get_base();
+       if (!config_base) {
+               pr_err("hardware reports only one core\n");
+               return -ENOENT;
+       }
+
+       scu_base = ioremap((phys_addr_t)config_base, CORTEX_A9_SCU_SIZE);
+       if (!scu_base) {
+               pr_err("failed to remap config base (%lu/%u) for SCU\n",
+                       config_base, CORTEX_A9_SCU_SIZE);
+               return -ENOMEM;
+       }
+
+       scu_enable(scu_base);
+
+       ncores = scu_base ? scu_get_core_count(scu_base) : 1;
+
+       if (ncores > nr_cpu_ids) {
+               pr_warn("SMP: %u cores greater than maximum (%u), clipping\n",
+                               ncores, nr_cpu_ids);
+               ncores = nr_cpu_ids;
+       }
+
+       /* The BCM63138 SoC has two Cortex-A9 CPUs, CPU0 features a complete
+        * and fully functional VFP unit that can be used, but CPU1 does not.
+        * Since we will not be able to trap kernel-mode NEON to force
+        * migration to CPU0, just do not advertise VFP support at all.
+        *
+        * This will make vfp_init bail out and do not attempt to use VFP at
+        * all, for kernel-mode NEON, we do not want to introduce any
+        * conditionals in hot-paths, so we just restrict the system to UP.
+        */
+#ifdef CONFIG_VFP
+       if (ncores > 1) {
+               pr_warn("SMP: secondary CPUs lack VFP unit, disabling VFP\n");
+               vfp_disable();
+
+#ifdef CONFIG_KERNEL_MODE_NEON
+               WARN(1, "SMP: kernel-mode NEON enabled, restricting to UP\n");
+               ncores = 1;
+#endif
+       }
+#endif
+
+       for (i = 0; i < ncores; i++)
+               set_cpu_possible(i, true);
+
+       iounmap(scu_base);      /* That's the last we'll need of this */
+
+       return 0;
+}
+
+static const struct of_device_id bcm63138_bootlut_ids[] = {
+       { .compatible = "brcm,bcm63138-bootlut", },
+       { /* sentinel */ },
+};
+
+#define BOOTLUT_RESET_VECT     0x20
+
+static int bcm63138_smp_boot_secondary(unsigned int cpu,
+                                      struct task_struct *idle)
+{
+       void __iomem *bootlut_base;
+       struct device_node *dn;
+       int ret = 0;
+       u32 val;
+
+       dn = of_find_matching_node(NULL, bcm63138_bootlut_ids);
+       if (!dn) {
+               pr_err("SMP: unable to find bcm63138 boot LUT node\n");
+               return -ENODEV;
+       }
+
+       bootlut_base = of_iomap(dn, 0);
+       of_node_put(dn);
+
+       if (!bootlut_base) {
+               pr_err("SMP: unable to remap boot LUT base register\n");
+               return -ENOMEM;
+       }
+
+       /* Locate the secondary CPU node */
+       dn = of_get_cpu_node(cpu_logical_map(cpu), NULL);
+       if (!dn) {
+               pr_err("SMP: failed to locate secondary CPU%d node\n", cpu);
+               ret = -ENODEV;
+               goto out;
+       }
+
+       /* Write the secondary init routine to the BootLUT reset vector */
+       val = virt_to_phys(bcm63138_secondary_startup);
+       writel_relaxed(val, bootlut_base + BOOTLUT_RESET_VECT);
+
+       /* Power up the core, will jump straight to its reset vector when we
+        * return
+        */
+       ret = bcm63xx_pmb_power_on_cpu(dn);
+       if (ret)
+               goto out;
+out:
+       iounmap(bootlut_base);
+
+       return ret;
+}
+
+static void __init bcm63138_smp_prepare_cpus(unsigned int max_cpus)
+{
+       int ret;
+
+       ret = scu_a9_enable();
+       if (ret) {
+               pr_warn("SMP: Cortex-A9 SCU setup failed\n");
+               return;
+       }
+}
+
+struct smp_operations bcm63138_smp_ops __initdata = {
+       .smp_prepare_cpus       = bcm63138_smp_prepare_cpus,
+       .smp_boot_secondary     = bcm63138_smp_boot_secondary,
+};
+
+CPU_METHOD_OF_DECLARE(bcm63138_smp, "brcm,bcm63138", &bcm63138_smp_ops);
diff --git a/arch/arm/mach-bcm/bcm63xx_smp.h b/arch/arm/mach-bcm/bcm63xx_smp.h
new file mode 100644 (file)
index 0000000..50b7604
--- /dev/null
@@ -0,0 +1,9 @@
+#ifndef __BCM63XX_SMP_H
+#define __BCM63XX_SMP_H
+
+struct device_node;
+
+extern void bcm63138_secondary_startup(void);
+extern int bcm63xx_pmb_power_on_cpu(struct device_node *dn);
+
+#endif /* __BCM63XX_SMP_H */
index e9bcbdbce55550e04e83a792d55b2eba65f94c32..7aef92720eb4fc126b67b176e0bd3ab79d254957 100644 (file)
@@ -18,15 +18,16 @@ static bool first_fault = true;
 static int bcm5301x_abort_handler(unsigned long addr, unsigned int fsr,
                                 struct pt_regs *regs)
 {
-       if (fsr == 0x1c06 && first_fault) {
+       if ((fsr == 0x1406 || fsr == 0x1c06) && first_fault) {
                first_fault = false;
 
                /*
-                * These faults with code 0x1c06 happens for no good reason,
-                * possibly left over from the CFE boot loader.
+                * These faults with codes 0x1406 (BCM4709) or 0x1c06 happens
+                * for no good reason, possibly left over from the CFE boot
+                * loader.
                 */
                pr_warn("External imprecise Data abort at addr=%#lx, fsr=%#x ignored.\n",
-               addr, fsr);
+                       addr, fsr);
 
                /* Returning non-zero causes fault display and panic */
                return 0;
index 70f2f3925f0e8e08487abb20b55ba580c4026c43..0f7b9eac3d15d23dc7faa78699e119c7faad547c 100644 (file)
@@ -12,7 +12,6 @@
  * GNU General Public License for more details.
  */
 
-#include <linux/delay.h>
 #include <linux/init.h>
 #include <linux/irqchip.h>
 #include <linux/of_address.h>
 #include <asm/mach/arch.h>
 #include <asm/mach/map.h>
 
-#define PM_RSTC                                0x1c
-#define PM_RSTS                                0x20
-#define PM_WDOG                                0x24
-
-#define PM_PASSWORD                    0x5a000000
-#define PM_RSTC_WRCFG_MASK             0x00000030
-#define PM_RSTC_WRCFG_FULL_RESET       0x00000020
-#define PM_RSTS_HADWRH_SET             0x00000040
-
-#define BCM2835_PERIPH_PHYS    0x20000000
-#define BCM2835_PERIPH_VIRT    0xf0000000
-#define BCM2835_PERIPH_SIZE    SZ_16M
-
-static void __iomem *wdt_regs;
-
-/*
- * The machine restart method can be called from an atomic context so we won't
- * be able to ioremap the regs then.
- */
-static void bcm2835_setup_restart(void)
-{
-       struct device_node *np = of_find_compatible_node(NULL, NULL,
-                                               "brcm,bcm2835-pm-wdt");
-       if (WARN(!np, "unable to setup watchdog restart"))
-               return;
-
-       wdt_regs = of_iomap(np, 0);
-       WARN(!wdt_regs, "failed to remap watchdog regs");
-}
-
-static void bcm2835_restart(enum reboot_mode mode, const char *cmd)
-{
-       u32 val;
-
-       if (!wdt_regs)
-               return;
-
-       /* use a timeout of 10 ticks (~150us) */
-       writel_relaxed(10 | PM_PASSWORD, wdt_regs + PM_WDOG);
-       val = readl_relaxed(wdt_regs + PM_RSTC);
-       val &= ~PM_RSTC_WRCFG_MASK;
-       val |= PM_PASSWORD | PM_RSTC_WRCFG_FULL_RESET;
-       writel_relaxed(val, wdt_regs + PM_RSTC);
-
-       /* No sleeping, possibly atomic. */
-       mdelay(1);
-}
-
-/*
- * We can't really power off, but if we do the normal reset scheme, and
- * indicate to bootcode.bin not to reboot, then most of the chip will be
- * powered off.
- */
-static void bcm2835_power_off(void)
-{
-       u32 val;
-
-       /*
-        * We set the watchdog hard reset bit here to distinguish this reset
-        * from the normal (full) reset. bootcode.bin will not reboot after a
-        * hard reset.
-        */
-       val = readl_relaxed(wdt_regs + PM_RSTS);
-       val &= ~PM_RSTC_WRCFG_MASK;
-       val |= PM_PASSWORD | PM_RSTS_HADWRH_SET;
-       writel_relaxed(val, wdt_regs + PM_RSTS);
-
-       /* Continue with normal reset mechanism */
-       bcm2835_restart(REBOOT_HARD, "");
-}
-
-static struct map_desc io_map __initdata = {
-       .virtual = BCM2835_PERIPH_VIRT,
-       .pfn = __phys_to_pfn(BCM2835_PERIPH_PHYS),
-       .length = BCM2835_PERIPH_SIZE,
-       .type = MT_DEVICE
-};
-
-static void __init bcm2835_map_io(void)
-{
-       iotable_init(&io_map, 1);
-}
-
 static void __init bcm2835_init(void)
 {
        int ret;
 
-       bcm2835_setup_restart();
-       if (wdt_regs)
-               pm_power_off = bcm2835_power_off;
-
        bcm2835_init_clocks();
 
        ret = of_platform_populate(NULL, of_default_bus_match_table, NULL,
@@ -129,9 +41,6 @@ static const char * const bcm2835_compat[] = {
 };
 
 DT_MACHINE_START(BCM2835, "BCM2835")
-       .map_io = bcm2835_map_io,
-       .init_irq = irqchip_init,
        .init_machine = bcm2835_init,
-       .restart = bcm2835_restart,
        .dt_compat = bcm2835_compat
 MACHINE_END
index 36f22c1a31fe596a71c596aa21d4e589435f15ba..3c950f5864f34194b87f39c526ec3ac1b58c0f84 100644 (file)
 #include <linux/platform_device.h>
 #include <linux/i2c.h>
 #include <linux/i2c-gpio.h>
+#include <linux/mmc/host.h>
+#include <linux/spi/spi.h>
+#include <linux/spi/mmc_spi.h>
+#include <linux/platform_data/video-ep93xx.h>
+#include <linux/platform_data/spi-ep93xx.h>
+#include <linux/gpio.h>
 
 #include <mach/hardware.h>
-#include <linux/platform_data/video-ep93xx.h>
 #include <mach/gpio-ep93xx.h>
 
 #include <asm/mach-types.h>
@@ -40,6 +45,132 @@ static struct ep93xxfb_mach_info __initdata simone_fb_info = {
        .flags          = EP93XXFB_USE_SDCSN0 | EP93XXFB_PCLK_FALLING,
 };
 
+/*
+ * GPIO lines used for MMC card detection.
+ */
+#define MMC_CARD_DETECT_GPIO EP93XX_GPIO_LINE_EGPIO0
+
+/*
+ * Up to v1.3, the Sim.One used SFRMOUT as SD card chip select, but this goes
+ * low between multi-message command blocks. From v1.4, it uses a GPIO instead.
+ * v1.3 parts will still work, since the signal on SFRMOUT is automatic.
+ */
+#define MMC_CHIP_SELECT_GPIO EP93XX_GPIO_LINE_EGPIO1
+
+/*
+ * MMC SPI chip select GPIO handling. If you are using SFRMOUT (SFRM1) signal,
+ * you can leave these empty and pass NULL as .controller_data.
+ */
+
+static int simone_mmc_spi_setup(struct spi_device *spi)
+{
+       unsigned int gpio = MMC_CHIP_SELECT_GPIO;
+       int err;
+
+       err = gpio_request(gpio, spi->modalias);
+       if (err)
+               return err;
+
+       err = gpio_direction_output(gpio, 1);
+       if (err) {
+               gpio_free(gpio);
+               return err;
+       }
+
+       return 0;
+}
+
+static void simone_mmc_spi_cleanup(struct spi_device *spi)
+{
+       unsigned int gpio = MMC_CHIP_SELECT_GPIO;
+
+       gpio_set_value(gpio, 1);
+       gpio_direction_input(gpio);
+       gpio_free(gpio);
+}
+
+static void simone_mmc_spi_cs_control(struct spi_device *spi, int value)
+{
+       gpio_set_value(MMC_CHIP_SELECT_GPIO, value);
+}
+
+static struct ep93xx_spi_chip_ops simone_mmc_spi_ops = {
+       .setup          = simone_mmc_spi_setup,
+       .cleanup        = simone_mmc_spi_cleanup,
+       .cs_control     = simone_mmc_spi_cs_control,
+};
+
+/*
+ * MMC card detection GPIO setup.
+ */
+
+static int simone_mmc_spi_init(struct device *dev,
+       irqreturn_t (*irq_handler)(int, void *), void *mmc)
+{
+       unsigned int gpio = MMC_CARD_DETECT_GPIO;
+       int irq, err;
+
+       err = gpio_request(gpio, dev_name(dev));
+       if (err)
+               return err;
+
+       err = gpio_direction_input(gpio);
+       if (err)
+               goto fail;
+
+       irq = gpio_to_irq(gpio);
+       if (irq < 0)
+               goto fail;
+
+       err = request_irq(irq, irq_handler, IRQF_TRIGGER_FALLING,
+                         "MMC card detect", mmc);
+       if (err)
+               goto fail;
+
+       printk(KERN_INFO "%s: using irq %d for MMC card detection\n",
+              dev_name(dev), irq);
+
+       return 0;
+fail:
+       gpio_free(gpio);
+       return err;
+}
+
+static void simone_mmc_spi_exit(struct device *dev, void *mmc)
+{
+       unsigned int gpio = MMC_CARD_DETECT_GPIO;
+
+       free_irq(gpio_to_irq(gpio), mmc);
+       gpio_free(gpio);
+}
+
+static struct mmc_spi_platform_data simone_mmc_spi_data = {
+       .init           = simone_mmc_spi_init,
+       .exit           = simone_mmc_spi_exit,
+       .detect_delay   = 500,
+       .ocr_mask       = MMC_VDD_32_33 | MMC_VDD_33_34,
+};
+
+static struct spi_board_info simone_spi_devices[] __initdata = {
+       {
+               .modalias               = "mmc_spi",
+               .controller_data        = &simone_mmc_spi_ops,
+               .platform_data          = &simone_mmc_spi_data,
+               /*
+                * We use 10 MHz even though the maximum is 3.7 MHz. The driver
+                * will limit it automatically to max. frequency.
+                */
+               .max_speed_hz           = 10 * 1000 * 1000,
+               .bus_num                = 0,
+               .chip_select            = 0,
+               .mode                   = SPI_MODE_3,
+       },
+};
+
+static struct ep93xx_spi_info simone_spi_info __initdata = {
+       .num_chipselect = ARRAY_SIZE(simone_spi_devices),
+};
+
 static struct i2c_gpio_platform_data __initdata simone_i2c_gpio_data = {
        .sda_pin                = EP93XX_GPIO_LINE_EEDAT,
        .sda_is_open_drain      = 0,
@@ -74,6 +205,8 @@ static void __init simone_init_machine(void)
        ep93xx_register_fb(&simone_fb_info);
        ep93xx_register_i2c(&simone_i2c_gpio_data, simone_i2c_board_info,
                            ARRAY_SIZE(simone_i2c_board_info));
+       ep93xx_register_spi(&simone_spi_info, simone_spi_devices,
+                           ARRAY_SIZE(simone_spi_devices));
        simone_register_audio();
 }
 
index 5f5cd562c593ef5f6a9224254c146e7d3d0136a3..e3a9256ed55fecc49e65aea229e74f82e933a91f 100644 (file)
@@ -163,7 +163,9 @@ extern void exynos_set_delayed_reset_assertion(bool enable);
 
 extern void s5p_init_cpu(void __iomem *cpuid_addr);
 extern unsigned int samsung_rev(void);
-extern void __iomem *cpu_boot_reg_base(void);
+extern void exynos_core_restart(u32 core_id);
+extern int exynos_set_boot_addr(u32 core_id, unsigned long boot_addr);
+extern int exynos_get_boot_addr(u32 core_id, unsigned long *boot_addr);
 
 static inline void pmu_raw_writel(u32 val, u32 offset)
 {
index 5917a30eee33f286c80708dfb84cdd610bd2dd9d..4bd8b76538175aa2ba4ab3f58a127b94bda08939 100644 (file)
@@ -234,7 +234,8 @@ static void __init exynos_dt_machine_init(void)
                exynos_sysram_init();
 
 #if defined(CONFIG_SMP) && defined(CONFIG_ARM_EXYNOS_CPUIDLE)
-       if (of_machine_is_compatible("samsung,exynos4210"))
+       if (of_machine_is_compatible("samsung,exynos4210") ||
+           of_machine_is_compatible("samsung,exynos3250"))
                exynos_cpuidle.dev.platform_data = &cpuidle_coupled_exynos_data;
 #endif
        if (of_machine_is_compatible("samsung,exynos4210") ||
index 1bd35763f12ec04d712ace47f0f88bd2f9c95c89..245f6dec1ded11a126b9386203eed4e9572a0157 100644 (file)
@@ -49,6 +49,7 @@ static int exynos_do_idle(unsigned long mode)
                             sysram_ns_base_addr + 0x24);
                __raw_writel(EXYNOS_AFTR_MAGIC, sysram_ns_base_addr + 0x20);
                if (soc_is_exynos3250()) {
+                       flush_cache_all();
                        exynos_smc(SMC_CMD_SAVE, OP_TYPE_CORE,
                                   SMC_POWERSTATE_IDLE, 0);
                        exynos_smc(SMC_CMD_SHUTDOWN, OP_TYPE_CLUSTER,
@@ -104,6 +105,22 @@ static int exynos_set_cpu_boot_addr(int cpu, unsigned long boot_addr)
        return 0;
 }
 
+static int exynos_get_cpu_boot_addr(int cpu, unsigned long *boot_addr)
+{
+       void __iomem *boot_reg;
+
+       if (!sysram_ns_base_addr)
+               return -ENODEV;
+
+       boot_reg = sysram_ns_base_addr + 0x1c;
+
+       if (soc_is_exynos4412())
+               boot_reg += 4 * cpu;
+
+       *boot_addr = __raw_readl(boot_reg);
+       return 0;
+}
+
 static int exynos_cpu_suspend(unsigned long arg)
 {
        flush_cache_all();
@@ -138,6 +155,7 @@ static int exynos_resume(void)
 static const struct firmware_ops exynos_firmware_ops = {
        .do_idle                = IS_ENABLED(CONFIG_EXYNOS_CPU_SUSPEND) ? exynos_do_idle : NULL,
        .set_cpu_boot_addr      = exynos_set_cpu_boot_addr,
+       .get_cpu_boot_addr      = exynos_get_cpu_boot_addr,
        .cpu_boot               = exynos_cpu_boot,
        .suspend                = IS_ENABLED(CONFIG_PM_SLEEP) ? exynos_suspend : NULL,
        .resume                 = IS_ENABLED(CONFIG_EXYNOS_CPU_SUSPEND) ? exynos_resume : NULL,
index a825bca2a2b699490809676cef6f66d4eb86fd21..58e05a2eae5737c1a558c3658e692184b064da34 100644 (file)
@@ -169,7 +169,7 @@ int exynos_cluster_power_state(int cluster)
                S5P_CORE_LOCAL_PWR_EN);
 }
 
-void __iomem *cpu_boot_reg_base(void)
+static void __iomem *cpu_boot_reg_base(void)
 {
        if (soc_is_exynos4210() && samsung_rev() == EXYNOS4210_REV_1_1)
                return pmu_base_addr + S5P_INFORM5;
@@ -195,7 +195,7 @@ static inline void __iomem *cpu_boot_reg(int cpu)
  *
  * Currently this is needed only when booting secondary CPU on Exynos3250.
  */
-static void exynos_core_restart(u32 core_id)
+void exynos_core_restart(u32 core_id)
 {
        u32 val;
 
@@ -210,7 +210,6 @@ static void exynos_core_restart(u32 core_id)
        val |= S5P_CORE_WAKEUP_FROM_LOCAL_CFG;
        pmu_raw_writel(val, EXYNOS_ARM_CORE_STATUS(core_id));
 
-       pr_info("CPU%u: Software reset\n", core_id);
        pmu_raw_writel(EXYNOS_CORE_PO_RESET(core_id), EXYNOS_SWRESET);
 }
 
@@ -248,6 +247,56 @@ static void exynos_secondary_init(unsigned int cpu)
        spin_unlock(&boot_lock);
 }
 
+int exynos_set_boot_addr(u32 core_id, unsigned long boot_addr)
+{
+       int ret;
+
+       /*
+        * Try to set boot address using firmware first
+        * and fall back to boot register if it fails.
+        */
+       ret = call_firmware_op(set_cpu_boot_addr, core_id, boot_addr);
+       if (ret && ret != -ENOSYS)
+               goto fail;
+       if (ret == -ENOSYS) {
+               void __iomem *boot_reg = cpu_boot_reg(core_id);
+
+               if (IS_ERR(boot_reg)) {
+                       ret = PTR_ERR(boot_reg);
+                       goto fail;
+               }
+               __raw_writel(boot_addr, boot_reg);
+               ret = 0;
+       }
+fail:
+       return ret;
+}
+
+int exynos_get_boot_addr(u32 core_id, unsigned long *boot_addr)
+{
+       int ret;
+
+       /*
+        * Try to get boot address using firmware first
+        * and fall back to boot register if it fails.
+        */
+       ret = call_firmware_op(get_cpu_boot_addr, core_id, boot_addr);
+       if (ret && ret != -ENOSYS)
+               goto fail;
+       if (ret == -ENOSYS) {
+               void __iomem *boot_reg = cpu_boot_reg(core_id);
+
+               if (IS_ERR(boot_reg)) {
+                       ret = PTR_ERR(boot_reg);
+                       goto fail;
+               }
+               *boot_addr = __raw_readl(boot_reg);
+               ret = 0;
+       }
+fail:
+       return ret;
+}
+
 static int exynos_boot_secondary(unsigned int cpu, struct task_struct *idle)
 {
        unsigned long timeout;
@@ -307,22 +356,9 @@ static int exynos_boot_secondary(unsigned int cpu, struct task_struct *idle)
 
                boot_addr = virt_to_phys(exynos4_secondary_startup);
 
-               /*
-                * Try to set boot address using firmware first
-                * and fall back to boot register if it fails.
-                */
-               ret = call_firmware_op(set_cpu_boot_addr, core_id, boot_addr);
-               if (ret && ret != -ENOSYS)
+               ret = exynos_set_boot_addr(core_id, boot_addr);
+               if (ret)
                        goto fail;
-               if (ret == -ENOSYS) {
-                       void __iomem *boot_reg = cpu_boot_reg(core_id);
-
-                       if (IS_ERR(boot_reg)) {
-                               ret = PTR_ERR(boot_reg);
-                               goto fail;
-                       }
-                       __raw_writel(boot_addr, boot_reg);
-               }
 
                call_firmware_op(cpu_boot, core_id);
 
@@ -337,6 +373,9 @@ static int exynos_boot_secondary(unsigned int cpu, struct task_struct *idle)
                udelay(10);
        }
 
+       if (pen_release != -1)
+               ret = -ETIMEDOUT;
+
        /*
         * now the secondary core is starting up let it run its
         * calibrations, then wait for it to finish
@@ -407,16 +446,9 @@ static void __init exynos_smp_prepare_cpus(unsigned int max_cpus)
                core_id = MPIDR_AFFINITY_LEVEL(mpidr, 0);
                boot_addr = virt_to_phys(exynos4_secondary_startup);
 
-               ret = call_firmware_op(set_cpu_boot_addr, core_id, boot_addr);
-               if (ret && ret != -ENOSYS)
+               ret = exynos_set_boot_addr(core_id, boot_addr);
+               if (ret)
                        break;
-               if (ret == -ENOSYS) {
-                       void __iomem *boot_reg = cpu_boot_reg(core_id);
-
-                       if (IS_ERR(boot_reg))
-                               break;
-                       __raw_writel(boot_addr, boot_reg);
-               }
        }
 }
 
index cc75ab448be3b4ce9b3c0fc2e626da4ed3d6e6ca..9c1506b499bca6f4599a20ece67494078a95d4d0 100644 (file)
@@ -22,6 +22,7 @@
 #include <asm/firmware.h>
 #include <asm/smp_scu.h>
 #include <asm/suspend.h>
+#include <asm/cacheflush.h>
 
 #include <mach/map.h>
 
@@ -209,6 +210,8 @@ static int exynos_cpu0_enter_aftr(void)
                 * sequence, let's wait for one of these to happen
                 */
                while (exynos_cpu_power_state(1)) {
+                       unsigned long boot_addr;
+
                        /*
                         * The other cpu may skip idle and boot back
                         * up again
@@ -221,7 +224,11 @@ static int exynos_cpu0_enter_aftr(void)
                         * boot back up again, getting stuck in the
                         * boot rom code
                         */
-                       if (__raw_readl(cpu_boot_reg_base()) == 0)
+                       ret = exynos_get_boot_addr(1, &boot_addr);
+                       if (ret)
+                               goto fail;
+                       ret = -1;
+                       if (boot_addr == 0)
                                goto abort;
 
                        cpu_relax();
@@ -233,11 +240,14 @@ static int exynos_cpu0_enter_aftr(void)
 
 abort:
        if (cpu_online(1)) {
+               unsigned long boot_addr = virt_to_phys(exynos_cpu_resume);
+
                /*
                 * Set the boot vector to something non-zero
                 */
-               __raw_writel(virt_to_phys(exynos_cpu_resume),
-                            cpu_boot_reg_base());
+               ret = exynos_set_boot_addr(1, boot_addr);
+               if (ret)
+                       goto fail;
                dsb();
 
                /*
@@ -247,22 +257,42 @@ abort:
                while (exynos_cpu_power_state(1) != S5P_CORE_LOCAL_PWR_EN)
                        cpu_relax();
 
+               if (soc_is_exynos3250()) {
+                       while (!pmu_raw_readl(S5P_PMU_SPARE2) &&
+                              !atomic_read(&cpu1_wakeup))
+                               cpu_relax();
+
+                       if (!atomic_read(&cpu1_wakeup))
+                               exynos_core_restart(1);
+               }
+
                while (!atomic_read(&cpu1_wakeup)) {
+                       smp_rmb();
+
                        /*
                         * Poke cpu1 out of the boot rom
                         */
-                       __raw_writel(virt_to_phys(exynos_cpu_resume),
-                                    cpu_boot_reg_base());
 
-                       arch_send_wakeup_ipi_mask(cpumask_of(1));
+                       ret = exynos_set_boot_addr(1, boot_addr);
+                       if (ret)
+                               goto fail;
+
+                       call_firmware_op(cpu_boot, 1);
+
+                       if (soc_is_exynos3250())
+                               dsb_sev();
+                       else
+                               arch_send_wakeup_ipi_mask(cpumask_of(1));
                }
        }
-
+fail:
        return ret;
 }
 
 static int exynos_wfi_finisher(unsigned long flags)
 {
+       if (soc_is_exynos3250())
+               flush_cache_all();
        cpu_do_idle();
 
        return -1;
@@ -283,6 +313,9 @@ static int exynos_cpu1_powerdown(void)
         */
        exynos_cpu_power_down(1);
 
+       if (soc_is_exynos3250())
+               pmu_raw_writel(0, S5P_PMU_SPARE2);
+
        ret = cpu_suspend(0, exynos_wfi_finisher);
 
        cpu_pm_exit();
@@ -299,7 +332,9 @@ cpu1_aborted:
 
 static void exynos_pre_enter_aftr(void)
 {
-       __raw_writel(virt_to_phys(exynos_cpu_resume), cpu_boot_reg_base());
+       unsigned long boot_addr = virt_to_phys(exynos_cpu_resume);
+
+       (void)exynos_set_boot_addr(1, boot_addr);
 }
 
 static void exynos_post_enter_aftr(void)
index a9686535f9ed460706a41a99dc60d6d4f575ab3b..6001f1c9d136f45fabd7d61e97638855d0beb46a 100644 (file)
@@ -62,6 +62,7 @@ static int exynos_pd_power(struct generic_pm_domain *domain, bool power_on)
                for (i = 0; i < MAX_CLK_PER_DOMAIN; i++) {
                        if (IS_ERR(pd->clk[i]))
                                break;
+                       pd->pclk[i] = clk_get_parent(pd->clk[i]);
                        if (clk_set_parent(pd->clk[i], pd->oscclk))
                                pr_err("%s: error setting oscclk as parent to clock %d\n",
                                                pd->name, i);
@@ -90,6 +91,9 @@ static int exynos_pd_power(struct generic_pm_domain *domain, bool power_on)
                for (i = 0; i < MAX_CLK_PER_DOMAIN; i++) {
                        if (IS_ERR(pd->clk[i]))
                                break;
+
+                       if (IS_ERR(pd->clk[i]))
+                               continue; /* Skip on first power up */
                        if (clk_set_parent(pd->clk[i], pd->pclk[i]))
                                pr_err("%s: error setting parent to clock%d\n",
                                                pd->name, i);
@@ -117,27 +121,37 @@ static int exynos_pd_power_off(struct generic_pm_domain *domain)
 
 static __init int exynos4_pm_init_power_domain(void)
 {
-       struct platform_device *pdev;
        struct device_node *np;
 
        for_each_compatible_node(np, NULL, "samsung,exynos4210-pd") {
                struct exynos_pm_domain *pd;
                int on, i;
-               struct device *dev;
-
-               pdev = of_find_device_by_node(np);
-               dev = &pdev->dev;
 
                pd = kzalloc(sizeof(*pd), GFP_KERNEL);
                if (!pd) {
                        pr_err("%s: failed to allocate memory for domain\n",
                                        __func__);
+                       of_node_put(np);
+                       return -ENOMEM;
+               }
+               pd->pd.name = kstrdup_const(strrchr(np->full_name, '/') + 1,
+                                           GFP_KERNEL);
+               if (!pd->pd.name) {
+                       kfree(pd);
+                       of_node_put(np);
                        return -ENOMEM;
                }
 
-               pd->pd.name = kstrdup(dev_name(dev), GFP_KERNEL);
                pd->name = pd->pd.name;
                pd->base = of_iomap(np, 0);
+               if (!pd->base) {
+                       pr_warn("%s: failed to map memory\n", __func__);
+                       kfree(pd->pd.name);
+                       kfree(pd);
+                       of_node_put(np);
+                       continue;
+               }
+
                pd->pd.power_off = exynos_pd_power_off;
                pd->pd.power_on = exynos_pd_power_on;
 
@@ -145,12 +159,12 @@ static __init int exynos4_pm_init_power_domain(void)
                        char clk_name[8];
 
                        snprintf(clk_name, sizeof(clk_name), "asb%d", i);
-                       pd->asb_clk[i] = clk_get(dev, clk_name);
+                       pd->asb_clk[i] = of_clk_get_by_name(np, clk_name);
                        if (IS_ERR(pd->asb_clk[i]))
                                break;
                }
 
-               pd->oscclk = clk_get(dev, "oscclk");
+               pd->oscclk = of_clk_get_by_name(np, "oscclk");
                if (IS_ERR(pd->oscclk))
                        goto no_clk;
 
@@ -158,16 +172,14 @@ static __init int exynos4_pm_init_power_domain(void)
                        char clk_name[8];
 
                        snprintf(clk_name, sizeof(clk_name), "clk%d", i);
-                       pd->clk[i] = clk_get(dev, clk_name);
+                       pd->clk[i] = of_clk_get_by_name(np, clk_name);
                        if (IS_ERR(pd->clk[i]))
                                break;
-                       snprintf(clk_name, sizeof(clk_name), "pclk%d", i);
-                       pd->pclk[i] = clk_get(dev, clk_name);
-                       if (IS_ERR(pd->pclk[i])) {
-                               clk_put(pd->clk[i]);
-                               pd->clk[i] = ERR_PTR(-EINVAL);
-                               break;
-                       }
+                       /*
+                        * Skip setting parent on first power up.
+                        * The parent at this time may not be useful at all.
+                        */
+                       pd->pclk[i] = ERR_PTR(-EINVAL);
                }
 
                if (IS_ERR(pd->clk[0]))
@@ -189,15 +201,15 @@ no_clk:
                args.args_count = 0;
                child_domain = of_genpd_get_from_provider(&args);
                if (IS_ERR(child_domain))
-                       continue;
+                       goto next_pd;
 
                if (of_parse_phandle_with_args(np, "power-domains",
                                         "#power-domain-cells", 0, &args) != 0)
-                       continue;
+                       goto next_pd;
 
                parent_domain = of_genpd_get_from_provider(&args);
                if (IS_ERR(parent_domain))
-                       continue;
+                       goto next_pd;
 
                if (pm_genpd_add_subdomain(parent_domain, child_domain))
                        pr_warn("%s failed to add subdomain: %s\n",
@@ -205,9 +217,10 @@ no_clk:
                else
                        pr_info("%s has as child subdomain: %s.\n",
                                parent_domain->name, child_domain->name);
+next_pd:
                of_node_put(np);
        }
 
        return 0;
 }
-arch_initcall(exynos4_pm_init_power_domain);
+core_initcall(exynos4_pm_init_power_domain);
index c15761ca2f187faaca0a6950f67a681820040a89..e812c1c85624c5a6c476a1092d2fed15b76649a3 100644 (file)
@@ -681,7 +681,7 @@ static unsigned int const exynos5420_list_disable_pmu_reg[] = {
        EXYNOS5420_CMU_RESET_FSYS_SYS_PWR_REG,
 };
 
-static void exynos5_power_off(void)
+static void exynos_power_off(void)
 {
        unsigned int tmp;
 
@@ -872,8 +872,6 @@ static void exynos5420_pmu_init(void)
                        EXYNOS5420_ARM_INTR_SPREAD_USE_STANDBYWFI);
 
        pmu_raw_writel(0x1, EXYNOS5420_UP_SCHEDULER);
-
-       pm_power_off = exynos5_power_off;
        pr_info("EXYNOS5420 PMU initialized\n");
 }
 
@@ -984,6 +982,8 @@ static int exynos_pmu_probe(struct platform_device *pdev)
        if (ret)
                dev_warn(dev, "can't register restart handler err=%d\n", ret);
 
+       pm_power_off = exynos_power_off;
+
        dev_dbg(dev, "Exynos PMU Driver probe done\n");
        return 0;
 }
index 7d23ce04cad5201919a58aefccafc88e882dd844..96866d03d281da1cc02715f1a1293cf9e79ff097 100644 (file)
@@ -223,7 +223,7 @@ static int exynos_pmu_domain_alloc(struct irq_domain *domain,
        return irq_domain_alloc_irqs_parent(domain, virq, nr_irqs, &parent_args);
 }
 
-static struct irq_domain_ops exynos_pmu_domain_ops = {
+static const struct irq_domain_ops exynos_pmu_domain_ops = {
        .xlate  = exynos_pmu_domain_xlate,
        .alloc  = exynos_pmu_domain_alloc,
        .free   = irq_domain_free_irqs_common,
index 388232ce92fc0fff4e3f99ae452992e6fbeeb892..573536f1bb739200e8a234a3a4844c5b591aa0ff 100644 (file)
@@ -1,8 +1,8 @@
 menuconfig ARCH_MXC
-       bool "Freescale i.MX family" if ARCH_MULTI_V4_V5 || ARCH_MULTI_V6_V7
+       bool "Freescale i.MX family" if ARCH_MULTI_V4_V5 || ARCH_MULTI_V6_V7 || ARM_SINGLE_ARMV7M
        select ARCH_REQUIRE_GPIOLIB
        select ARM_CPU_SUSPEND if PM
-       select CLKSRC_MMIO
+       select CLKSRC_IMX_GPT
        select GENERIC_IRQ_CHIP
        select PINCTRL
        select PM_OPP if PM
@@ -462,10 +462,10 @@ config MACH_VPR200
 
 endif
 
-if ARCH_MULTI_V5
-
 comment "Device tree only"
 
+if ARCH_MULTI_V5
+
 config SOC_IMX25
        bool "i.MX25 support"
        select ARCH_MXC_IOMUX_V3
@@ -478,7 +478,7 @@ endif
 
 if ARCH_MULTI_V7
 
-comment "Device tree only"
+comment "Cortex-A platforms"
 
 config SOC_IMX5
        bool
@@ -548,10 +548,33 @@ config SOC_IMX6SX
        help
          This enables support for Freescale i.MX6 SoloX processor.
 
+config SOC_IMX7D
+       bool "i.MX7 Dual support"
+       select PINCTRL_IMX7D
+       select ARM_GIC
+       select HAVE_IMX_ANATOP
+       select HAVE_IMX_MMDC
+       help
+               This enables support for Freescale i.MX7 Dual processor.
+
+config SOC_LS1021A
+       bool "Freescale LS1021A support"
+       select ARM_GIC
+       select HAVE_ARM_ARCH_TIMER
+       select PCI_DOMAINS if PCI
+       select ZONE_DMA if ARM_LPAE
+       help
+         This enables support for Freescale LS1021A processor.
+
+endif
+
+comment "Cortex-A/Cortex-M asymmetric multiprocessing platforms"
+
+if ARCH_MULTI_V7 || ARM_SINGLE_ARMV7M
+
 config SOC_VF610
        bool "Vybrid Family VF610 support"
-       select IRQ_DOMAIN_HIERARCHY
-       select ARM_GIC
+       select ARM_GIC if ARCH_MULTI_V7
        select PINCTRL_VF610
        select PL310_ERRATA_769419 if CACHE_L2X0
        select SMP_ON_UP if SMP
@@ -565,7 +588,7 @@ choice
        default VF_USE_ARM_GLOBAL_TIMER
 
        config VF_USE_ARM_GLOBAL_TIMER
-               bool "Use ARM Global Timer"
+               bool "Use ARM Global Timer" if ARCH_MULTI_V7
                select ARM_GLOBAL_TIMER
                select CLKSRC_ARM_GLOBAL_TIMER_SCHED_CLOCK
                help
@@ -579,16 +602,6 @@ choice
 
 endchoice
 
-config SOC_LS1021A
-       bool "Freescale LS1021A support"
-       select ARM_GIC
-       select HAVE_ARM_ARCH_TIMER
-       select PCI_DOMAINS if PCI
-       select ZONE_DMA if ARM_LPAE
-
-       help
-         This enables support for Freescale LS1021A processor.
-
 endif
 
 source "arch/arm/mach-imx/devices/Kconfig"
index eed609834ffbdf40a8f7684d61b549df640dbc71..37c502ac959508cc4b02c36d24c0086f753c2fa0 100644 (file)
@@ -1,23 +1,18 @@
-obj-y := time.o cpu.o system.o irq-common.o
+obj-y := cpu.o system.o irq-common.o
 
-obj-$(CONFIG_SOC_IMX1) += clk-imx1.o mm-imx1.o
-obj-$(CONFIG_SOC_IMX21) += clk-imx21.o mm-imx21.o
+obj-$(CONFIG_SOC_IMX1) += mm-imx1.o
+obj-$(CONFIG_SOC_IMX21) += mm-imx21.o
 
-obj-$(CONFIG_SOC_IMX25) += clk-imx25.o cpu-imx25.o mach-imx25.o
+obj-$(CONFIG_SOC_IMX25) += cpu-imx25.o mach-imx25.o
 
 obj-$(CONFIG_SOC_IMX27) += cpu-imx27.o pm-imx27.o
-obj-$(CONFIG_SOC_IMX27) += clk-imx27.o mm-imx27.o ehci-imx27.o
+obj-$(CONFIG_SOC_IMX27) += mm-imx27.o ehci-imx27.o
 
-obj-$(CONFIG_SOC_IMX31) += mm-imx3.o cpu-imx31.o clk-imx31.o iomux-imx31.o ehci-imx31.o pm-imx3.o
-obj-$(CONFIG_SOC_IMX35) += mm-imx3.o cpu-imx35.o clk-imx35.o ehci-imx35.o pm-imx3.o
+obj-$(CONFIG_SOC_IMX31) += mm-imx3.o cpu-imx31.o iomux-imx31.o ehci-imx31.o pm-imx3.o
+obj-$(CONFIG_SOC_IMX35) += mm-imx3.o cpu-imx35.o ehci-imx35.o pm-imx3.o
 
 imx5-pm-$(CONFIG_PM) += pm-imx5.o
-obj-$(CONFIG_SOC_IMX5) += cpu-imx5.o clk-imx51-imx53.o clk-cpu.o $(imx5-pm-y)
-
-obj-$(CONFIG_COMMON_CLK) += clk-pllv1.o clk-pllv2.o clk-pllv3.o clk-gate2.o \
-                           clk-pfd.o clk-busy.o clk.o \
-                           clk-fixup-div.o clk-fixup-mux.o \
-                           clk-gate-exclusive.o
+obj-$(CONFIG_SOC_IMX5) += cpu-imx5.o $(imx5-pm-y)
 
 obj-$(CONFIG_IMX_HAVE_IOMUX_V1) += iomux-v1.o
 obj-$(CONFIG_ARCH_MXC_IOMUX_V3) += iomux-v3.o
@@ -85,13 +80,15 @@ AFLAGS_headsmp.o :=-Wa,-march=armv7-a
 obj-$(CONFIG_SMP) += headsmp.o platsmp.o
 obj-$(CONFIG_HOTPLUG_CPU) += hotplug.o
 endif
-obj-$(CONFIG_SOC_IMX6Q) += clk-imx6q.o mach-imx6q.o
-obj-$(CONFIG_SOC_IMX6SL) += clk-imx6sl.o mach-imx6sl.o
-obj-$(CONFIG_SOC_IMX6SX) += clk-imx6sx.o mach-imx6sx.o
+obj-$(CONFIG_SOC_IMX6Q) += mach-imx6q.o
+obj-$(CONFIG_SOC_IMX6SL) += mach-imx6sl.o
+obj-$(CONFIG_SOC_IMX6SX) += mach-imx6sx.o
+obj-$(CONFIG_SOC_IMX7D) += mach-imx7d.o
 
 ifeq ($(CONFIG_SUSPEND),y)
 AFLAGS_suspend-imx6.o :=-Wa,-march=armv7-a
 obj-$(CONFIG_SOC_IMX6) += suspend-imx6.o
+obj-$(CONFIG_SOC_IMX53) += suspend-imx53.o
 endif
 obj-$(CONFIG_SOC_IMX6) += pm-imx6.o
 
@@ -99,7 +96,7 @@ obj-$(CONFIG_SOC_IMX50) += mach-imx50.o
 obj-$(CONFIG_SOC_IMX51) += mach-imx51.o
 obj-$(CONFIG_SOC_IMX53) += mach-imx53.o
 
-obj-$(CONFIG_SOC_VF610) += clk-vf610.o mach-vf610.o
+obj-$(CONFIG_SOC_VF610) += mach-vf610.o
 
 obj-$(CONFIG_SOC_LS1021A) += mach-ls1021a.o
 
diff --git a/arch/arm/mach-imx/Makefile.boot b/arch/arm/mach-imx/Makefile.boot
new file mode 100644 (file)
index 0000000..e69de29
index 7f262fe4ba77d7d28d95aaed8e4d56cf745c83bc..231bb250c5719d21962404a9301765cdcf499924 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2013 Freescale Semiconductor, Inc.
+ * Copyright (C) 2013-2015 Freescale Semiconductor, Inc.
  *
  * The code contained herein is licensed under the GNU General Public
  * License. You may obtain a copy of the GNU General Public License
@@ -28,6 +28,7 @@
 #define ANADIG_USB2_CHRG_DETECT        0x210
 #define ANADIG_DIGPROG         0x260
 #define ANADIG_DIGPROG_IMX6SL  0x280
+#define ANADIG_DIGPROG_IMX7D   0x800
 
 #define BM_ANADIG_REG_2P5_ENABLE_WEAK_LINREG   0x40000
 #define BM_ANADIG_REG_2P5_ENABLE_PULLDOWN      0x8
@@ -121,6 +122,8 @@ void __init imx_init_revision_from_anatop(void)
        WARN_ON(!anatop_base);
        if (of_device_is_compatible(np, "fsl,imx6sl-anatop"))
                offset = ANADIG_DIGPROG_IMX6SL;
+       if (of_device_is_compatible(np, "fsl,imx7d-anatop"))
+               offset = ANADIG_DIGPROG_IMX7D;
        digprog = readl_relaxed(anatop_base + offset);
        iounmap(anatop_base);
 
index 0f04e30b726d22e43ad725427bf2731295a705e7..21e4e8697a58f7d020d155277caabf85c5a0934e 100644 (file)
@@ -44,7 +44,6 @@ void imx27_soc_init(void);
 void imx31_soc_init(void);
 void imx35_soc_init(void);
 void epit_timer_init(void __iomem *base, int irq);
-void mxc_timer_init(void __iomem *, int);
 int mx1_clocks_init(unsigned long fref);
 int mx21_clocks_init(unsigned long lref, unsigned long fref);
 int mx27_clocks_init(unsigned long fref);
@@ -56,13 +55,10 @@ struct platform_device *mxc_register_gpio(char *name, int id,
 void mxc_set_cpu_type(unsigned int type);
 void mxc_restart(enum reboot_mode, const char *);
 void mxc_arch_reset_init(void __iomem *);
-int mx51_revision(void);
-int mx53_revision(void);
 void imx_set_aips(void __iomem *);
 void imx_aips_allow_unprivileged_access(const char *compat);
 int mxc_device_init(void);
 void imx_set_soc_revision(unsigned int rev);
-unsigned int imx_get_soc_revision(void);
 void imx_init_revision_from_anatop(void);
 struct device *imx_soc_device_init(void);
 void imx6_enable_rbc(bool enable);
@@ -87,7 +83,6 @@ enum mx3_cpu_pwr_mode {
 };
 
 void mx3_cpu_lp_set(enum mx3_cpu_pwr_mode mode);
-void imx_print_silicon_rev(const char *cpu, int srev);
 
 void imx_enable_cpu(int cpu, bool enable);
 void imx_set_cpu_jump(int cpu, void *jump_addr);
@@ -111,7 +106,7 @@ void imx_gpc_hwirq_unmask(unsigned int hwirq);
 void imx_anatop_init(void);
 void imx_anatop_pre_suspend(void);
 void imx_anatop_post_resume(void);
-int imx6q_set_lpm(enum mxc_cpu_pwr_mode mode);
+int imx6_set_lpm(enum mxc_cpu_pwr_mode mode);
 void imx6q_set_int_mem_clk_lpm(bool enable);
 void imx6sl_set_wait_clk(bool enter);
 int imx_mmdc_get_ddr_type(void);
@@ -121,26 +116,28 @@ int imx_cpu_kill(unsigned int cpu);
 
 #ifdef CONFIG_SUSPEND
 void v7_cpu_resume(void);
+void imx53_suspend(void __iomem *ocram_vbase);
+extern const u32 imx53_suspend_sz;
 void imx6_suspend(void __iomem *ocram_vbase);
 #else
 static inline void v7_cpu_resume(void) {}
+static inline void imx53_suspend(void __iomem *ocram_vbase) {}
+static const u32 imx53_suspend_sz;
 static inline void imx6_suspend(void __iomem *ocram_vbase) {}
 #endif
 
+void imx6_pm_ccm_init(const char *ccm_compat);
 void imx6q_pm_init(void);
 void imx6dl_pm_init(void);
 void imx6sl_pm_init(void);
 void imx6sx_pm_init(void);
-void imx6q_pm_set_ccm_base(void __iomem *base);
 
 #ifdef CONFIG_PM
 void imx51_pm_init(void);
 void imx53_pm_init(void);
-void imx5_pm_set_ccm_base(void __iomem *base);
 #else
 static inline void imx51_pm_init(void) {}
 static inline void imx53_pm_init(void) {}
-static inline void imx5_pm_set_ccm_base(void __iomem *base) {}
 #endif
 
 #ifdef CONFIG_NEON
index df42c14ff7497fb0c1dbd89153c88b46a86748cd..a7fa92a7b1d7122e5edfda24247b3b1afb52bc18 100644 (file)
@@ -130,6 +130,9 @@ struct device * __init imx_soc_device_init(void)
        case MXC_CPU_IMX6Q:
                soc_id = "i.MX6Q";
                break;
+       case MXC_CPU_IMX7D:
+               soc_id = "i.MX7D";
+               break;
        default:
                soc_id = "Unknown";
        }
index 8e21ccc1eda25a0c45109e2b20c5d63f02bf99f8..353bb8774112d8068a072d0afe8f8f32a61683ae 100644 (file)
@@ -27,9 +27,9 @@ static int imx6q_enter_wait(struct cpuidle_device *dev,
                 */
                if (!spin_trylock(&master_lock))
                        goto idle;
-               imx6q_set_lpm(WAIT_UNCLOCKED);
+               imx6_set_lpm(WAIT_UNCLOCKED);
                cpu_do_idle();
-               imx6q_set_lpm(WAIT_CLOCKED);
+               imx6_set_lpm(WAIT_CLOCKED);
                spin_unlock(&master_lock);
                goto done;
        }
index 5742a9fd1ef29c5d367924115ccb5fe859051633..8d866fb674a85af738422ab0a6fc055a5ee0f191 100644 (file)
@@ -16,7 +16,7 @@
 static int imx6sl_enter_wait(struct cpuidle_device *dev,
                            struct cpuidle_driver *drv, int index)
 {
-       imx6q_set_lpm(WAIT_UNCLOCKED);
+       imx6_set_lpm(WAIT_UNCLOCKED);
        /*
         * Software workaround for ERR005311, see function
         * description for details.
@@ -24,7 +24,7 @@ static int imx6sl_enter_wait(struct cpuidle_device *dev,
        imx6sl_set_wait_clk(true);
        cpu_do_idle();
        imx6sl_set_wait_clk(false);
-       imx6q_set_lpm(WAIT_CLOCKED);
+       imx6_set_lpm(WAIT_CLOCKED);
 
        return index;
 }
index 2c9f1a8bf24590cf21b6d8aea80938d1f966e77e..3c6672b3796b24b2ffebb3ad7166688697ba980f 100644 (file)
@@ -25,7 +25,7 @@ static int imx6sx_idle_finish(unsigned long val)
 static int imx6sx_enter_wait(struct cpuidle_device *dev,
                            struct cpuidle_driver *drv, int index)
 {
-       imx6q_set_lpm(WAIT_UNCLOCKED);
+       imx6_set_lpm(WAIT_UNCLOCKED);
 
        switch (index) {
        case 1:
@@ -50,7 +50,7 @@ static int imx6sx_enter_wait(struct cpuidle_device *dev,
                break;
        }
 
-       imx6q_set_lpm(WAIT_CLOCKED);
+       imx6_set_lpm(WAIT_CLOCKED);
 
        return index;
 }
index 0ea77ed25b25a8cf45953fea587738f221421f1c..80bad29d609ac2bf2be07f4de20d3650d8ea28d9 100644 (file)
@@ -227,7 +227,7 @@ static int imx_gpc_domain_alloc(struct irq_domain *domain,
        return irq_domain_alloc_irqs_parent(domain, irq, nr_irqs, &parent_args);
 }
 
-static struct irq_domain_ops imx_gpc_domain_ops = {
+static const struct irq_domain_ops imx_gpc_domain_ops = {
        .xlate  = imx_gpc_domain_xlate,
        .alloc  = imx_gpc_domain_alloc,
        .free   = irq_domain_free_irqs_common,
index 76af2c03c241eff9509e6cdf6b1129763537824b..d737f95ebb0773a78c4cb77da0b3490c7f4e1d7e 100644 (file)
@@ -22,6 +22,7 @@
 
 #ifndef __ASSEMBLY__
 #include <asm/io.h>
+#include <soc/imx/revision.h>
 #endif
 #include <asm/sizes.h>
 
index d6a30753ca7cb27c9d5c5704e417102d065a2d60..6dd22cabf4d345e8d6bcfb6f77dc333cd53ea45e 100644 (file)
@@ -40,7 +40,7 @@ static DEFINE_SPINLOCK(gpio_mux_lock);
 
 #define IOMUX_REG_MASK (IOMUX_PADNUM_MASK & ~0x3)
 
-static unsigned long mxc_pin_alloc_map[NB_PORTS * 32 / BITS_PER_LONG];
+static DECLARE_BITMAP(mxc_pin_alloc_map, NB_PORTS * 32);
 /*
  * set the mode for a IOMUX pin.
  */
index 3ab61549ce0fb8939c8f0a04b5a4c528fe64fbd1..9602cc12d2f1014efbac3887dc49278191745c67 100644 (file)
@@ -393,6 +393,7 @@ static void __init imx6q_init_irq(void)
        imx_init_l2cache();
        imx_src_init();
        irqchip_init();
+       imx6_pm_ccm_init("fsl,imx6q-ccm");
 }
 
 static const char * const imx6q_dt_compat[] __initconst = {
index 12a1b098fc6a98bd80de68161b94ae6377f04e37..300326373166bc85c84470b6939ba0180fef1358 100644 (file)
@@ -66,6 +66,7 @@ static void __init imx6sl_init_irq(void)
        imx_init_l2cache();
        imx_src_init();
        irqchip_init();
+       imx6_pm_ccm_init("fsl,imx6sl-ccm");
 }
 
 static const char * const imx6sl_dt_compat[] __initconst = {
index f17b7004c24ba809caf27186c56cded060682586..6a0b0614de293b197742c613587d3fd0593ccae1 100644 (file)
@@ -86,6 +86,7 @@ static void __init imx6sx_init_irq(void)
        imx_init_l2cache();
        imx_src_init();
        irqchip_init();
+       imx6_pm_ccm_init("fsl,imx6sx-ccm");
 }
 
 static void __init imx6sx_init_late(void)
diff --git a/arch/arm/mach-imx/mach-imx7d.c b/arch/arm/mach-imx/mach-imx7d.c
new file mode 100644 (file)
index 0000000..4d4a190
--- /dev/null
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2015 Freescale Semiconductor, Inc.
+ *
+ * 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/irqchip.h>
+#include <linux/of_platform.h>
+#include <asm/mach/arch.h>
+#include <asm/mach/map.h>
+
+#include "common.h"
+
+static void __init imx7d_init_machine(void)
+{
+       struct device *parent;
+
+       parent = imx_soc_device_init();
+       if (parent == NULL)
+               pr_warn("failed to initialize soc device\n");
+
+       of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL);
+       imx_anatop_init();
+}
+
+static void __init imx7d_init_irq(void)
+{
+       imx_init_revision_from_anatop();
+       imx_src_init();
+       irqchip_init();
+}
+
+static const char *imx7d_dt_compat[] __initconst = {
+       "fsl,imx7d",
+       NULL,
+};
+
+DT_MACHINE_START(IMX7D, "Freescale i.MX7 Dual (Device Tree)")
+       .init_irq       = imx7d_init_irq,
+       .init_machine   = imx7d_init_machine,
+       .dt_compat      = imx7d_dt_compat,
+MACHINE_END
index 2e7c75b66fe03420ef5fad642fdaf968cc95c441..b20f6c14eda527cd71be2a4445901ca96e6fcd4a 100644 (file)
@@ -17,6 +17,7 @@ static const char * const vf610_dt_compat[] __initconst = {
        "fsl,vf510",
        "fsl,vf600",
        "fsl,vf610",
+       "fsl,vf610m4",
        NULL,
 };
 
index 0411f0664c15c0bce0469b9cd073205834ba366a..db9621c718ecae1ff2567f596f4d71ecd6428c4a 100644 (file)
@@ -17,6 +17,8 @@
 #include <linux/of_address.h>
 #include <linux/of_device.h>
 
+#include "common.h"
+
 #define MMDC_MAPSR             0x404
 #define BP_MMDC_MAPSR_PSD      0
 #define BP_MMDC_MAPSR_PSS      4
index 8a65f192e7f31fb82b998b9e094ae9e1f69441a7..f96bb2642677a1870863c97c3f1b8afd619aa261 100644 (file)
 #define MX27_DMA_REQ_SDHC3     36
 #define MX27_DMA_REQ_NFC       37
 
-#ifndef __ASSEMBLY__
-extern int mx27_revision(void);
-#endif
-
 #endif /* ifndef __MACH_MX27_H__ */
index 96fb4fbc8ad7c34dd4ea9d9324a655470db58318..6fec6114c2f12001cf9db1969ae27e638616b9e7 100644 (file)
 
 #define MX3x_PROD_SIGNATURE            0x1     /* For MX31 */
 
-/* Mandatory defines used globally */
-
-#if !defined(__ASSEMBLY__) && !defined(__MXC_BOOT_UNCOMPRESS)
-extern int mx35_revision(void);
-extern int mx31_revision(void);
-#endif
-
 #endif /* ifndef __MACH_MX3x_H__ */
index 4c1343df2ba495b511ecdbf064c8da11f91310ab..c4436d4fd6fdb6be76ca1613027ee424b752113a 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright 2004-2007, 2010 Freescale Semiconductor, Inc. All Rights Reserved.
+ * Copyright 2004-2007, 2010-2015 Freescale Semiconductor, Inc.
  * Copyright (C) 2008 Juergen Beisert (kernel@pengutronix.de)
  *
  * This program is free software; you can redistribute it and/or
 #define MXC_CPU_IMX6DL         0x61
 #define MXC_CPU_IMX6SX         0x62
 #define MXC_CPU_IMX6Q          0x63
-
-#define IMX_CHIP_REVISION_1_0          0x10
-#define IMX_CHIP_REVISION_1_1          0x11
-#define IMX_CHIP_REVISION_1_2          0x12
-#define IMX_CHIP_REVISION_1_3          0x13
-#define IMX_CHIP_REVISION_1_4          0x14
-#define IMX_CHIP_REVISION_1_5          0x15
-#define IMX_CHIP_REVISION_2_0          0x20
-#define IMX_CHIP_REVISION_2_1          0x21
-#define IMX_CHIP_REVISION_2_2          0x22
-#define IMX_CHIP_REVISION_2_3          0x23
-#define IMX_CHIP_REVISION_3_0          0x30
-#define IMX_CHIP_REVISION_3_1          0x31
-#define IMX_CHIP_REVISION_3_2          0x32
-#define IMX_CHIP_REVISION_3_3          0x33
-#define IMX_CHIP_REVISION_UNKNOWN      0xff
+#define MXC_CPU_IMX7D          0x72
 
 #define IMX_DDR_TYPE_LPDDR2            1
 
@@ -185,6 +170,11 @@ static inline bool cpu_is_imx6q(void)
        return __mxc_cpu_type == MXC_CPU_IMX6Q;
 }
 
+static inline bool cpu_is_imx7d(void)
+{
+       return __mxc_cpu_type == MXC_CPU_IMX7D;
+}
+
 struct cpu_op {
        u32 cpu_rate;
 };
index f1f80ab73e692ea70e95044eb016e92c9eddc28f..0309ccda36a91704e3aa4a395cebce66aa9eaa21 100644 (file)
 #include <linux/io.h>
 #include <linux/err.h>
 #include <linux/export.h>
+
+#include <linux/genalloc.h>
+#include <linux/of.h>
+#include <linux/of_address.h>
+#include <linux/of_platform.h>
+
 #include <asm/cacheflush.h>
+#include <asm/fncpy.h>
 #include <asm/system_misc.h>
 #include <asm/tlbflush.h>
 
  */
 #define IMX5_DEFAULT_CPU_IDLE_STATE WAIT_UNCLOCKED_POWER_OFF
 
+struct imx5_suspend_io_state {
+       u32     offset;
+       u32     clear;
+       u32     set;
+       u32     saved_value;
+};
+
 struct imx5_pm_data {
+       phys_addr_t ccm_addr;
        phys_addr_t cortex_addr;
        phys_addr_t gpc_addr;
+       phys_addr_t m4if_addr;
+       phys_addr_t iomuxc_addr;
+       void (*suspend_asm)(void __iomem *ocram_vbase);
+       const u32 *suspend_asm_sz;
+       const struct imx5_suspend_io_state *suspend_io_config;
+       int suspend_io_count;
+};
+
+static const struct imx5_suspend_io_state imx53_suspend_io_config[] = {
+#define MX53_DSE_HIGHZ_MASK (0x7 << 19)
+       {.offset = 0x584, .clear = MX53_DSE_HIGHZ_MASK}, /* DQM0 */
+       {.offset = 0x594, .clear = MX53_DSE_HIGHZ_MASK}, /* DQM1 */
+       {.offset = 0x560, .clear = MX53_DSE_HIGHZ_MASK}, /* DQM2 */
+       {.offset = 0x554, .clear = MX53_DSE_HIGHZ_MASK}, /* DQM3 */
+       {.offset = 0x574, .clear = MX53_DSE_HIGHZ_MASK}, /* CAS */
+       {.offset = 0x588, .clear = MX53_DSE_HIGHZ_MASK}, /* RAS */
+       {.offset = 0x578, .clear = MX53_DSE_HIGHZ_MASK}, /* SDCLK_0 */
+       {.offset = 0x570, .clear = MX53_DSE_HIGHZ_MASK}, /* SDCLK_1 */
+
+       {.offset = 0x580, .clear = MX53_DSE_HIGHZ_MASK}, /* SDODT0 */
+       {.offset = 0x564, .clear = MX53_DSE_HIGHZ_MASK}, /* SDODT1 */
+       {.offset = 0x57c, .clear = MX53_DSE_HIGHZ_MASK}, /* SDQS0 */
+       {.offset = 0x590, .clear = MX53_DSE_HIGHZ_MASK}, /* SDQS1 */
+       {.offset = 0x568, .clear = MX53_DSE_HIGHZ_MASK}, /* SDQS2 */
+       {.offset = 0x558, .clear = MX53_DSE_HIGHZ_MASK}, /* SDSQ3 */
+       {.offset = 0x6f0, .clear = MX53_DSE_HIGHZ_MASK}, /* GRP_ADDS */
+       {.offset = 0x718, .clear = MX53_DSE_HIGHZ_MASK}, /* GRP_BODS */
+       {.offset = 0x71c, .clear = MX53_DSE_HIGHZ_MASK}, /* GRP_B1DS */
+       {.offset = 0x728, .clear = MX53_DSE_HIGHZ_MASK}, /* GRP_B2DS */
+       {.offset = 0x72c, .clear = MX53_DSE_HIGHZ_MASK}, /* GRP_B3DS */
+
+       /* Controls the CKE signal which is required to leave self refresh */
+       {.offset = 0x720, .clear = MX53_DSE_HIGHZ_MASK, .set = 1 << 19}, /* CTLDS */
 };
 
 static const struct imx5_pm_data imx51_pm_data __initconst = {
+       .ccm_addr = 0x73fd4000,
        .cortex_addr = 0x83fa0000,
        .gpc_addr = 0x73fd8000,
 };
 
 static const struct imx5_pm_data imx53_pm_data __initconst = {
+       .ccm_addr = 0x53fd4000,
        .cortex_addr = 0x63fa0000,
        .gpc_addr = 0x53fd8000,
+       .m4if_addr = 0x63fd8000,
+       .iomuxc_addr = 0x53fa8000,
+       .suspend_asm = &imx53_suspend,
+       .suspend_asm_sz = &imx53_suspend_sz,
+       .suspend_io_config = imx53_suspend_io_config,
+       .suspend_io_count = ARRAY_SIZE(imx53_suspend_io_config),
 };
 
+#define MX5_MAX_SUSPEND_IOSTATE ARRAY_SIZE(imx53_suspend_io_config)
+
+/*
+ * This structure is for passing necessary data for low level ocram
+ * suspend code(arch/arm/mach-imx/suspend-imx53.S), if this struct
+ * definition is changed, the offset definition in that file
+ * must be also changed accordingly otherwise, the suspend to ocram
+ * function will be broken!
+ */
+struct imx5_cpu_suspend_info {
+       void __iomem    *m4if_base;
+       void __iomem    *iomuxc_base;
+       u32             io_count;
+       struct imx5_suspend_io_state io_state[MX5_MAX_SUSPEND_IOSTATE];
+} __aligned(8);
+
 static void __iomem *ccm_base;
 static void __iomem *cortex_base;
 static void __iomem *gpc_base;
-
-void __init imx5_pm_set_ccm_base(void __iomem *base)
-{
-       ccm_base = base;
-}
+static void __iomem *suspend_ocram_base;
+static void (*imx5_suspend_in_ocram_fn)(void __iomem *ocram_vbase);
 
 /*
  * set cpu low power mode before WFI instruction. This function is called
@@ -161,8 +230,15 @@ static int mx5_suspend_enter(suspend_state_t state)
                /*clear the EMPGC0/1 bits */
                __raw_writel(0, gpc_base + MXC_SRPG_EMPGC0_SRPGCR);
                __raw_writel(0, gpc_base + MXC_SRPG_EMPGC1_SRPGCR);
+
+               if (imx5_suspend_in_ocram_fn)
+                       imx5_suspend_in_ocram_fn(suspend_ocram_base);
+               else
+                       cpu_do_idle();
+
+       } else {
+               cpu_do_idle();
        }
-       cpu_do_idle();
 
        /* return registers to default idle state */
        mx5_cpu_lp_set(IMX5_DEFAULT_CPU_IDLE_STATE);
@@ -194,6 +270,111 @@ static void imx5_pm_idle(void)
        imx5_cpu_do_idle();
 }
 
+static int __init imx_suspend_alloc_ocram(
+                               size_t size,
+                               void __iomem **virt_out,
+                               phys_addr_t *phys_out)
+{
+       struct device_node *node;
+       struct platform_device *pdev;
+       struct gen_pool *ocram_pool;
+       unsigned long ocram_base;
+       void __iomem *virt;
+       phys_addr_t phys;
+       int ret = 0;
+
+       /* Copied from imx6: TODO factorize */
+       node = of_find_compatible_node(NULL, NULL, "mmio-sram");
+       if (!node) {
+               pr_warn("%s: failed to find ocram node!\n", __func__);
+               return -ENODEV;
+       }
+
+       pdev = of_find_device_by_node(node);
+       if (!pdev) {
+               pr_warn("%s: failed to find ocram device!\n", __func__);
+               ret = -ENODEV;
+               goto put_node;
+       }
+
+       ocram_pool = dev_get_gen_pool(&pdev->dev);
+       if (!ocram_pool) {
+               pr_warn("%s: ocram pool unavailable!\n", __func__);
+               ret = -ENODEV;
+               goto put_node;
+       }
+
+       ocram_base = gen_pool_alloc(ocram_pool, size);
+       if (!ocram_base) {
+               pr_warn("%s: unable to alloc ocram!\n", __func__);
+               ret = -ENOMEM;
+               goto put_node;
+       }
+
+       phys = gen_pool_virt_to_phys(ocram_pool, ocram_base);
+       virt = __arm_ioremap_exec(phys, size, false);
+       if (phys_out)
+               *phys_out = phys;
+       if (virt_out)
+               *virt_out = virt;
+
+put_node:
+       of_node_put(node);
+
+       return ret;
+}
+
+static int __init imx5_suspend_init(const struct imx5_pm_data *soc_data)
+{
+       struct imx5_cpu_suspend_info *suspend_info;
+       int ret;
+       /* Need this to avoid compile error due to const typeof in fncpy.h */
+       void (*suspend_asm)(void __iomem *) = soc_data->suspend_asm;
+
+       if (!suspend_asm)
+               return 0;
+
+       if (!soc_data->suspend_asm_sz || !*soc_data->suspend_asm_sz)
+               return -EINVAL;
+
+       ret = imx_suspend_alloc_ocram(
+               *soc_data->suspend_asm_sz + sizeof(*suspend_info),
+               &suspend_ocram_base, NULL);
+       if (ret)
+               return ret;
+
+       suspend_info = suspend_ocram_base;
+
+       suspend_info->io_count = soc_data->suspend_io_count;
+       memcpy(suspend_info->io_state, soc_data->suspend_io_config,
+              sizeof(*suspend_info->io_state) * soc_data->suspend_io_count);
+
+       suspend_info->m4if_base = ioremap(soc_data->m4if_addr, SZ_16K);
+       if (!suspend_info->m4if_base) {
+               ret = -ENOMEM;
+               goto failed_map_m4if;
+       }
+
+       suspend_info->iomuxc_base = ioremap(soc_data->iomuxc_addr, SZ_16K);
+       if (!suspend_info->iomuxc_base) {
+               ret = -ENOMEM;
+               goto failed_map_iomuxc;
+       }
+
+       imx5_suspend_in_ocram_fn = fncpy(
+               suspend_ocram_base + sizeof(*suspend_info),
+               suspend_asm,
+               *soc_data->suspend_asm_sz);
+
+       return 0;
+
+failed_map_iomuxc:
+       iounmap(suspend_info->m4if_base);
+
+failed_map_m4if:
+       return ret;
+}
+
 static int __init imx5_pm_common_init(const struct imx5_pm_data *data)
 {
        int ret;
@@ -208,6 +389,7 @@ static int __init imx5_pm_common_init(const struct imx5_pm_data *data)
 
        arm_pm_idle = imx5_pm_idle;
 
+       ccm_base = ioremap(data->ccm_addr, SZ_16K);
        cortex_base = ioremap(data->cortex_addr, SZ_16K);
        gpc_base = ioremap(data->gpc_addr, SZ_16K);
        WARN_ON(!ccm_base || !cortex_base || !gpc_base);
@@ -219,6 +401,11 @@ static int __init imx5_pm_common_init(const struct imx5_pm_data *data)
        if (ret)
                pr_warn("%s: cpuidle init failed %d\n", __func__, ret);
 
+       ret = imx5_suspend_init(data);
+       if (ret)
+               pr_warn("%s: No DDR LPM support with suspend %d!\n",
+                       __func__, ret);
+
        suspend_set_ops(&mx5_suspend_ops);
 
        return 0;
@@ -226,10 +413,12 @@ static int __init imx5_pm_common_init(const struct imx5_pm_data *data)
 
 void __init imx51_pm_init(void)
 {
-       imx5_pm_common_init(&imx51_pm_data);
+       if (IS_ENABLED(CONFIG_SOC_IMX51))
+               imx5_pm_common_init(&imx51_pm_data);
 }
 
 void __init imx53_pm_init(void)
 {
-       imx5_pm_common_init(&imx53_pm_data);
+       if (IS_ENABLED(CONFIG_SOC_IMX53))
+               imx5_pm_common_init(&imx53_pm_data);
 }
index 6a7c6fc780cce686650ea684d2965c30de3746df..b01650d94f910111d04628dfc87a21cac4b6b9bf 100644 (file)
@@ -255,7 +255,7 @@ static void imx6q_enable_wb(bool enable)
        writel_relaxed(val, ccm_base + CCR);
 }
 
-int imx6q_set_lpm(enum mxc_cpu_pwr_mode mode)
+int imx6_set_lpm(enum mxc_cpu_pwr_mode mode)
 {
        u32 val = readl_relaxed(ccm_base + CLPCR);
 
@@ -340,7 +340,7 @@ static int imx6q_pm_enter(suspend_state_t state)
 {
        switch (state) {
        case PM_SUSPEND_STANDBY:
-               imx6q_set_lpm(STOP_POWER_ON);
+               imx6_set_lpm(STOP_POWER_ON);
                imx6q_set_int_mem_clk_lpm(true);
                imx_gpc_pre_suspend(false);
                if (cpu_is_imx6sl())
@@ -350,10 +350,10 @@ static int imx6q_pm_enter(suspend_state_t state)
                if (cpu_is_imx6sl())
                        imx6sl_set_wait_clk(false);
                imx_gpc_post_resume();
-               imx6q_set_lpm(WAIT_CLOCKED);
+               imx6_set_lpm(WAIT_CLOCKED);
                break;
        case PM_SUSPEND_MEM:
-               imx6q_set_lpm(STOP_POWER_OFF);
+               imx6_set_lpm(STOP_POWER_OFF);
                imx6q_set_int_mem_clk_lpm(false);
                imx6q_enable_wb(true);
                /*
@@ -373,7 +373,7 @@ static int imx6q_pm_enter(suspend_state_t state)
                imx6_enable_rbc(false);
                imx6q_enable_wb(false);
                imx6q_set_int_mem_clk_lpm(true);
-               imx6q_set_lpm(WAIT_CLOCKED);
+               imx6_set_lpm(WAIT_CLOCKED);
                break;
        default:
                return -EINVAL;
@@ -392,11 +392,6 @@ static const struct platform_suspend_ops imx6q_pm_ops = {
        .valid = imx6q_pm_valid,
 };
 
-void __init imx6q_pm_set_ccm_base(void __iomem *base)
-{
-       ccm_base = base;
-}
-
 static int __init imx6_pm_get_base(struct imx6_pm_base *base,
                                const char *compat)
 {
@@ -482,8 +477,7 @@ static int __init imx6q_suspend_init(const struct imx6_pm_socdata *socdata)
 
        /*
         * ccm physical address is not used by asm code currently,
-        * so get ccm virtual address directly, as we already have
-        * it from ccm driver.
+        * so get ccm virtual address directly.
         */
        pm_info->ccm_base.vbase = ccm_base;
 
@@ -568,7 +562,7 @@ static void __init imx6_pm_common_init(const struct imx6_pm_socdata
 
        /*
         * This is for SW workaround step #1 of ERR007265, see comments
-        * in imx6q_set_lpm for details of this errata.
+        * in imx6_set_lpm for details of this errata.
         * Force IOMUXC irq pending, so that the interrupt to GPC can be
         * used to deassert dsm_request signal when the signal gets
         * asserted unexpectedly.
@@ -579,6 +573,24 @@ static void __init imx6_pm_common_init(const struct imx6_pm_socdata
                                   IMX6Q_GPR1_GINT);
 }
 
+void __init imx6_pm_ccm_init(const char *ccm_compat)
+{
+       struct device_node *np;
+       u32 val;
+
+       np = of_find_compatible_node(NULL, NULL, ccm_compat);
+       ccm_base = of_iomap(np, 0);
+       BUG_ON(!ccm_base);
+
+       /*
+        * Initialize CCM_CLPCR_LPM into RUN mode to avoid ARM core
+        * clock being shut down unexpectedly by WAIT mode.
+        */
+       val = readl_relaxed(ccm_base + CLPCR);
+       val &= ~BM_CLPCR_LPM;
+       writel_relaxed(val, ccm_base + CLPCR);
+}
+
 void __init imx6q_pm_init(void)
 {
        imx6_pm_common_init(&imx6q_pm_data);
diff --git a/arch/arm/mach-imx/suspend-imx53.S b/arch/arm/mach-imx/suspend-imx53.S
new file mode 100644 (file)
index 0000000..5ed078a
--- /dev/null
@@ -0,0 +1,139 @@
+/*
+ * Copyright (C) 2008-2011 Freescale Semiconductor, Inc.
+ */
+/*
+ * The code contained herein is licensed under the GNU General Public
+ * License. You may obtain a copy of the GNU General Public License
+ * Version 2 or later at the following locations:
+ *
+ * http://www.opensource.org/licenses/gpl-license.html
+ * http://www.gnu.org/copyleft/gpl.html
+ */
+
+#include <linux/linkage.h>
+
+#define M4IF_MCR0_OFFSET                       (0x008C)
+#define M4IF_MCR0_FDVFS                                (0x1 << 11)
+#define M4IF_MCR0_FDVACK                       (0x1 << 27)
+
+       .align 3
+
+/*
+ * ==================== low level suspend ====================
+ *
+ * On entry
+ * r0: pm_info structure address;
+ *
+ * suspend ocram space layout:
+ * ======================== high address ======================
+ *                              .
+ *                              .
+ *                              .
+ *                              ^
+ *                              ^
+ *                              ^
+ *                      imx53_suspend code
+ *              PM_INFO structure(imx53_suspend_info)
+ * ======================== low address =======================
+ */
+
+/* Offsets of members of struct imx53_suspend_info */
+#define SUSPEND_INFO_MX53_M4IF_V_OFFSET                0x0
+#define SUSPEND_INFO_MX53_IOMUXC_V_OFFSET      0x4
+#define SUSPEND_INFO_MX53_IO_COUNT_OFFSET      0x8
+#define SUSPEND_INFO_MX53_IO_STATE_OFFSET      0xc
+
+ENTRY(imx53_suspend)
+       stmfd   sp!, {r4,r5,r6,r7}
+
+       /* Save pad config */
+       ldr     r1, [r0, #SUSPEND_INFO_MX53_IO_COUNT_OFFSET]
+       cmp     r1, #0
+       beq     skip_pad_conf_1
+
+       add     r2, r0, #SUSPEND_INFO_MX53_IO_STATE_OFFSET
+       ldr     r3, [r0, #SUSPEND_INFO_MX53_IOMUXC_V_OFFSET]
+
+1:
+       ldr     r5, [r2], #12   /* IOMUXC register offset */
+       ldr     r6, [r3, r5]    /* current value */
+       str     r6, [r2], #4    /* save area */
+       subs    r1, r1, #1
+       bne     1b
+
+skip_pad_conf_1:
+       /* Set FDVFS bit of M4IF_MCR0 to request DDR to enter self-refresh */
+       ldr     r1, [r0, #SUSPEND_INFO_MX53_M4IF_V_OFFSET]
+       ldr     r2,[r1, #M4IF_MCR0_OFFSET]
+       orr     r2, r2, #M4IF_MCR0_FDVFS
+       str     r2,[r1, #M4IF_MCR0_OFFSET]
+
+       /* Poll FDVACK bit of M4IF_MCR to wait for DDR to enter self-refresh */
+wait_sr_ack:
+       ldr     r2,[r1, #M4IF_MCR0_OFFSET]
+       ands    r2, r2, #M4IF_MCR0_FDVACK
+       beq     wait_sr_ack
+
+       /* Set pad config */
+       ldr     r1, [r0, #SUSPEND_INFO_MX53_IO_COUNT_OFFSET]
+       cmp     r1, #0
+       beq     skip_pad_conf_2
+
+       add     r2, r0, #SUSPEND_INFO_MX53_IO_STATE_OFFSET
+       ldr     r3, [r0, #SUSPEND_INFO_MX53_IOMUXC_V_OFFSET]
+
+2:
+       ldr     r5, [r2], #4    /* IOMUXC register offset */
+       ldr     r6, [r2], #4    /* clear */
+       ldr     r7, [r3, r5]
+       bic     r7, r7, r6
+       ldr     r6, [r2], #8    /* set */
+       orr     r7, r7, r6
+       str     r7, [r3, r5]
+       subs    r1, r1, #1
+       bne     2b
+
+skip_pad_conf_2:
+       /* Zzz, enter stop mode */
+       wfi
+       nop
+       nop
+       nop
+       nop
+
+       /* Restore pad config */
+       ldr     r1, [r0, #SUSPEND_INFO_MX53_IO_COUNT_OFFSET]
+       cmp     r1, #0
+       beq     skip_pad_conf_3
+
+       add     r2, r0, #SUSPEND_INFO_MX53_IO_STATE_OFFSET
+       ldr     r3, [r0, #SUSPEND_INFO_MX53_IOMUXC_V_OFFSET]
+
+3:
+       ldr     r5, [r2], #12   /* IOMUXC register offset */
+       ldr     r6, [r2], #4    /* saved value */
+       str     r6, [r3, r5]
+       subs    r1, r1, #1
+       bne     3b
+
+skip_pad_conf_3:
+       /* Clear FDVFS bit of M4IF_MCR0 to request DDR to exit self-refresh */
+       ldr     r1, [r0, #SUSPEND_INFO_MX53_M4IF_V_OFFSET]
+       ldr     r2,[r1, #M4IF_MCR0_OFFSET]
+       bic     r2, r2, #M4IF_MCR0_FDVFS
+       str     r2,[r1, #M4IF_MCR0_OFFSET]
+
+       /* Poll FDVACK bit of M4IF_MCR to wait for DDR to exit self-refresh */
+wait_ar_ack:
+       ldr     r2,[r1, #M4IF_MCR0_OFFSET]
+       ands    r2, r2, #M4IF_MCR0_FDVACK
+       bne     wait_ar_ack
+
+       /* Restore registers */
+       ldmfd   sp!, {r4,r5,r6,r7}
+       mov     pc, lr
+
+ENDPROC(imx53_suspend)
+
+ENTRY(imx53_suspend_sz)
+        .word   . - imx53_suspend
diff --git a/arch/arm/mach-imx/time.c b/arch/arm/mach-imx/time.c
deleted file mode 100644 (file)
index 15d18e1..0000000
+++ /dev/null
@@ -1,385 +0,0 @@
-/*
- *  linux/arch/arm/plat-mxc/time.c
- *
- *  Copyright (C) 2000-2001 Deep Blue Solutions
- *  Copyright (C) 2002 Shane Nay (shane@minirl.com)
- *  Copyright (C) 2006-2007 Pavel Pisa (ppisa@pikron.com)
- *  Copyright (C) 2008 Juergen Beisert (kernel@pengutronix.de)
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
- * MA 02110-1301, USA.
- */
-
-#include <linux/interrupt.h>
-#include <linux/irq.h>
-#include <linux/clockchips.h>
-#include <linux/clk.h>
-#include <linux/delay.h>
-#include <linux/err.h>
-#include <linux/sched_clock.h>
-#include <linux/of.h>
-#include <linux/of_address.h>
-#include <linux/of_irq.h>
-
-#include <asm/mach/time.h>
-
-#include "common.h"
-#include "hardware.h"
-
-/*
- * There are 2 versions of the timer hardware on Freescale MXC hardware.
- * Version 1: MX1/MXL, MX21, MX27.
- * Version 2: MX25, MX31, MX35, MX37, MX51
- */
-
-/* defines common for all i.MX */
-#define MXC_TCTL               0x00
-#define MXC_TCTL_TEN           (1 << 0) /* Enable module */
-#define MXC_TPRER              0x04
-
-/* MX1, MX21, MX27 */
-#define MX1_2_TCTL_CLK_PCLK1   (1 << 1)
-#define MX1_2_TCTL_IRQEN       (1 << 4)
-#define MX1_2_TCTL_FRR         (1 << 8)
-#define MX1_2_TCMP             0x08
-#define MX1_2_TCN              0x10
-#define MX1_2_TSTAT            0x14
-
-/* MX21, MX27 */
-#define MX2_TSTAT_CAPT         (1 << 1)
-#define MX2_TSTAT_COMP         (1 << 0)
-
-/* MX31, MX35, MX25, MX5, MX6 */
-#define V2_TCTL_WAITEN         (1 << 3) /* Wait enable mode */
-#define V2_TCTL_CLK_IPG                (1 << 6)
-#define V2_TCTL_CLK_PER                (2 << 6)
-#define V2_TCTL_CLK_OSC_DIV8   (5 << 6)
-#define V2_TCTL_FRR            (1 << 9)
-#define V2_TCTL_24MEN          (1 << 10)
-#define V2_TPRER_PRE24M                12
-#define V2_IR                  0x0c
-#define V2_TSTAT               0x08
-#define V2_TSTAT_OF1           (1 << 0)
-#define V2_TCN                 0x24
-#define V2_TCMP                        0x10
-
-#define V2_TIMER_RATE_OSC_DIV8 3000000
-
-#define timer_is_v1()  (cpu_is_mx1() || cpu_is_mx21() || cpu_is_mx27())
-#define timer_is_v2()  (!timer_is_v1())
-
-static struct clock_event_device clockevent_mxc;
-static enum clock_event_mode clockevent_mode = CLOCK_EVT_MODE_UNUSED;
-
-static void __iomem *timer_base;
-
-static inline void gpt_irq_disable(void)
-{
-       unsigned int tmp;
-
-       if (timer_is_v2())
-               __raw_writel(0, timer_base + V2_IR);
-       else {
-               tmp = __raw_readl(timer_base + MXC_TCTL);
-               __raw_writel(tmp & ~MX1_2_TCTL_IRQEN, timer_base + MXC_TCTL);
-       }
-}
-
-static inline void gpt_irq_enable(void)
-{
-       if (timer_is_v2())
-               __raw_writel(1<<0, timer_base + V2_IR);
-       else {
-               __raw_writel(__raw_readl(timer_base + MXC_TCTL) | MX1_2_TCTL_IRQEN,
-                       timer_base + MXC_TCTL);
-       }
-}
-
-static void gpt_irq_acknowledge(void)
-{
-       if (timer_is_v1()) {
-               if (cpu_is_mx1())
-                       __raw_writel(0, timer_base + MX1_2_TSTAT);
-               else
-                       __raw_writel(MX2_TSTAT_CAPT | MX2_TSTAT_COMP,
-                               timer_base + MX1_2_TSTAT);
-       } else if (timer_is_v2())
-               __raw_writel(V2_TSTAT_OF1, timer_base + V2_TSTAT);
-}
-
-static void __iomem *sched_clock_reg;
-
-static u64 notrace mxc_read_sched_clock(void)
-{
-       return sched_clock_reg ? __raw_readl(sched_clock_reg) : 0;
-}
-
-static struct delay_timer imx_delay_timer;
-
-static unsigned long imx_read_current_timer(void)
-{
-       return __raw_readl(sched_clock_reg);
-}
-
-static int __init mxc_clocksource_init(struct clk *timer_clk)
-{
-       unsigned int c = clk_get_rate(timer_clk);
-       void __iomem *reg = timer_base + (timer_is_v2() ? V2_TCN : MX1_2_TCN);
-
-       imx_delay_timer.read_current_timer = &imx_read_current_timer;
-       imx_delay_timer.freq = c;
-       register_current_timer_delay(&imx_delay_timer);
-
-       sched_clock_reg = reg;
-
-       sched_clock_register(mxc_read_sched_clock, 32, c);
-       return clocksource_mmio_init(reg, "mxc_timer1", c, 200, 32,
-                       clocksource_mmio_readl_up);
-}
-
-/* clock event */
-
-static int mx1_2_set_next_event(unsigned long evt,
-                             struct clock_event_device *unused)
-{
-       unsigned long tcmp;
-
-       tcmp = __raw_readl(timer_base + MX1_2_TCN) + evt;
-
-       __raw_writel(tcmp, timer_base + MX1_2_TCMP);
-
-       return (int)(tcmp - __raw_readl(timer_base + MX1_2_TCN)) < 0 ?
-                               -ETIME : 0;
-}
-
-static int v2_set_next_event(unsigned long evt,
-                             struct clock_event_device *unused)
-{
-       unsigned long tcmp;
-
-       tcmp = __raw_readl(timer_base + V2_TCN) + evt;
-
-       __raw_writel(tcmp, timer_base + V2_TCMP);
-
-       return evt < 0x7fffffff &&
-               (int)(tcmp - __raw_readl(timer_base + V2_TCN)) < 0 ?
-                               -ETIME : 0;
-}
-
-#ifdef DEBUG
-static const char *clock_event_mode_label[] = {
-       [CLOCK_EVT_MODE_PERIODIC] = "CLOCK_EVT_MODE_PERIODIC",
-       [CLOCK_EVT_MODE_ONESHOT]  = "CLOCK_EVT_MODE_ONESHOT",
-       [CLOCK_EVT_MODE_SHUTDOWN] = "CLOCK_EVT_MODE_SHUTDOWN",
-       [CLOCK_EVT_MODE_UNUSED]   = "CLOCK_EVT_MODE_UNUSED",
-       [CLOCK_EVT_MODE_RESUME]   = "CLOCK_EVT_MODE_RESUME",
-};
-#endif /* DEBUG */
-
-static void mxc_set_mode(enum clock_event_mode mode,
-                               struct clock_event_device *evt)
-{
-       unsigned long flags;
-
-       /*
-        * The timer interrupt generation is disabled at least
-        * for enough time to call mxc_set_next_event()
-        */
-       local_irq_save(flags);
-
-       /* Disable interrupt in GPT module */
-       gpt_irq_disable();
-
-       if (mode != clockevent_mode) {
-               /* Set event time into far-far future */
-               if (timer_is_v2())
-                       __raw_writel(__raw_readl(timer_base + V2_TCN) - 3,
-                                       timer_base + V2_TCMP);
-               else
-                       __raw_writel(__raw_readl(timer_base + MX1_2_TCN) - 3,
-                                       timer_base + MX1_2_TCMP);
-
-               /* Clear pending interrupt */
-               gpt_irq_acknowledge();
-       }
-
-#ifdef DEBUG
-       printk(KERN_INFO "mxc_set_mode: changing mode from %s to %s\n",
-               clock_event_mode_label[clockevent_mode],
-               clock_event_mode_label[mode]);
-#endif /* DEBUG */
-
-       /* Remember timer mode */
-       clockevent_mode = mode;
-       local_irq_restore(flags);
-
-       switch (mode) {
-       case CLOCK_EVT_MODE_PERIODIC:
-               printk(KERN_ERR"mxc_set_mode: Periodic mode is not "
-                               "supported for i.MX\n");
-               break;
-       case CLOCK_EVT_MODE_ONESHOT:
-       /*
-        * Do not put overhead of interrupt enable/disable into
-        * mxc_set_next_event(), the core has about 4 minutes
-        * to call mxc_set_next_event() or shutdown clock after
-        * mode switching
-        */
-               local_irq_save(flags);
-               gpt_irq_enable();
-               local_irq_restore(flags);
-               break;
-       case CLOCK_EVT_MODE_SHUTDOWN:
-       case CLOCK_EVT_MODE_UNUSED:
-       case CLOCK_EVT_MODE_RESUME:
-               /* Left event sources disabled, no more interrupts appear */
-               break;
-       }
-}
-
-/*
- * IRQ handler for the timer
- */
-static irqreturn_t mxc_timer_interrupt(int irq, void *dev_id)
-{
-       struct clock_event_device *evt = &clockevent_mxc;
-       uint32_t tstat;
-
-       if (timer_is_v2())
-               tstat = __raw_readl(timer_base + V2_TSTAT);
-       else
-               tstat = __raw_readl(timer_base + MX1_2_TSTAT);
-
-       gpt_irq_acknowledge();
-
-       evt->event_handler(evt);
-
-       return IRQ_HANDLED;
-}
-
-static struct irqaction mxc_timer_irq = {
-       .name           = "i.MX Timer Tick",
-       .flags          = IRQF_TIMER | IRQF_IRQPOLL,
-       .handler        = mxc_timer_interrupt,
-};
-
-static struct clock_event_device clockevent_mxc = {
-       .name           = "mxc_timer1",
-       .features       = CLOCK_EVT_FEAT_ONESHOT,
-       .set_mode       = mxc_set_mode,
-       .set_next_event = mx1_2_set_next_event,
-       .rating         = 200,
-};
-
-static int __init mxc_clockevent_init(struct clk *timer_clk)
-{
-       if (timer_is_v2())
-               clockevent_mxc.set_next_event = v2_set_next_event;
-
-       clockevent_mxc.cpumask = cpumask_of(0);
-       clockevents_config_and_register(&clockevent_mxc,
-                                       clk_get_rate(timer_clk),
-                                       0xff, 0xfffffffe);
-
-       return 0;
-}
-
-static void __init _mxc_timer_init(int irq,
-                                  struct clk *clk_per, struct clk *clk_ipg)
-{
-       uint32_t tctl_val;
-
-       if (IS_ERR(clk_per)) {
-               pr_err("i.MX timer: unable to get clk\n");
-               return;
-       }
-
-       if (!IS_ERR(clk_ipg))
-               clk_prepare_enable(clk_ipg);
-
-       clk_prepare_enable(clk_per);
-
-       /*
-        * Initialise to a known state (all timers off, and timing reset)
-        */
-
-       __raw_writel(0, timer_base + MXC_TCTL);
-       __raw_writel(0, timer_base + MXC_TPRER); /* see datasheet note */
-
-       if (timer_is_v2()) {
-               tctl_val = V2_TCTL_FRR | V2_TCTL_WAITEN | MXC_TCTL_TEN;
-               if (clk_get_rate(clk_per) == V2_TIMER_RATE_OSC_DIV8) {
-                       tctl_val |= V2_TCTL_CLK_OSC_DIV8;
-                       if (cpu_is_imx6dl() || cpu_is_imx6sx()) {
-                               /* 24 / 8 = 3 MHz */
-                               __raw_writel(7 << V2_TPRER_PRE24M,
-                                       timer_base + MXC_TPRER);
-                               tctl_val |= V2_TCTL_24MEN;
-                       }
-               } else {
-                       tctl_val |= V2_TCTL_CLK_PER;
-               }
-       } else {
-               tctl_val = MX1_2_TCTL_FRR | MX1_2_TCTL_CLK_PCLK1 | MXC_TCTL_TEN;
-       }
-
-       __raw_writel(tctl_val, timer_base + MXC_TCTL);
-
-       /* init and register the timer to the framework */
-       mxc_clocksource_init(clk_per);
-       mxc_clockevent_init(clk_per);
-
-       /* Make irqs happen */
-       setup_irq(irq, &mxc_timer_irq);
-}
-
-void __init mxc_timer_init(void __iomem *base, int irq)
-{
-       struct clk *clk_per = clk_get_sys("imx-gpt.0", "per");
-       struct clk *clk_ipg = clk_get_sys("imx-gpt.0", "ipg");
-
-       timer_base = base;
-
-       _mxc_timer_init(irq, clk_per, clk_ipg);
-}
-
-static void __init mxc_timer_init_dt(struct device_node *np)
-{
-       struct clk *clk_per, *clk_ipg;
-       int irq;
-
-       if (timer_base)
-               return;
-
-       timer_base = of_iomap(np, 0);
-       WARN_ON(!timer_base);
-       irq = irq_of_parse_and_map(np, 0);
-
-       clk_ipg = of_clk_get_by_name(np, "ipg");
-
-       /* Try osc_per first, and fall back to per otherwise */
-       clk_per = of_clk_get_by_name(np, "osc_per");
-       if (IS_ERR(clk_per))
-               clk_per = of_clk_get_by_name(np, "per");
-
-       _mxc_timer_init(irq, clk_per, clk_ipg);
-}
-CLOCKSOURCE_OF_DECLARE(mx1_timer, "fsl,imx1-gpt", mxc_timer_init_dt);
-CLOCKSOURCE_OF_DECLARE(mx25_timer, "fsl,imx25-gpt", mxc_timer_init_dt);
-CLOCKSOURCE_OF_DECLARE(mx50_timer, "fsl,imx50-gpt", mxc_timer_init_dt);
-CLOCKSOURCE_OF_DECLARE(mx51_timer, "fsl,imx51-gpt", mxc_timer_init_dt);
-CLOCKSOURCE_OF_DECLARE(mx53_timer, "fsl,imx53-gpt", mxc_timer_init_dt);
-CLOCKSOURCE_OF_DECLARE(mx6q_timer, "fsl,imx6q-gpt", mxc_timer_init_dt);
-CLOCKSOURCE_OF_DECLARE(mx6sl_timer, "fsl,imx6sl-gpt", mxc_timer_init_dt);
-CLOCKSOURCE_OF_DECLARE(mx6sx_timer, "fsl,imx6sx-gpt", mxc_timer_init_dt);
diff --git a/arch/arm/mach-lpc18xx/Makefile b/arch/arm/mach-lpc18xx/Makefile
new file mode 100644 (file)
index 0000000..bd0b7b5
--- /dev/null
@@ -0,0 +1 @@
+obj-y += board-dt.o
diff --git a/arch/arm/mach-lpc18xx/Makefile.boot b/arch/arm/mach-lpc18xx/Makefile.boot
new file mode 100644 (file)
index 0000000..eacfc3f
--- /dev/null
@@ -0,0 +1,3 @@
+# Empty file waiting for deletion once Makefile.boot isn't needed any more.
+# Patch waits for application at
+# http://www.arm.linux.org.uk/developer/patches/viewpatch.php?id=7889/1 .
diff --git a/arch/arm/mach-lpc18xx/board-dt.c b/arch/arm/mach-lpc18xx/board-dt.c
new file mode 100644 (file)
index 0000000..fdcee78
--- /dev/null
@@ -0,0 +1,22 @@
+/*
+ * Device Tree board file for NXP LPC18xx/43xx
+ *
+ * Copyright (C) 2015 Joachim Eastwood <manabian@gmail.com>
+ *
+ * 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.
+ */
+
+#include <asm/mach/arch.h>
+
+static const char *const lpc18xx_43xx_compat[] __initconst = {
+       "nxp,lpc1850",
+       "nxp,lpc4350",
+       "nxp,lpc4370",
+       NULL
+};
+
+DT_MACHINE_START(LPC18XXDT, "NXP LPC18xx/43xx (Device Tree)")
+       .dt_compat = lpc18xx_43xx_compat,
+MACHINE_END
index 3d1e1c250a1ab4b5e4eb25b52ed4eae3da0b0aef..5d7fb596bf4afb6d14b7c835cad0cbc38b827869 100644 (file)
 #include <asm/assembler.h>
 
 #include <mach/board-ams-delta.h>
-
-#include <mach/irqs.h>
 #include <mach/ams-delta-fiq.h>
 
 #include "iomap.h"
+#include "soc.h"
 
 /*
  * GPIO related definitions, copied from arch/arm/plat-omap/gpio.c.
index 2aab761ee68db7ae8fee7fd5eaf84e82f9c80572..a95499ea87064d4f886b234f2a8eafba922fe573 100644 (file)
@@ -626,6 +626,7 @@ MACHINE_START(AMS_DELTA, "Amstrad E3 (Delta)")
        .map_io         = ams_delta_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = ams_delta_init,
        .init_late      = ams_delta_init_late,
        .init_time      = omap1_timer_init,
index 702d58039cc1a90820232615224d2015bf7a6329..0fb51d22c8b57fd8b4de7aa5a04fdae2f8499d4b 100644 (file)
@@ -362,6 +362,7 @@ MACHINE_START(OMAP_FSAMPLE, "OMAP730 F-Sample")
        .map_io         = omap_fsample_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = omap_fsample_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index e1d9171774bca91eec6f2a4802c7153208822743..9708629f8c5f9c83e3db2161e7d56e1cac02b7b4 100644 (file)
@@ -82,6 +82,7 @@ MACHINE_START(OMAP_GENERIC, "Generic OMAP1510/1610/1710")
        .map_io         = omap16xx_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = omap_generic_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 5b45d266d83e0de774c3bdea376c3f29d5193aea..8340d684d8b6003fd8da9c4b801d35f82e7c15ca 100644 (file)
@@ -426,6 +426,7 @@ MACHINE_START(OMAP_H2, "TI-H2")
        .map_io         = omap16xx_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = h2_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 17d77914d769233d4c1360ef5159a3df98cda596..43aab63cbc39da2903fc600faf0fbdbbfbb9d8d6 100644 (file)
@@ -16,6 +16,7 @@
 
 #include <linux/i2c/tps65010.h>
 
+#include "common.h"
 #include "board-h3.h"
 #include "mmc.h"
 
index bfed4f928663a52b3643a7518f35e3c8c0537800..086ff34e072b6e5e4a489a84b00f9ca2f35cc189 100644 (file)
@@ -452,6 +452,7 @@ MACHINE_START(OMAP_H3, "TI OMAP1710 H3 board")
        .map_io         = omap16xx_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = h3_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 35a2379b986f676618a49991dcd621cbe3e6e51b..9525ef9bc6c0db1b3e706a58b4348980b8843712 100644 (file)
@@ -601,6 +601,7 @@ MACHINE_START(HERALD, "HTC Herald")
        .map_io         = htcherald_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = htcherald_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index c49ce83cc1ebd066abcc4200f78cd9e008dda61a..ed4e045c2ad8278b360c7b5ebba8bd0ed75f48bb 100644 (file)
@@ -456,6 +456,7 @@ MACHINE_START(OMAP_INNOVATOR, "TI-Innovator")
        .map_io         = innovator_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = innovator_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 85089d821982193b2e2d79f5f5fbf050eefad464..9f6c7af3a4e71158d25f72e0cecb8fdfc59fec57 100644 (file)
@@ -294,6 +294,7 @@ MACHINE_START(NOKIA770, "Nokia 770")
        .map_io         = omap16xx_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = omap_nokia770_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 7436d4cf659640731acaaca4a0bc352561bfd769..0efd165b82278f52626c3cf2fd2a8af230020aa4 100644 (file)
@@ -610,6 +610,7 @@ MACHINE_START(OMAP_OSK, "TI-OSK")
        .map_io         = omap16xx_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = osk_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 3b8e98f4353c465675bef171a19580c1987e35ae..1142ae431fe0dc2999a85da6847c4478e8ee2ee5 100644 (file)
@@ -235,6 +235,7 @@ MACHINE_START(OMAP_PALMTE, "OMAP310 based Palm Tungsten E")
        .map_io         = omap15xx_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = omap_palmte_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index ca501208825fc5fb62d49701e09aaf057b44d635..54a547a96950651733677ba66ba05b58a1435aa2 100644 (file)
@@ -282,6 +282,7 @@ MACHINE_START(OMAP_PALMTT, "OMAP1510 based Palm Tungsten|T")
        .map_io         = omap15xx_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = omap_palmtt_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 470e12d67360cd351ae41b9467dfaf406b679c64..87ec04ae40dd691f29aa3f014f3fbe4269b5a394 100644 (file)
@@ -297,6 +297,7 @@ MACHINE_START(OMAP_PALMZ71, "OMAP310 based Palm Zire71")
        .map_io         = omap15xx_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = omap_palmz71_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 8b2f7127f716ae583fb1ba05adc2976fb0905dd9..3d76f05407f0cbe87d16f514b4b6b4c3fab1f3af 100644 (file)
@@ -324,6 +324,7 @@ MACHINE_START(OMAP_PERSEUS2, "OMAP730 Perseus2")
        .map_io         = omap_perseus2_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = omap_perseus2_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 29e526235dc2e06e964e2f54631b08d01a0a5f23..939991ea33d5cab3f31713ea427cd38325618fda 100644 (file)
@@ -343,6 +343,7 @@ MACHINE_START(SX1, "OMAP310 based Siemens SX1")
        .map_io         = omap15xx_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = omap_sx1_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 4677a9ccb3cbbb222bc50c2a59e3b66b81d73e18..e960687d0cb155465efe41ed34dcf4ca36e5d932 100644 (file)
@@ -288,6 +288,7 @@ MACHINE_START(VOICEBLUE, "VoiceBlue OMAP5910")
        .map_io         = omap15xx_map_io,
        .init_early     = omap1_init_early,
        .init_irq       = omap1_init_irq,
+       .handle_irq     = omap1_handle_irq,
        .init_machine   = voiceblue_init,
        .init_late      = omap1_init_late,
        .init_time      = omap1_timer_init,
index 732f8ee2fcd2ce544a28eabda14f5fdde8250e7a..65bb6e8085de1fd8b81a335be4dc9117a352f892 100644 (file)
 #include <linux/i2c-omap.h>
 #include <linux/reboot.h>
 
+#include <asm/exception.h>
+
 #include <plat/i2c.h>
 
 #include <mach/irqs.h>
 
+#include "soc.h"
+
 #if defined(CONFIG_ARCH_OMAP730) || defined(CONFIG_ARCH_OMAP850)
 void omap7xx_map_io(void);
 #else
@@ -73,6 +77,7 @@ static inline int omap_serial_wakeup_init(void)
 
 void omap1_init_early(void);
 void omap1_init_irq(void);
+void __exception_irq_entry omap1_handle_irq(struct pt_regs *regs);
 void omap1_init_late(void);
 void omap1_restart(enum reboot_mode, const char *);
 
@@ -91,8 +96,6 @@ static inline int __init omap_32k_timer_init(void)
 }
 #endif
 
-extern u32 omap_irq_flags;
-
 #ifdef CONFIG_ARCH_OMAP16XX
 extern int ocpi_enable(void);
 #else
index 4be601b638d7aa8c0d35b7fa5924eb54aa6e2534..7b02ed218a42f693a7347c58488d026f11b5b113 100644 (file)
@@ -28,7 +28,7 @@
 #include <linux/omap-dma.h>
 #include <mach/tc.h>
 
-#include <mach/irqs.h>
+#include "soc.h"
 
 #define OMAP1_DMA_BASE                 (0xfffed800)
 #define OMAP1_LOGICAL_DMA_CH_COUNT     17
index 6e6ec93dcbb3fd4a4f0d889b2e871737a38f028e..5b7a29b294d47991f4d66e87ca535ea9c4ea5f99 100644 (file)
@@ -21,6 +21,8 @@
 
 #include <mach/irqs.h>
 
+#include "soc.h"
+
 #define OMAP1610_GPIO1_BASE            0xfffbe400
 #define OMAP1610_GPIO2_BASE            0xfffbec00
 #define OMAP1610_GPIO3_BASE            0xfffbb400
index 4612d2506a2db5a6e7e22d06a643e6beb6747409..0e5f68de23bfb4484b578dee72979559e959ba0e 100644 (file)
@@ -21,6 +21,8 @@
 
 #include <mach/irqs.h>
 
+#include "soc.h"
+
 #define OMAP7XX_GPIO1_BASE             0xfffbc000
 #define OMAP7XX_GPIO2_BASE             0xfffbc800
 #define OMAP7XX_GPIO3_BASE             0xfffbd000
index 7f5761cffd2eaf75561b3b77112b4c8553b020f4..82887d645a6acb38462089da235d5aeb446181e5 100644 (file)
@@ -27,7 +27,6 @@
 
 #define OMAP_I2C_SIZE          0x3f
 #define OMAP1_I2C_BASE         0xfffb3800
-#define OMAP1_INT_I2C          (32 + 4)
 
 static const char name[] = "omap_i2c";
 
@@ -67,7 +66,7 @@ int __init omap_i2c_add_bus(struct omap_i2c_bus_platform_data *pdata,
        res[0].start = OMAP1_I2C_BASE;
        res[0].end = res[0].start + OMAP_I2C_SIZE;
        res[0].flags = IORESOURCE_MEM;
-       res[1].start = OMAP1_INT_I2C;
+       res[1].start = INT_I2C;
        res[1].flags = IORESOURCE_IRQ;
        pdev->resource = res;
 
diff --git a/arch/arm/mach-omap1/include/mach/entry-macro.S b/arch/arm/mach-omap1/include/mach/entry-macro.S
deleted file mode 100644 (file)
index 78a8c6c..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * arch/arm/mach-omap1/include/mach/entry-macro.S
- *
- * Low-level IRQ helper macros for OMAP-based platforms
- *
- * Copyright (C) 2009 Texas Instruments
- *
- * 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.
- */
-
-#include <mach/hardware.h>
-#include <mach/irqs.h>
-
-               .macro  get_irqnr_preamble, base, tmp
-               .endm
-
-               .macro  get_irqnr_and_base, irqnr, irqstat, base, tmp
-               ldr     \base, =OMAP1_IO_ADDRESS(OMAP_IH1_BASE)
-               ldr     \irqnr, [\base, #IRQ_ITR_REG_OFFSET]
-               ldr     \tmp, [\base, #IRQ_MIR_REG_OFFSET]
-               mov     \irqstat, #0xffffffff
-               bic     \tmp, \irqstat, \tmp
-               tst     \irqnr, \tmp
-               beq     1510f
-
-               ldr     \irqnr, [\base, #IRQ_SIR_FIQ_REG_OFFSET]
-               ldr     \tmp, =omap_irq_flags   @ irq flags address
-               ldr     \tmp, [\tmp, #0]        @ irq flags value
-               cmp     \irqnr, #0
-               ldreq   \irqnr, [\base, #IRQ_SIR_IRQ_REG_OFFSET]
-               cmpeq   \irqnr, \tmp
-               ldreq   \base, =OMAP1_IO_ADDRESS(OMAP_IH2_BASE)
-               ldreq   \irqnr, [\base, #IRQ_SIR_IRQ_REG_OFFSET]
-               addeqs  \irqnr, \irqnr, #32
-1510:
-               .endm
-
index 729992d7d26a871cf237d08378d13ff383f102c2..9050085271bc794ef9639da55fbff3c39db3495d 100644 (file)
  * NOTE: See also the OMAP-1510 and 1610 specific IRQ numbers below
  *
  */
-#define INT_CAMERA             1
-#define INT_FIQ                        3
-#define INT_RTDX               6
-#define INT_DSP_MMU_ABORT      7
-#define INT_HOST               8
-#define INT_ABORT              9
-#define INT_BRIDGE_PRIV                13
-#define INT_GPIO_BANK1         14
-#define INT_UART3              15
-#define INT_TIMER3             16
-#define INT_DMA_CH0_6          19
-#define INT_DMA_CH1_7          20
-#define INT_DMA_CH2_8          21
-#define INT_DMA_CH3            22
-#define INT_DMA_CH4            23
-#define INT_DMA_CH5            24
-#define INT_TIMER1             26
-#define INT_WD_TIMER           27
-#define INT_BRIDGE_PUB         28
-#define INT_TIMER2             30
-#define INT_LCD_CTRL           31
+#define INT_CAMERA             (NR_IRQS_LEGACY + 1)
+#define INT_FIQ                        (NR_IRQS_LEGACY + 3)
+#define INT_RTDX               (NR_IRQS_LEGACY + 6)
+#define INT_DSP_MMU_ABORT      (NR_IRQS_LEGACY + 7)
+#define INT_HOST               (NR_IRQS_LEGACY + 8)
+#define INT_ABORT              (NR_IRQS_LEGACY + 9)
+#define INT_BRIDGE_PRIV                (NR_IRQS_LEGACY + 13)
+#define INT_GPIO_BANK1         (NR_IRQS_LEGACY + 14)
+#define INT_UART3              (NR_IRQS_LEGACY + 15)
+#define INT_TIMER3             (NR_IRQS_LEGACY + 16)
+#define INT_DMA_CH0_6          (NR_IRQS_LEGACY + 19)
+#define INT_DMA_CH1_7          (NR_IRQS_LEGACY + 20)
+#define INT_DMA_CH2_8          (NR_IRQS_LEGACY + 21)
+#define INT_DMA_CH3            (NR_IRQS_LEGACY + 22)
+#define INT_DMA_CH4            (NR_IRQS_LEGACY + 23)
+#define INT_DMA_CH5            (NR_IRQS_LEGACY + 24)
+#define INT_TIMER1             (NR_IRQS_LEGACY + 26)
+#define INT_WD_TIMER           (NR_IRQS_LEGACY + 27)
+#define INT_BRIDGE_PUB         (NR_IRQS_LEGACY + 28)
+#define INT_TIMER2             (NR_IRQS_LEGACY + 30)
+#define INT_LCD_CTRL           (NR_IRQS_LEGACY + 31)
 
 /*
  * OMAP-1510 specific IRQ numbers for interrupt handler 1
  */
-#define INT_1510_IH2_IRQ       0
-#define INT_1510_RES2          2
-#define INT_1510_SPI_TX                4
-#define INT_1510_SPI_RX                5
-#define INT_1510_DSP_MAILBOX1  10
-#define INT_1510_DSP_MAILBOX2  11
-#define INT_1510_RES12         12
-#define INT_1510_LB_MMU                17
-#define INT_1510_RES18         18
-#define INT_1510_LOCAL_BUS     29
+#define INT_1510_IH2_IRQ       (NR_IRQS_LEGACY + 0)
+#define INT_1510_RES2          (NR_IRQS_LEGACY + 2)
+#define INT_1510_SPI_TX                (NR_IRQS_LEGACY + 4)
+#define INT_1510_SPI_RX                (NR_IRQS_LEGACY + 5)
+#define INT_1510_DSP_MAILBOX1  (NR_IRQS_LEGACY + 10)
+#define INT_1510_DSP_MAILBOX2  (NR_IRQS_LEGACY + 11)
+#define INT_1510_RES12         (NR_IRQS_LEGACY + 12)
+#define INT_1510_LB_MMU                (NR_IRQS_LEGACY + 17)
+#define INT_1510_RES18         (NR_IRQS_LEGACY + 18)
+#define INT_1510_LOCAL_BUS     (NR_IRQS_LEGACY + 29)
 
 /*
  * OMAP-1610 specific IRQ numbers for interrupt handler 1
  */
 #define INT_1610_IH2_IRQ       INT_1510_IH2_IRQ
-#define INT_1610_IH2_FIQ       2
-#define INT_1610_McBSP2_TX     4
-#define INT_1610_McBSP2_RX     5
-#define INT_1610_DSP_MAILBOX1  10
-#define INT_1610_DSP_MAILBOX2  11
-#define INT_1610_LCD_LINE      12
-#define INT_1610_GPTIMER1      17
-#define INT_1610_GPTIMER2      18
-#define INT_1610_SSR_FIFO_0    29
+#define INT_1610_IH2_FIQ       (NR_IRQS_LEGACY + 2)
+#define INT_1610_McBSP2_TX     (NR_IRQS_LEGACY + 4)
+#define INT_1610_McBSP2_RX     (NR_IRQS_LEGACY + 5)
+#define INT_1610_DSP_MAILBOX1  (NR_IRQS_LEGACY + 10)
+#define INT_1610_DSP_MAILBOX2  (NR_IRQS_LEGACY + 11)
+#define INT_1610_LCD_LINE      (NR_IRQS_LEGACY + 12)
+#define INT_1610_GPTIMER1      (NR_IRQS_LEGACY + 17)
+#define INT_1610_GPTIMER2      (NR_IRQS_LEGACY + 18)
+#define INT_1610_SSR_FIFO_0    (NR_IRQS_LEGACY + 29)
 
 /*
  * OMAP-7xx specific IRQ numbers for interrupt handler 1
  */
-#define INT_7XX_IH2_FIQ                0
-#define INT_7XX_IH2_IRQ                1
-#define INT_7XX_USB_NON_ISO    2
-#define INT_7XX_USB_ISO                3
-#define INT_7XX_ICR            4
-#define INT_7XX_EAC            5
-#define INT_7XX_GPIO_BANK1     6
-#define INT_7XX_GPIO_BANK2     7
-#define INT_7XX_GPIO_BANK3     8
-#define INT_7XX_McBSP2TX       10
-#define INT_7XX_McBSP2RX       11
-#define INT_7XX_McBSP2RX_OVF   12
-#define INT_7XX_LCD_LINE       14
-#define INT_7XX_GSM_PROTECT    15
-#define INT_7XX_TIMER3         16
-#define INT_7XX_GPIO_BANK5     17
-#define INT_7XX_GPIO_BANK6     18
-#define INT_7XX_SPGIO_WR       29
+#define INT_7XX_IH2_FIQ                (NR_IRQS_LEGACY + 0)
+#define INT_7XX_IH2_IRQ                (NR_IRQS_LEGACY + 1)
+#define INT_7XX_USB_NON_ISO    (NR_IRQS_LEGACY + 2)
+#define INT_7XX_USB_ISO                (NR_IRQS_LEGACY + 3)
+#define INT_7XX_ICR            (NR_IRQS_LEGACY + 4)
+#define INT_7XX_EAC            (NR_IRQS_LEGACY + 5)
+#define INT_7XX_GPIO_BANK1     (NR_IRQS_LEGACY + 6)
+#define INT_7XX_GPIO_BANK2     (NR_IRQS_LEGACY + 7)
+#define INT_7XX_GPIO_BANK3     (NR_IRQS_LEGACY + 8)
+#define INT_7XX_McBSP2TX       (NR_IRQS_LEGACY + 10)
+#define INT_7XX_McBSP2RX       (NR_IRQS_LEGACY + 11)
+#define INT_7XX_McBSP2RX_OVF   (NR_IRQS_LEGACY + 12)
+#define INT_7XX_LCD_LINE       (NR_IRQS_LEGACY + 14)
+#define INT_7XX_GSM_PROTECT    (NR_IRQS_LEGACY + 15)
+#define INT_7XX_TIMER3         (NR_IRQS_LEGACY + 16)
+#define INT_7XX_GPIO_BANK5     (NR_IRQS_LEGACY + 17)
+#define INT_7XX_GPIO_BANK6     (NR_IRQS_LEGACY + 18)
+#define INT_7XX_SPGIO_WR       (NR_IRQS_LEGACY + 29)
 
 /*
  * IRQ numbers for interrupt handler 2
  *
  * NOTE: See also the OMAP-1510 and 1610 specific IRQ numbers below
  */
-#define IH2_BASE               32
+#define IH2_BASE               (NR_IRQS_LEGACY + 32)
 
 #define INT_KEYBOARD           (1 + IH2_BASE)
 #define INT_uWireTX            (2 + IH2_BASE)
 #endif
 #define OMAP_FPGA_IRQ_END      (OMAP_FPGA_IRQ_BASE + OMAP_FPGA_NR_IRQS)
 
-#define NR_IRQS                        OMAP_FPGA_IRQ_END
-
-#define OMAP_IRQ_BIT(irq)      (1 << ((irq) % 32))
-
-#include <mach/hardware.h>
+#define OMAP_IRQ_BIT(irq)      (1 << ((irq - NR_IRQS_LEGACY) % 32))
 
 #ifdef CONFIG_FIQ
 #define FIQ_START              1024
index 058a4f7d44c59fc9535ed6e79f353007238f012f..d43ff0f1cbf8d339525415d65e249abff3e2fc61 100644 (file)
@@ -5,6 +5,9 @@
 #ifndef __ASM_ARCH_MEMORY_H
 #define __ASM_ARCH_MEMORY_H
 
+/* REVISIT: omap1 legacy drivers still rely on this */
+#include <mach/soc.h>
+
 /*
  * Bus address is physical address, except for OMAP-1510 Local Bus.
  * OMAP-1510 bus address is translated into a Local Bus address if the
@@ -14,7 +17,6 @@
  * because of the strncmp().
  */
 #if defined(CONFIG_ARCH_OMAP15XX) && !defined(__ASSEMBLER__)
-#include <mach/soc.h>
 
 /*
  * OMAP-1510 Local Bus address offset
index 2ce6a2db470b43006e3e961b5b3fd18f12dd9c72..4700e384c3d9cf690c6191fad83ca62a50afc1b8 100644 (file)
  */
 #define OMAP_UART_INFO_OFS     0x3ffc
 
-/* OMAP1 serial ports */
-#define OMAP1_UART1_BASE       0xfffb0000
-#define OMAP1_UART2_BASE       0xfffb0800
-#define OMAP1_UART3_BASE       0xfffb9800
-
 #define OMAP_PORT_SHIFT                2
 #define OMAP7XX_PORT_SHIFT     0
 
index 612bd1cc257c147255eb9baefb86ff6d0a6a2497..3d935570eb3b45a84da004ce1ad61e719e3dff1f 100644 (file)
 #ifndef __ASM_ARCH_OMAP_CPU_H
 #define __ASM_ARCH_OMAP_CPU_H
 
+#include <asm/irq.h>
+#include <mach/hardware.h>
+#include <mach/irqs.h>
+
 #ifndef __ASSEMBLY__
 
 #include <linux/bitops.h>
index a8a533df24e102a12a01f6b0897209b014a0bc60..f4d346fda9da8c44bc201f328df4293420168fab 100644 (file)
@@ -43,6 +43,7 @@
 #include <linux/io.h>
 
 #include <asm/irq.h>
+#include <asm/exception.h>
 #include <asm/mach/irq.h>
 
 #include "soc.h"
 
 struct omap_irq_bank {
        unsigned long base_reg;
+       void __iomem *va;
        unsigned long trigger_map;
        unsigned long wake_enable;
 };
 
-u32 omap_irq_flags;
+static u32 omap_l2_irq;
 static unsigned int irq_bank_count;
 static struct omap_irq_bank *irq_banks;
+static struct irq_domain *domain;
 
-static inline void irq_bank_writel(unsigned long value, int bank, int offset)
-{
-       omap_writel(value, irq_banks[bank].base_reg + offset);
-}
-
-static void omap_ack_irq(struct irq_data *d)
+static inline unsigned int irq_bank_readl(int bank, int offset)
 {
-       if (d->irq > 31)
-               omap_writel(0x1, OMAP_IH2_BASE + IRQ_CONTROL_REG_OFFSET);
-
-       omap_writel(0x1, OMAP_IH1_BASE + IRQ_CONTROL_REG_OFFSET);
+       return readl_relaxed(irq_banks[bank].va + offset);
 }
-
-static void omap_mask_irq(struct irq_data *d)
+static inline void irq_bank_writel(unsigned long value, int bank, int offset)
 {
-       int bank = IRQ_BANK(d->irq);
-       u32 l;
-
-       l = omap_readl(irq_banks[bank].base_reg + IRQ_MIR_REG_OFFSET);
-       l |= 1 << IRQ_BIT(d->irq);
-       omap_writel(l, irq_banks[bank].base_reg + IRQ_MIR_REG_OFFSET);
+       writel_relaxed(value, irq_banks[bank].va + offset);
 }
 
-static void omap_unmask_irq(struct irq_data *d)
+static void omap_ack_irq(int irq)
 {
-       int bank = IRQ_BANK(d->irq);
-       u32 l;
+       if (irq > 31)
+               writel_relaxed(0x1, irq_banks[1].va + IRQ_CONTROL_REG_OFFSET);
 
-       l = omap_readl(irq_banks[bank].base_reg + IRQ_MIR_REG_OFFSET);
-       l &= ~(1 << IRQ_BIT(d->irq));
-       omap_writel(l, irq_banks[bank].base_reg + IRQ_MIR_REG_OFFSET);
+       writel_relaxed(0x1, irq_banks[0].va + IRQ_CONTROL_REG_OFFSET);
 }
 
 static void omap_mask_ack_irq(struct irq_data *d)
 {
-       omap_mask_irq(d);
-       omap_ack_irq(d);
-}
-
-static int omap_wake_irq(struct irq_data *d, unsigned int enable)
-{
-       int bank = IRQ_BANK(d->irq);
-
-       if (enable)
-               irq_banks[bank].wake_enable |= IRQ_BIT(d->irq);
-       else
-               irq_banks[bank].wake_enable &= ~IRQ_BIT(d->irq);
+       struct irq_chip_type *ct = irq_data_get_chip_type(d);
 
-       return 0;
+       ct->chip.irq_mask(d);
+       omap_ack_irq(d->irq);
 }
 
-
 /*
  * Allows tuning the IRQ type and priority
  *
@@ -165,46 +141,105 @@ static struct omap_irq_bank omap1610_irq_banks[] = {
 };
 #endif
 
-static struct irq_chip omap_irq_chip = {
-       .name           = "MPU",
-       .irq_ack        = omap_mask_ack_irq,
-       .irq_mask       = omap_mask_irq,
-       .irq_unmask     = omap_unmask_irq,
-       .irq_set_wake   = omap_wake_irq,
-};
+asmlinkage void __exception_irq_entry omap1_handle_irq(struct pt_regs *regs)
+{
+       void __iomem *l1 = irq_banks[0].va;
+       void __iomem *l2 = irq_banks[1].va;
+       u32 irqnr;
+
+       do {
+               irqnr = readl_relaxed(l1 + IRQ_ITR_REG_OFFSET);
+               irqnr &= ~(readl_relaxed(l1 + IRQ_MIR_REG_OFFSET) & 0xffffffff);
+               if (!irqnr)
+                       break;
+
+               irqnr = readl_relaxed(l1 + IRQ_SIR_FIQ_REG_OFFSET);
+               if (irqnr)
+                       goto irq;
+
+               irqnr = readl_relaxed(l1 + IRQ_SIR_IRQ_REG_OFFSET);
+               if (irqnr == omap_l2_irq) {
+                       irqnr = readl_relaxed(l2 + IRQ_SIR_IRQ_REG_OFFSET);
+                       if (irqnr)
+                               irqnr += 32;
+               }
+irq:
+               if (irqnr)
+                       handle_domain_irq(domain, irqnr, regs);
+               else
+                       break;
+       } while (irqnr);
+}
+
+static __init void
+omap_alloc_gc(void __iomem *base, unsigned int irq_start, unsigned int num)
+{
+       struct irq_chip_generic *gc;
+       struct irq_chip_type *ct;
+
+       gc = irq_alloc_generic_chip("MPU", 1, irq_start, base,
+                                   handle_level_irq);
+       ct = gc->chip_types;
+       ct->chip.irq_ack = omap_mask_ack_irq;
+       ct->chip.irq_mask = irq_gc_mask_set_bit;
+       ct->chip.irq_unmask = irq_gc_mask_clr_bit;
+       ct->chip.irq_set_wake = irq_gc_set_wake;
+       ct->regs.mask = IRQ_MIR_REG_OFFSET;
+       irq_setup_generic_chip(gc, IRQ_MSK(num), IRQ_GC_INIT_MASK_CACHE,
+                              IRQ_NOREQUEST | IRQ_NOPROBE, 0);
+}
 
 void __init omap1_init_irq(void)
 {
-       int i, j;
+       struct irq_chip_type *ct;
+       struct irq_data *d = NULL;
+       int i, j, irq_base;
+       unsigned long nr_irqs;
 
 #if defined(CONFIG_ARCH_OMAP730) || defined(CONFIG_ARCH_OMAP850)
        if (cpu_is_omap7xx()) {
-               omap_irq_flags = INT_7XX_IH2_IRQ;
                irq_banks = omap7xx_irq_banks;
                irq_bank_count = ARRAY_SIZE(omap7xx_irq_banks);
        }
 #endif
 #ifdef CONFIG_ARCH_OMAP15XX
        if (cpu_is_omap1510()) {
-               omap_irq_flags = INT_1510_IH2_IRQ;
                irq_banks = omap1510_irq_banks;
                irq_bank_count = ARRAY_SIZE(omap1510_irq_banks);
        }
        if (cpu_is_omap310()) {
-               omap_irq_flags = INT_1510_IH2_IRQ;
                irq_banks = omap310_irq_banks;
                irq_bank_count = ARRAY_SIZE(omap310_irq_banks);
        }
 #endif
 #if defined(CONFIG_ARCH_OMAP16XX)
        if (cpu_is_omap16xx()) {
-               omap_irq_flags = INT_1510_IH2_IRQ;
                irq_banks = omap1610_irq_banks;
                irq_bank_count = ARRAY_SIZE(omap1610_irq_banks);
        }
 #endif
-       printk("Total of %i interrupts in %i interrupt banks\n",
-              irq_bank_count * 32, irq_bank_count);
+
+       for (i = 0; i < irq_bank_count; i++) {
+               irq_banks[i].va = ioremap(irq_banks[i].base_reg, 0xff);
+               if (WARN_ON(!irq_banks[i].va))
+                       return;
+       }
+
+       nr_irqs = irq_bank_count * 32;
+
+       irq_base = irq_alloc_descs(-1, 0, nr_irqs, 0);
+       if (irq_base < 0) {
+               pr_warn("Couldn't allocate IRQ numbers\n");
+               irq_base = 0;
+       }
+       omap_l2_irq = cpu_is_omap7xx() ? irq_base + 1 : irq_base;
+       omap_l2_irq -= NR_IRQS_LEGACY;
+
+       domain = irq_domain_add_legacy(NULL, nr_irqs, irq_base, 0,
+                                      &irq_domain_simple_ops, NULL);
+
+       pr_info("Total of %lu interrupts in %i interrupt banks\n",
+               nr_irqs, irq_bank_count);
 
        /* Mask and clear all interrupts */
        for (i = 0; i < irq_bank_count; i++) {
@@ -227,19 +262,15 @@ void __init omap1_init_irq(void)
 
                        irq_trigger = irq_banks[i].trigger_map >> IRQ_BIT(j);
                        omap_irq_set_cfg(j, 0, 0, irq_trigger);
-
-                       irq_set_chip_and_handler(j, &omap_irq_chip,
-                                                handle_level_irq);
                        set_irq_flags(j, IRQF_VALID);
                }
+               omap_alloc_gc(irq_banks[i].va, irq_base + i * 32, 32);
        }
 
        /* Unmask level 2 handler */
-
-       if (cpu_is_omap7xx())
-               omap_unmask_irq(irq_get_irq_data(INT_7XX_IH2_IRQ));
-       else if (cpu_is_omap15xx())
-               omap_unmask_irq(irq_get_irq_data(INT_1510_IH2_IRQ));
-       else if (cpu_is_omap16xx())
-               omap_unmask_irq(irq_get_irq_data(INT_1610_IH2_IRQ));
+       d = irq_get_irq_data(irq_find_mapping(domain, omap_l2_irq));
+       if (d) {
+               ct = irq_data_get_chip_type(d);
+               ct->chip.irq_unmask(d);
+       }
 }
index 667ce5027f6332cffd81a47435cbce6945f1b2b9..599490a596a776e11aa2127298153b2455d0cd55 100644 (file)
@@ -36,7 +36,7 @@
 static struct omap_mux_cfg arch_mux_cfg;
 
 #if defined(CONFIG_ARCH_OMAP730) || defined(CONFIG_ARCH_OMAP850)
-static struct pin_config __initdata_or_module omap7xx_pins[] = {
+static struct pin_config omap7xx_pins[] = {
 MUX_CFG_7XX("E2_7XX_KBR0",        12,   21,    0,   20,   1, 0)
 MUX_CFG_7XX("J7_7XX_KBR1",        12,   25,    0,   24,   1, 0)
 MUX_CFG_7XX("E1_7XX_KBR2",        12,   29,    0,   28,   1, 0)
@@ -82,7 +82,7 @@ MUX_CFG_7XX("UART_7XX_2",          8,    1,    6,    0,   0, 0)
 #endif /* CONFIG_ARCH_OMAP730 || CONFIG_ARCH_OMAP850 */
 
 #if defined(CONFIG_ARCH_OMAP15XX) || defined(CONFIG_ARCH_OMAP16XX)
-static struct pin_config __initdata_or_module omap1xxx_pins[] = {
+static struct pin_config omap1xxx_pins[] = {
 /*
  *      description            mux  mode   mux  pull pull  pull  pu_pd  pu  dbg
  *                             reg  offset mode reg  bit   ena   reg
@@ -343,7 +343,7 @@ MUX_CFG("Y14_1610_CCP_DATAM",        9,   21,    6,   2,   3,   1,    2,     0,  0)
 #define OMAP1XXX_PINS_SZ       0
 #endif /* CONFIG_ARCH_OMAP15XX || CONFIG_ARCH_OMAP16XX */
 
-static int __init_or_module omap1_cfg_reg(const struct pin_config *cfg)
+static int omap1_cfg_reg(const struct pin_config *cfg)
 {
        static DEFINE_SPINLOCK(mux_spin_lock);
        unsigned long flags;
@@ -469,7 +469,7 @@ int __init omap_mux_register(struct omap_mux_cfg *arch_mux_cfg)
 /*
  * Sets the Omap MUX and PULL_DWN registers based on the table
  */
-int __init_or_module omap_cfg_reg(const unsigned long index)
+int omap_cfg_reg(const unsigned long index)
 {
        struct pin_config *reg;
 
index dd94567c36289c16303a267a86cde69cfba82e75..ee5460b8ec2ee6e93c06ab60c10bac27c03774c3 100644 (file)
@@ -62,6 +62,7 @@
 #include "iomap.h"
 #include "clock.h"
 #include "pm.h"
+#include "soc.h"
 #include "sram.h"
 
 static unsigned int arm_sleep_save[ARM_SLEEP_SAVE_SIZE];
index d1ac08016f0bbaa99d9c6a99f38b4d38869b9675..a65bd0c4429607b3c7f2090ab876aed062348311 100644 (file)
@@ -25,6 +25,7 @@
 #include <mach/mux.h>
 
 #include "pm.h"
+#include "soc.h"
 
 static struct clk * uart1_ck;
 static struct clk * uart2_ck;
index bde7a35e5000227990f9fdbdb9b04e9449e0080e..06c5ba7574a534b73531c000d6cd0948704206c3 100644 (file)
 #include <linux/platform_device.h>
 #include <linux/platform_data/dmtimer-omap.h>
 
-#include <mach/irqs.h>
-
 #include <plat/dmtimer.h>
 
+#include "soc.h"
+
 #define OMAP1610_GPTIMER1_BASE         0xfffb1400
 #define OMAP1610_GPTIMER2_BASE         0xfffb1c00
 #define OMAP1610_GPTIMER3_BASE         0xfffb2400
index 166b18f515a206ab3747d4eb51d4d1677c3879a2..4a7303cf563e09baeb0ecf473f8aa87cbfc06106 100644 (file)
@@ -224,13 +224,13 @@ static int _omap_device_notifier_call(struct notifier_block *nb,
  */
 static int _omap_device_enable_hwmods(struct omap_device *od)
 {
+       int ret = 0;
        int i;
 
        for (i = 0; i < od->hwmods_cnt; i++)
-               omap_hwmod_enable(od->hwmods[i]);
+               ret |= omap_hwmod_enable(od->hwmods[i]);
 
-       /* XXX pass along return value here? */
-       return 0;
+       return ret;
 }
 
 /**
@@ -241,13 +241,13 @@ static int _omap_device_enable_hwmods(struct omap_device *od)
  */
 static int _omap_device_idle_hwmods(struct omap_device *od)
 {
+       int ret = 0;
        int i;
 
        for (i = 0; i < od->hwmods_cnt; i++)
-               omap_hwmod_idle(od->hwmods[i]);
+               ret |= omap_hwmod_idle(od->hwmods[i]);
 
-       /* XXX pass along return value here? */
-       return 0;
+       return ret;
 }
 
 /* Public functions for use by core code */
@@ -595,18 +595,20 @@ static int _od_runtime_suspend(struct device *dev)
        int ret;
 
        ret = pm_generic_runtime_suspend(dev);
+       if (ret)
+               return ret;
 
-       if (!ret)
-               omap_device_idle(pdev);
-
-       return ret;
+       return omap_device_idle(pdev);
 }
 
 static int _od_runtime_resume(struct device *dev)
 {
        struct platform_device *pdev = to_platform_device(dev);
+       int ret;
 
-       omap_device_enable(pdev);
+       ret = omap_device_enable(pdev);
+       if (ret)
+               return ret;
 
        return pm_generic_runtime_resume(dev);
 }
@@ -743,7 +745,8 @@ int omap_device_enable(struct platform_device *pdev)
 
        ret = _omap_device_enable_hwmods(od);
 
-       od->_state = OMAP_DEVICE_STATE_ENABLED;
+       if (ret == 0)
+               od->_state = OMAP_DEVICE_STATE_ENABLED;
 
        return ret;
 }
@@ -773,7 +776,8 @@ int omap_device_idle(struct platform_device *pdev)
 
        ret = _omap_device_idle_hwmods(od);
 
-       od->_state = OMAP_DEVICE_STATE_IDLE;
+       if (ret == 0)
+               od->_state = OMAP_DEVICE_STATE_IDLE;
 
        return ret;
 }
index 752969ff9de04f95ef8b9a695325901b6297cf78..d78c12e7cb5e1ace5f79a9d28f45321e809dea24 100644 (file)
@@ -3318,16 +3318,17 @@ int omap_hwmod_enable(struct omap_hwmod *oh)
  */
 int omap_hwmod_idle(struct omap_hwmod *oh)
 {
+       int r;
        unsigned long flags;
 
        if (!oh)
                return -EINVAL;
 
        spin_lock_irqsave(&oh->_lock, flags);
-       _idle(oh);
+       r = _idle(oh);
        spin_unlock_irqrestore(&oh->_lock, flags);
 
-       return 0;
+       return r;
 }
 
 /**
@@ -3340,16 +3341,17 @@ int omap_hwmod_idle(struct omap_hwmod *oh)
  */
 int omap_hwmod_shutdown(struct omap_hwmod *oh)
 {
+       int r;
        unsigned long flags;
 
        if (!oh)
                return -EINVAL;
 
        spin_lock_irqsave(&oh->_lock, flags);
-       _shutdown(oh);
+       r = _shutdown(oh);
        spin_unlock_irqrestore(&oh->_lock, flags);
 
-       return 0;
+       return r;
 }
 
 /*
index 9611c91d9b82154e6d5d7f46c75c1b1ab6ffd588..b5d27ec81610333d99868247eebb7ba011e5cca0 100644 (file)
@@ -109,6 +109,12 @@ extern struct omap_hwmod_sysc_fields omap_hwmod_sysc_type3;
 
 #define DEBUG_OMAPUART_FLAGS   (HWMOD_INIT_NO_IDLE | HWMOD_INIT_NO_RESET)
 
+#ifdef CONFIG_OMAP_GPMC_DEBUG
+#define DEBUG_OMAP_GPMC_HWMOD_FLAGS    HWMOD_INIT_NO_RESET
+#else
+#define DEBUG_OMAP_GPMC_HWMOD_FLAGS    0
+#endif
+
 #if defined(CONFIG_DEBUG_OMAP2UART1)
 #undef DEBUG_OMAP2UART1_FLAGS
 #define DEBUG_OMAP2UART1_FLAGS DEBUG_OMAPUART_FLAGS
index 8821b9d6bae432859a6415f5686e10f977e92ae4..6dcfd03ced8faf878746245e8aaf4b45ded3a757 100644 (file)
@@ -762,16 +762,8 @@ struct omap_hwmod omap2xxx_gpmc_hwmod = {
        .name           = "gpmc",
        .class          = &omap2xxx_gpmc_hwmod_class,
        .main_clk       = "gpmc_fck",
-       /*
-        * XXX HWMOD_INIT_NO_RESET should not be needed for this IP
-        * block.  It is not being added due to any known bugs with
-        * resetting the GPMC IP block, but rather because any timings
-        * set by the bootloader are not being correctly programmed by
-        * the kernel from the board file or DT data.
-        * HWMOD_INIT_NO_RESET should be removed ASAP.
-        */
-       .flags          = (HWMOD_INIT_NO_IDLE | HWMOD_INIT_NO_RESET |
-                          HWMOD_NO_IDLEST),
+       /* Skip reset for CONFIG_OMAP_GPMC_DEBUG for bootloader timings */
+       .flags          = HWMOD_NO_IDLEST | DEBUG_OMAP_GPMC_HWMOD_FLAGS,
        .prcm           = {
                .omap2  = {
                        .prcm_reg_id = 3,
index 130332c0534d341c67de45167e6b81b46a4c3c56..7f737965f543325b8c7fe1a50b4453f09f15b767 100644 (file)
@@ -145,6 +145,7 @@ extern struct omap_hwmod am33xx_uart5_hwmod;
 extern struct omap_hwmod am33xx_uart6_hwmod;
 extern struct omap_hwmod am33xx_wd_timer1_hwmod;
 
+extern struct omap_hwmod_class am33xx_emif_hwmod_class;
 extern struct omap_hwmod_class am33xx_l4_hwmod_class;
 extern struct omap_hwmod_class am33xx_wkup_m3_hwmod_class;
 extern struct omap_hwmod_class am33xx_control_hwmod_class;
index cabc5695b5043dd3c55db960de5103f4dcdbd2f9..907a452b78ea240b07d061993d4355b0dbde01a4 100644 (file)
@@ -202,6 +202,19 @@ struct omap_hwmod am33xx_prcm_hwmod = {
        .clkdm_name     = "l4_wkup_clkdm",
 };
 
+/*
+ * 'emif' class
+ * instance(s): emif
+ */
+static struct omap_hwmod_class_sysconfig am33xx_emif_sysc = {
+       .rev_offs       = 0x0000,
+};
+
+struct omap_hwmod_class am33xx_emif_hwmod_class = {
+       .name           = "emif",
+       .sysc           = &am33xx_emif_sysc,
+};
+
 /*
  * 'aes0' class
  */
@@ -668,7 +681,8 @@ struct omap_hwmod am33xx_gpmc_hwmod = {
        .name           = "gpmc",
        .class          = &am33xx_gpmc_hwmod_class,
        .clkdm_name     = "l3s_clkdm",
-       .flags          = (HWMOD_INIT_NO_IDLE | HWMOD_INIT_NO_RESET),
+       /* Skip reset for CONFIG_OMAP_GPMC_DEBUG for bootloader timings */
+       .flags          = DEBUG_OMAP_GPMC_HWMOD_FLAGS,
        .main_clk       = "l3s_gclk",
        .prcm           = {
                .omap4  = {
index 0cf7b563dcd137702921b1033c1215d0108bd811..cc0791d9125be8f5f7ead557665990ee851fbeda 100644 (file)
  * IP blocks
  */
 
-/*
- * 'emif' class
- * instance(s): emif
- */
-static struct omap_hwmod_class_sysconfig am33xx_emif_sysc = {
-       .rev_offs       = 0x0000,
-};
-
-static struct omap_hwmod_class am33xx_emif_hwmod_class = {
-       .name           = "emif",
-       .sysc           = &am33xx_emif_sysc,
-};
-
 /* emif */
 static struct omap_hwmod am33xx_emif_hwmod = {
        .name           = "emif",
index 4e8e93c398db77ac98c235f38cf57354c5f2ab96..dc55f8dedf2c6bb597bddd858d9acd960398fceb 100644 (file)
@@ -2169,16 +2169,8 @@ static struct omap_hwmod omap3xxx_gpmc_hwmod = {
        .clkdm_name     = "core_l3_clkdm",
        .mpu_irqs       = omap3xxx_gpmc_irqs,
        .main_clk       = "gpmc_fck",
-       /*
-        * XXX HWMOD_INIT_NO_RESET should not be needed for this IP
-        * block.  It is not being added due to any known bugs with
-        * resetting the GPMC IP block, but rather because any timings
-        * set by the bootloader are not being correctly programmed by
-        * the kernel from the board file or DT data.
-        * HWMOD_INIT_NO_RESET should be removed ASAP.
-        */
-       .flags          = (HWMOD_INIT_NO_IDLE | HWMOD_INIT_NO_RESET |
-                          HWMOD_NO_IDLEST),
+       /* Skip reset for CONFIG_OMAP_GPMC_DEBUG for bootloader timings */
+       .flags          = HWMOD_NO_IDLEST | DEBUG_OMAP_GPMC_HWMOD_FLAGS,
 };
 
 /*
@@ -3744,29 +3736,54 @@ static struct omap_hwmod_ocp_if *omap3xxx_hwmod_ocp_ifs[] __initdata = {
 /* GP-only hwmod links */
 static struct omap_hwmod_ocp_if *omap34xx_gp_hwmod_ocp_ifs[] __initdata = {
        &omap3xxx_l4_sec__timer12,
-       &omap3xxx_l4_core__sham,
-       &omap3xxx_l4_core__aes,
        NULL
 };
 
 static struct omap_hwmod_ocp_if *omap36xx_gp_hwmod_ocp_ifs[] __initdata = {
        &omap3xxx_l4_sec__timer12,
-       &omap3xxx_l4_core__sham,
-       &omap3xxx_l4_core__aes,
        NULL
 };
 
 static struct omap_hwmod_ocp_if *am35xx_gp_hwmod_ocp_ifs[] __initdata = {
        &omap3xxx_l4_sec__timer12,
-       /*
-        * Apparently the SHA/MD5 and AES accelerator IP blocks are
-        * only present on some AM35xx chips, and no one knows which
-        * ones.  See
-        * http://www.spinics.net/lists/arm-kernel/msg215466.html So
-        * if you need these IP blocks on an AM35xx, try uncommenting
-        * the following lines.
-        */
+       NULL
+};
+
+/* crypto hwmod links */
+static struct omap_hwmod_ocp_if *omap34xx_sham_hwmod_ocp_ifs[] __initdata = {
+       &omap3xxx_l4_core__sham,
+       NULL
+};
+
+static struct omap_hwmod_ocp_if *omap34xx_aes_hwmod_ocp_ifs[] __initdata = {
+       &omap3xxx_l4_core__aes,
+       NULL
+};
+
+static struct omap_hwmod_ocp_if *omap36xx_sham_hwmod_ocp_ifs[] __initdata = {
+       &omap3xxx_l4_core__sham,
+       NULL
+};
+
+static struct omap_hwmod_ocp_if *omap36xx_aes_hwmod_ocp_ifs[] __initdata = {
+       &omap3xxx_l4_core__aes,
+       NULL
+};
+
+/*
+ * Apparently the SHA/MD5 and AES accelerator IP blocks are
+ * only present on some AM35xx chips, and no one knows which
+ * ones.  See
+ * http://www.spinics.net/lists/arm-kernel/msg215466.html So
+ * if you need these IP blocks on an AM35xx, try uncommenting
+ * the following lines.
+ */
+static struct omap_hwmod_ocp_if *am35xx_sham_hwmod_ocp_ifs[] __initdata = {
        /* &omap3xxx_l4_core__sham, */
+       NULL
+};
+
+static struct omap_hwmod_ocp_if *am35xx_aes_hwmod_ocp_ifs[] __initdata = {
        /* &omap3xxx_l4_core__aes, */
        NULL
 };
@@ -3868,10 +3885,41 @@ static struct omap_hwmod_ocp_if *omap3xxx_dss_hwmod_ocp_ifs[] __initdata = {
        NULL
 };
 
+/**
+ * omap3xxx_hwmod_is_hs_ip_block_usable - is a security IP block accessible?
+ * @bus: struct device_node * for the top-level OMAP DT data
+ * @dev_name: device name used in the DT file
+ *
+ * Determine whether a "secure" IP block @dev_name is usable by Linux.
+ * There doesn't appear to be a 100% reliable way to determine this,
+ * so we rely on heuristics.  If @bus is null, meaning there's no DT
+ * data, then we only assume the IP block is accessible if the OMAP is
+ * fused as a 'general-purpose' SoC.  If however DT data is present,
+ * test to see if the IP block is described in the DT data and set to
+ * 'status = "okay"'.  If so then we assume the ODM has configured the
+ * OMAP firewalls to allow access to the IP block.
+ *
+ * Return: 0 if device named @dev_name is not likely to be accessible,
+ * or 1 if it is likely to be accessible.
+ */
+static int __init omap3xxx_hwmod_is_hs_ip_block_usable(struct device_node *bus,
+                                                      const char *dev_name)
+{
+       if (!bus)
+               return (omap_type() == OMAP2_DEVICE_TYPE_GP) ? 1 : 0;
+
+       if (of_device_is_available(of_find_node_by_name(bus, dev_name)))
+               return 1;
+
+       return 0;
+}
+
 int __init omap3xxx_hwmod_init(void)
 {
        int r;
-       struct omap_hwmod_ocp_if **h = NULL, **h_gp = NULL;
+       struct omap_hwmod_ocp_if **h = NULL, **h_gp = NULL, **h_sham = NULL;
+       struct omap_hwmod_ocp_if **h_aes = NULL;
+       struct device_node *bus = NULL;
        unsigned int rev;
 
        omap_hwmod_init();
@@ -3893,13 +3941,19 @@ int __init omap3xxx_hwmod_init(void)
            rev == OMAP3430_REV_ES3_1 || rev == OMAP3430_REV_ES3_1_2) {
                h = omap34xx_hwmod_ocp_ifs;
                h_gp = omap34xx_gp_hwmod_ocp_ifs;
+               h_sham = omap34xx_sham_hwmod_ocp_ifs;
+               h_aes = omap34xx_aes_hwmod_ocp_ifs;
        } else if (rev == AM35XX_REV_ES1_0 || rev == AM35XX_REV_ES1_1) {
                h = am35xx_hwmod_ocp_ifs;
                h_gp = am35xx_gp_hwmod_ocp_ifs;
+               h_sham = am35xx_sham_hwmod_ocp_ifs;
+               h_aes = am35xx_aes_hwmod_ocp_ifs;
        } else if (rev == OMAP3630_REV_ES1_0 || rev == OMAP3630_REV_ES1_1 ||
                   rev == OMAP3630_REV_ES1_2) {
                h = omap36xx_hwmod_ocp_ifs;
                h_gp = omap36xx_gp_hwmod_ocp_ifs;
+               h_sham = omap36xx_sham_hwmod_ocp_ifs;
+               h_aes = omap36xx_aes_hwmod_ocp_ifs;
        } else {
                WARN(1, "OMAP3 hwmod family init: unknown chip type\n");
                return -EINVAL;
@@ -3916,6 +3970,25 @@ int __init omap3xxx_hwmod_init(void)
                        return r;
        }
 
+       /*
+        * Register crypto hwmod links only if they are not disabled in DT.
+        * If DT information is missing, enable them only for GP devices.
+        */
+
+       if (of_have_populated_dt())
+               bus = of_find_node_by_name(NULL, "ocp");
+
+       if (h_sham && omap3xxx_hwmod_is_hs_ip_block_usable(bus, "sham")) {
+               r = omap_hwmod_register_links(h_sham);
+               if (r < 0)
+                       return r;
+       }
+
+       if (h_aes && omap3xxx_hwmod_is_hs_ip_block_usable(bus, "aes")) {
+               r = omap_hwmod_register_links(h_aes);
+               if (r < 0)
+                       return r;
+       }
 
        /*
         * Register hwmod links specific to certain ES levels of a
index 17e8004fc20f9e48c69722c32643f7684b7c9eb2..215d5efa0dba1d3c3773332ce4db315554df318e 100644 (file)
 
 
 /* IP blocks */
+static struct omap_hwmod am43xx_emif_hwmod = {
+       .name           = "emif",
+       .class          = &am33xx_emif_hwmod_class,
+       .clkdm_name     = "emif_clkdm",
+       .flags          = HWMOD_INIT_NO_IDLE,
+       .main_clk       = "dpll_ddr_m2_ck",
+       .prcm           = {
+               .omap4  = {
+                       .clkctrl_offs   = AM43XX_CM_PER_EMIF_CLKCTRL_OFFSET,
+                       .modulemode     = MODULEMODE_SWCTRL,
+               },
+       },
+};
+
 static struct omap_hwmod am43xx_l4_hs_hwmod = {
        .name           = "l4_hs",
        .class          = &am33xx_l4_hwmod_class,
@@ -583,6 +597,13 @@ static struct omap_hwmod am43xx_vpfe1_hwmod = {
 };
 
 /* Interfaces */
+static struct omap_hwmod_ocp_if am43xx_l3_main__emif = {
+       .master         = &am33xx_l3_main_hwmod,
+       .slave          = &am43xx_emif_hwmod,
+       .clk            = "dpll_core_m4_ck",
+       .user           = OCP_USER_MPU | OCP_USER_SDMA,
+};
+
 static struct omap_hwmod_ocp_if am43xx_l3_main__l4_hs = {
        .master         = &am33xx_l3_main_hwmod,
        .slave          = &am43xx_l4_hs_hwmod,
@@ -918,6 +939,7 @@ static struct omap_hwmod_ocp_if *am43xx_hwmod_ocp_ifs[] __initdata = {
        &am33xx_l3_main__l3_instr,
        &am33xx_l3_main__gfx,
        &am33xx_l3_s__l3_main,
+       &am43xx_l3_main__emif,
        &am33xx_pruss__l3_main,
        &am43xx_wkup_m3__l4_wkup,
        &am33xx_gfx__l3_main,
index f5e68a7820251360dc1aad459e259ee1c6d217ae..43eebf2c59e2f71a375cdbc5d3dbf227f7b99378 100644 (file)
@@ -1188,15 +1188,8 @@ static struct omap_hwmod omap44xx_gpmc_hwmod = {
        .name           = "gpmc",
        .class          = &omap44xx_gpmc_hwmod_class,
        .clkdm_name     = "l3_2_clkdm",
-       /*
-        * XXX HWMOD_INIT_NO_RESET should not be needed for this IP
-        * block.  It is not being added due to any known bugs with
-        * resetting the GPMC IP block, but rather because any timings
-        * set by the bootloader are not being correctly programmed by
-        * the kernel from the board file or DT data.
-        * HWMOD_INIT_NO_RESET should be removed ASAP.
-        */
-       .flags          = HWMOD_INIT_NO_IDLE | HWMOD_INIT_NO_RESET,
+       /* Skip reset for CONFIG_OMAP_GPMC_DEBUG for bootloader timings */
+       .flags          = DEBUG_OMAP_GPMC_HWMOD_FLAGS,
        .prcm = {
                .omap4 = {
                        .clkctrl_offs = OMAP4_CM_L3_2_GPMC_CLKCTRL_OFFSET,
index 0e64c2fac0b5fad2c92af76a2042a1080108fc04..a0411f32e8b140d54fd0e5f2c4b6a860bd5db699 100644 (file)
@@ -819,8 +819,8 @@ static struct omap_hwmod dra7xx_gpmc_hwmod = {
        .name           = "gpmc",
        .class          = &dra7xx_gpmc_hwmod_class,
        .clkdm_name     = "l3main1_clkdm",
-       .flags          = (HWMOD_INIT_NO_IDLE | HWMOD_INIT_NO_RESET |
-                          HWMOD_SWSUP_SIDLE),
+       /* Skip reset for CONFIG_OMAP_GPMC_DEBUG for bootloader timings */
+       .flags          = HWMOD_SWSUP_SIDLE | DEBUG_OMAP_GPMC_HWMOD_FLAGS,
        .main_clk       = "l3_iclk_div",
        .prcm = {
                .omap4 = {
index cab1eb61ac96ef5c2599e85c04f242ad5d54bbf3..c92413769144820f24e1a2cff369ff7910e06f2e 100644 (file)
@@ -478,6 +478,8 @@ static struct omap_hwmod dm81xx_gpmc_hwmod = {
        .clkdm_name     = "alwon_l3s_clkdm",
        .class          = &dm81xx_gpmc_hwmod_class,
        .main_clk       = "sysclk6_ck",
+       /* Skip reset for CONFIG_OMAP_GPMC_DEBUG for bootloader timings */
+       .flags          = DEBUG_OMAP_GPMC_HWMOD_FLAGS,
        .prcm = {
                .omap4 = {
                        .clkctrl_offs = DM816X_CM_ALWON_GPMC_CLKCTRL,
index d0261996db6d5e0e0f91f40e9429b4c9ea73a4c8..7eebc27fa89219b3138dfb968a20f26b0edee565 100644 (file)
 #define AM43XX_CM_PER_HDQ1W_CLKCTRL_OFFSET             0x04a0
 #define AM43XX_CM_PER_VPFE0_CLKCTRL_OFFSET             0x0068
 #define AM43XX_CM_PER_VPFE1_CLKCTRL_OFFSET             0x0070
+#define AM43XX_CM_PER_EMIF_CLKCTRL_OFFSET              0x0720
+
 #endif
index 4087d334ecdfc6e36ace6ed23ce30fb9198ee6ef..2ceed407eda975141643e9ba973cae4a9e221390 100644 (file)
@@ -3,16 +3,15 @@
 #
 
 # Common support (must be linked before board specific support)
-obj-y                          += clock.o devices.o generic.o irq.o \
-                                  reset.o
+obj-y                          += devices.o generic.o irq.o reset.o
 obj-$(CONFIG_PM)               += pm.o sleep.o standby.o
 
 # Generic drivers that other drivers may depend upon
 
 # SoC-specific code
-obj-$(CONFIG_PXA25x)           += mfp-pxa2xx.o clock-pxa2xx.o pxa2xx.o pxa25x.o
-obj-$(CONFIG_PXA27x)           += mfp-pxa2xx.o clock-pxa2xx.o pxa2xx.o pxa27x.o
-obj-$(CONFIG_PXA3xx)           += mfp-pxa3xx.o clock-pxa3xx.o pxa3xx.o smemc.o pxa3xx-ulpi.o
+obj-$(CONFIG_PXA25x)           += mfp-pxa2xx.o pxa2xx.o pxa25x.o
+obj-$(CONFIG_PXA27x)           += mfp-pxa2xx.o pxa2xx.o pxa27x.o
+obj-$(CONFIG_PXA3xx)           += mfp-pxa3xx.o pxa3xx.o smemc.o pxa3xx-ulpi.o
 obj-$(CONFIG_CPU_PXA300)       += pxa300.o
 obj-$(CONFIG_CPU_PXA320)       += pxa320.o
 obj-$(CONFIG_CPU_PXA930)       += pxa930.o
diff --git a/arch/arm/mach-pxa/clock-pxa2xx.c b/arch/arm/mach-pxa/clock-pxa2xx.c
deleted file mode 100644 (file)
index 9ee2ad6..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * linux/arch/arm/mach-pxa/clock-pxa2xx.c
- *
- * 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/module.h>
-#include <linux/kernel.h>
-#include <linux/init.h>
-#include <linux/io.h>
-#include <linux/syscore_ops.h>
-
-#include <mach/pxa2xx-regs.h>
-
-#include "clock.h"
-
-void clk_pxa2xx_cken_enable(struct clk *clk)
-{
-       CKEN |= 1 << clk->cken;
-}
-
-void clk_pxa2xx_cken_disable(struct clk *clk)
-{
-       CKEN &= ~(1 << clk->cken);
-}
-
-const struct clkops clk_pxa2xx_cken_ops = {
-       .enable         = clk_pxa2xx_cken_enable,
-       .disable        = clk_pxa2xx_cken_disable,
-};
-
-#ifdef CONFIG_PM
-static uint32_t saved_cken;
-
-static int pxa2xx_clock_suspend(void)
-{
-       saved_cken = CKEN;
-       return 0;
-}
-
-static void pxa2xx_clock_resume(void)
-{
-       CKEN = saved_cken;
-}
-#else
-#define pxa2xx_clock_suspend   NULL
-#define pxa2xx_clock_resume    NULL
-#endif
-
-struct syscore_ops pxa2xx_clock_syscore_ops = {
-       .suspend        = pxa2xx_clock_suspend,
-       .resume         = pxa2xx_clock_resume,
-};
diff --git a/arch/arm/mach-pxa/clock-pxa3xx.c b/arch/arm/mach-pxa/clock-pxa3xx.c
deleted file mode 100644 (file)
index d4e9499..0000000
+++ /dev/null
@@ -1,212 +0,0 @@
-/*
- * linux/arch/arm/mach-pxa/clock-pxa3xx.c
- *
- * 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/module.h>
-#include <linux/kernel.h>
-#include <linux/init.h>
-#include <linux/io.h>
-#include <linux/syscore_ops.h>
-
-#include <mach/smemc.h>
-#include <mach/pxa3xx-regs.h>
-
-#include "clock.h"
-
-/* Crystal clock: 13MHz */
-#define BASE_CLK       13000000
-
-/* Ring Oscillator Clock: 60MHz */
-#define RO_CLK         60000000
-
-#define ACCR_D0CS      (1 << 26)
-#define ACCR_PCCE      (1 << 11)
-
-/* crystal frequency to HSIO bus frequency multiplier (HSS) */
-static unsigned char hss_mult[4] = { 8, 12, 16, 24 };
-
-/*
- * Get the clock frequency as reflected by CCSR and the turbo flag.
- * We assume these values have been applied via a fcs.
- * If info is not 0 we also display the current settings.
- */
-unsigned int pxa3xx_get_clk_frequency_khz(int info)
-{
-       unsigned long acsr, xclkcfg;
-       unsigned int t, xl, xn, hss, ro, XL, XN, CLK, HSS;
-
-       /* Read XCLKCFG register turbo bit */
-       __asm__ __volatile__("mrc\tp14, 0, %0, c6, c0, 0" : "=r"(xclkcfg));
-       t = xclkcfg & 0x1;
-
-       acsr = ACSR;
-
-       xl  = acsr & 0x1f;
-       xn  = (acsr >> 8) & 0x7;
-       hss = (acsr >> 14) & 0x3;
-
-       XL = xl * BASE_CLK;
-       XN = xn * XL;
-
-       ro = acsr & ACCR_D0CS;
-
-       CLK = (ro) ? RO_CLK : ((t) ? XN : XL);
-       HSS = (ro) ? RO_CLK : hss_mult[hss] * BASE_CLK;
-
-       if (info) {
-               pr_info("RO Mode clock: %d.%02dMHz (%sactive)\n",
-                       RO_CLK / 1000000, (RO_CLK % 1000000) / 10000,
-                       (ro) ? "" : "in");
-               pr_info("Run Mode clock: %d.%02dMHz (*%d)\n",
-                       XL / 1000000, (XL % 1000000) / 10000, xl);
-               pr_info("Turbo Mode clock: %d.%02dMHz (*%d, %sactive)\n",
-                       XN / 1000000, (XN % 1000000) / 10000, xn,
-                       (t) ? "" : "in");
-               pr_info("HSIO bus clock: %d.%02dMHz\n",
-                       HSS / 1000000, (HSS % 1000000) / 10000);
-       }
-
-       return CLK / 1000;
-}
-
-/*
- * Return the current AC97 clock frequency.
- */
-static unsigned long clk_pxa3xx_ac97_getrate(struct clk *clk)
-{
-       unsigned long rate = 312000000;
-       unsigned long ac97_div;
-
-       ac97_div = AC97_DIV;
-
-       /* This may loose precision for some rates but won't for the
-        * standard 24.576MHz.
-        */
-       rate /= (ac97_div >> 12) & 0x7fff;
-       rate *= (ac97_div & 0xfff);
-
-       return rate;
-}
-
-/*
- * Return the current HSIO bus clock frequency
- */
-static unsigned long clk_pxa3xx_hsio_getrate(struct clk *clk)
-{
-       unsigned long acsr;
-       unsigned int hss, hsio_clk;
-
-       acsr = ACSR;
-
-       hss = (acsr >> 14) & 0x3;
-       hsio_clk = (acsr & ACCR_D0CS) ? RO_CLK : hss_mult[hss] * BASE_CLK;
-
-       return hsio_clk;
-}
-
-/* crystal frequency to static memory controller multiplier (SMCFS) */
-static unsigned int smcfs_mult[8] = { 6, 0, 8, 0, 0, 16, };
-static unsigned int df_clkdiv[4] = { 1, 2, 4, 1 };
-
-static unsigned long clk_pxa3xx_smemc_getrate(struct clk *clk)
-{
-       unsigned long acsr = ACSR;
-       unsigned long memclkcfg = __raw_readl(MEMCLKCFG);
-
-       return BASE_CLK * smcfs_mult[(acsr >> 23) & 0x7] /
-                       df_clkdiv[(memclkcfg >> 16) & 0x3];
-}
-
-void clk_pxa3xx_cken_enable(struct clk *clk)
-{
-       unsigned long mask = 1ul << (clk->cken & 0x1f);
-
-       if (clk->cken < 32)
-               CKENA |= mask;
-       else if (clk->cken < 64)
-               CKENB |= mask;
-       else
-               CKENC |= mask;
-}
-
-void clk_pxa3xx_cken_disable(struct clk *clk)
-{
-       unsigned long mask = 1ul << (clk->cken & 0x1f);
-
-       if (clk->cken < 32)
-               CKENA &= ~mask;
-       else if (clk->cken < 64)
-               CKENB &= ~mask;
-       else
-               CKENC &= ~mask;
-}
-
-const struct clkops clk_pxa3xx_cken_ops = {
-       .enable         = clk_pxa3xx_cken_enable,
-       .disable        = clk_pxa3xx_cken_disable,
-};
-
-const struct clkops clk_pxa3xx_hsio_ops = {
-       .enable         = clk_pxa3xx_cken_enable,
-       .disable        = clk_pxa3xx_cken_disable,
-       .getrate        = clk_pxa3xx_hsio_getrate,
-};
-
-const struct clkops clk_pxa3xx_ac97_ops = {
-       .enable         = clk_pxa3xx_cken_enable,
-       .disable        = clk_pxa3xx_cken_disable,
-       .getrate        = clk_pxa3xx_ac97_getrate,
-};
-
-const struct clkops clk_pxa3xx_smemc_ops = {
-       .enable         = clk_pxa3xx_cken_enable,
-       .disable        = clk_pxa3xx_cken_disable,
-       .getrate        = clk_pxa3xx_smemc_getrate,
-};
-
-static void clk_pout_enable(struct clk *clk)
-{
-       OSCC |= OSCC_PEN;
-}
-
-static void clk_pout_disable(struct clk *clk)
-{
-       OSCC &= ~OSCC_PEN;
-}
-
-const struct clkops clk_pxa3xx_pout_ops = {
-       .enable         = clk_pout_enable,
-       .disable        = clk_pout_disable,
-};
-
-#ifdef CONFIG_PM
-static uint32_t cken[2];
-static uint32_t accr;
-
-static int pxa3xx_clock_suspend(void)
-{
-       cken[0] = CKENA;
-       cken[1] = CKENB;
-       accr = ACCR;
-       return 0;
-}
-
-static void pxa3xx_clock_resume(void)
-{
-       ACCR = accr;
-       CKENA = cken[0];
-       CKENB = cken[1];
-}
-#else
-#define pxa3xx_clock_suspend   NULL
-#define pxa3xx_clock_resume    NULL
-#endif
-
-struct syscore_ops pxa3xx_clock_syscore_ops = {
-       .suspend        = pxa3xx_clock_suspend,
-       .resume         = pxa3xx_clock_resume,
-};
diff --git a/arch/arm/mach-pxa/clock.c b/arch/arm/mach-pxa/clock.c
deleted file mode 100644 (file)
index 4d46610..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- *  linux/arch/arm/mach-sa1100/clock.c
- */
-#include <linux/module.h>
-#include <linux/kernel.h>
-#include <linux/clk.h>
-#include <linux/spinlock.h>
-#include <linux/delay.h>
-#include <linux/clkdev.h>
-
-#include "clock.h"
-
-static DEFINE_SPINLOCK(clocks_lock);
-
-int clk_enable(struct clk *clk)
-{
-       unsigned long flags;
-
-       spin_lock_irqsave(&clocks_lock, flags);
-       if (clk->enabled++ == 0)
-               clk->ops->enable(clk);
-       spin_unlock_irqrestore(&clocks_lock, flags);
-
-       if (clk->delay)
-               udelay(clk->delay);
-
-       return 0;
-}
-EXPORT_SYMBOL(clk_enable);
-
-void clk_disable(struct clk *clk)
-{
-       unsigned long flags;
-
-       WARN_ON(clk->enabled == 0);
-
-       spin_lock_irqsave(&clocks_lock, flags);
-       if (--clk->enabled == 0)
-               clk->ops->disable(clk);
-       spin_unlock_irqrestore(&clocks_lock, flags);
-}
-EXPORT_SYMBOL(clk_disable);
-
-unsigned long clk_get_rate(struct clk *clk)
-{
-       unsigned long rate;
-
-       rate = clk->rate;
-       if (clk->ops->getrate)
-               rate = clk->ops->getrate(clk);
-
-       return rate;
-}
-EXPORT_SYMBOL(clk_get_rate);
-
-int clk_set_rate(struct clk *clk, unsigned long rate)
-{
-       unsigned long flags;
-       int ret = -EINVAL;
-
-       if (clk->ops->setrate) {
-               spin_lock_irqsave(&clocks_lock, flags);
-               ret = clk->ops->setrate(clk, rate);
-               spin_unlock_irqrestore(&clocks_lock, flags);
-       }
-
-       return ret;
-}
-EXPORT_SYMBOL(clk_set_rate);
-
-void clk_dummy_enable(struct clk *clk)
-{
-}
-
-void clk_dummy_disable(struct clk *clk)
-{
-}
-
-const struct clkops clk_dummy_ops = {
-       .enable         = clk_dummy_enable,
-       .disable        = clk_dummy_disable,
-};
-
-struct clk clk_dummy = {
-       .ops            = &clk_dummy_ops,
-};
diff --git a/arch/arm/mach-pxa/clock.h b/arch/arm/mach-pxa/clock.h
deleted file mode 100644 (file)
index 1f65d32..0000000
+++ /dev/null
@@ -1,80 +0,0 @@
-#include <linux/clkdev.h>
-#include <linux/syscore_ops.h>
-
-struct clkops {
-       void                    (*enable)(struct clk *);
-       void                    (*disable)(struct clk *);
-       unsigned long           (*getrate)(struct clk *);
-       int                     (*setrate)(struct clk *, unsigned long);
-};
-
-struct clk {
-       const struct clkops     *ops;
-       unsigned long           rate;
-       unsigned int            cken;
-       unsigned int            delay;
-       unsigned int            enabled;
-};
-
-void clk_dummy_enable(struct clk *);
-void clk_dummy_disable(struct clk *);
-
-extern const struct clkops clk_dummy_ops;
-extern struct clk clk_dummy;
-
-#define INIT_CLKREG(_clk,_devname,_conname)            \
-       {                                               \
-               .clk            = _clk,                 \
-               .dev_id         = _devname,             \
-               .con_id         = _conname,             \
-       }
-
-#define DEFINE_CK(_name, _cken, _ops)                  \
-struct clk clk_##_name = {                             \
-               .ops    = _ops,                         \
-               .cken   = CKEN_##_cken,                 \
-       }
-
-#define DEFINE_CLK(_name, _ops, _rate, _delay)         \
-struct clk clk_##_name = {                             \
-               .ops    = _ops,                         \
-               .rate   = _rate,                        \
-               .delay  = _delay,                       \
-       }
-
-#define DEFINE_PXA2_CKEN(_name, _cken, _rate, _delay)  \
-struct clk clk_##_name = {                             \
-               .ops    = &clk_pxa2xx_cken_ops,         \
-               .rate   = _rate,                        \
-               .cken   = CKEN_##_cken,                 \
-               .delay  = _delay,                       \
-       }
-
-extern const struct clkops clk_pxa2xx_cken_ops;
-
-void clk_pxa2xx_cken_enable(struct clk *clk);
-void clk_pxa2xx_cken_disable(struct clk *clk);
-
-extern struct syscore_ops pxa2xx_clock_syscore_ops;
-
-#if defined(CONFIG_PXA3xx)
-#define DEFINE_PXA3_CKEN(_name, _cken, _rate, _delay)  \
-struct clk clk_##_name = {                             \
-               .ops    = &clk_pxa3xx_cken_ops,         \
-               .rate   = _rate,                        \
-               .cken   = CKEN_##_cken,                 \
-               .delay  = _delay,                       \
-       }
-
-extern const struct clkops clk_pxa3xx_cken_ops;
-extern const struct clkops clk_pxa3xx_hsio_ops;
-extern const struct clkops clk_pxa3xx_ac97_ops;
-extern const struct clkops clk_pxa3xx_pout_ops;
-extern const struct clkops clk_pxa3xx_smemc_ops;
-
-extern void clk_pxa3xx_cken_enable(struct clk *);
-extern void clk_pxa3xx_cken_disable(struct clk *);
-
-extern struct syscore_ops pxa3xx_clock_syscore_ops;
-
-#endif
index cfb864173ce33b13ea01a5cab8321c0fc9f4131f..11863be590665a5ca41736a9e546f377e8bfdbc6 100644 (file)
@@ -12,6 +12,7 @@
 
 #include <linux/kernel.h>
 #include <linux/init.h>
+#include <linux/clk-provider.h>
 #include <linux/gpio.h>
 #include <linux/delay.h>
 #include <linux/platform_device.h>
@@ -39,7 +40,6 @@
 
 #include "devices.h"
 #include "generic.h"
-#include "clock.h"
 
 /* Only e800 has 128MB RAM */
 void __init eseries_fixup(struct tag *tags, char **cmdline)
@@ -125,27 +125,9 @@ struct resource eseries_tmio_resources[] = {
 };
 
 /* Some e-series hardware cannot control the 32K clock */
-static void clk_32k_dummy(struct clk *clk)
-{
-}
-
-static const struct clkops clk_32k_dummy_ops = {
-       .enable         = clk_32k_dummy,
-       .disable        = clk_32k_dummy,
-};
-
-static struct clk tmio_dummy_clk = {
-       .ops    = &clk_32k_dummy_ops,
-       .rate   = 32768,
-};
-
-static struct clk_lookup eseries_clkregs[] = {
-       INIT_CLKREG(&tmio_dummy_clk, NULL, "CLK_CK32K"),
-};
-
 static void __init eseries_register_clks(void)
 {
-       clkdev_add_table(eseries_clkregs, ARRAY_SIZE(eseries_clkregs));
+       clk_register_fixed_rate(NULL, "CLK_CK32K", NULL, CLK_IS_ROOT, 32768);
 }
 
 #ifdef CONFIG_MACH_E330
@@ -683,7 +665,7 @@ static unsigned long e750_pin_config[] __initdata = {
        /* PC Card */
        GPIO8_GPIO,   /* CD0 */
        GPIO44_GPIO,  /* CD1 */
-       GPIO11_GPIO,  /* IRQ0 */
+       /* GPIO11_GPIO,  IRQ0 */
        GPIO6_GPIO,   /* IRQ1 */
        GPIO27_GPIO,  /* RST0 */
        GPIO24_GPIO,  /* RST1 */
@@ -778,6 +760,9 @@ static unsigned long e800_pin_config[] __initdata = {
        GPIO29_AC97_SDATA_IN_0,
        GPIO30_AC97_SDATA_OUT,
        GPIO31_AC97_SYNC,
+
+       /* tc6393xb */
+       GPIO11_3_6MHz,
 };
 
 static struct w100_gen_regs e800_lcd_regs = {
index 04b013fbc98f46a02ae227fe86c631fa26985caa..ec510ecf83702f90d376369e799ab97d0bd5780b 100644 (file)
@@ -63,6 +63,12 @@ EXPORT_SYMBOL(get_clock_tick_rate);
  */
 void __init pxa_timer_init(void)
 {
+       if (cpu_is_pxa25x())
+               pxa25x_clocks_init();
+       if (cpu_is_pxa27x())
+               pxa27x_clocks_init();
+       if (cpu_is_pxa3xx())
+               pxa3xx_clocks_init();
        pxa_timer_nodt_init(IRQ_OST0, io_p2v(0x40a00000),
                            get_clock_tick_rate());
 }
index 7a9fa1aa4e41838d05ae1a72354572e12fb8581c..0b1dbb54871aaa9f465bd6dcd0095f0fc8f8ba08 100644 (file)
@@ -26,17 +26,20 @@ extern void pxa_timer_init(void);
 #define ARRAY_AND_SIZE(x)      (x), ARRAY_SIZE(x)
 
 #define pxa25x_handle_irq icip_handle_irq
+extern int __init pxa25x_clocks_init(void);
 extern void __init pxa25x_init_irq(void);
 extern void __init pxa25x_map_io(void);
 extern void __init pxa26x_init_irq(void);
 
 #define pxa27x_handle_irq ichp_handle_irq
+extern int __init pxa27x_clocks_init(void);
 extern void __init pxa27x_dt_init_irq(void);
 extern unsigned        pxa27x_get_clk_frequency_khz(int);
 extern void __init pxa27x_init_irq(void);
 extern void __init pxa27x_map_io(void);
 
 #define pxa3xx_handle_irq ichp_handle_irq
+extern int __init pxa3xx_clocks_init(void);
 extern void __init pxa3xx_dt_init_irq(void);
 extern void __init pxa3xx_init_irq(void);
 extern void __init pxa3xx_map_io(void);
index 89a7c06570d3adf248a00bf07c3c3aff631d23cf..98608c5575cb7cdc31d83386334db2ff7b523a25 100644 (file)
@@ -138,7 +138,7 @@ static int pxa_irq_map(struct irq_domain *h, unsigned int virq,
        return 0;
 }
 
-static struct irq_domain_ops pxa_irq_ops = {
+static const struct irq_domain_ops pxa_irq_ops = {
        .map    = pxa_irq_map,
        .xlate  = irq_domain_xlate_onecell,
 };
index 4ac9ab80d24bdf147c23a4f31ab85d76cb4a82c5..2d4bf1fb73120fb561416602e26fd9853fd742ad 100644 (file)
@@ -57,7 +57,6 @@
 #include <mach/smemc.h>
 
 #include "generic.h"
-#include "clock.h"
 #include "devices.h"
 
 static unsigned long lubbock_pin_config[] __initdata = {
@@ -102,6 +101,9 @@ static unsigned long lubbock_pin_config[] __initdata = {
        GPIO6_MMC_CLK,
        GPIO8_MMC_CS0,
 
+       /* SA1111 chip */
+       GPIO11_3_6MHz,
+
        /* wakeup */
        GPIO1_GPIO | WAKEUP_ON_EDGE_RISE,
 };
index 66e4a2b6316ea650d02aace1fcc4dfae7e5a8909..23a90c62ec11bf3b82ed77693351a669a6dc697a 100644 (file)
 
 #include "generic.h"
 #include "devices.h"
-#include "clock.h"
 
 /*
  * Various clock factors driven by the CCCR register.
  */
 
-/* Crystal Frequency to Memory Frequency Multiplier (L) */
-static unsigned char L_clk_mult[32] = { 0, 27, 32, 36, 40, 45, 0, };
-
-/* Memory Frequency to Run Mode Frequency Multiplier (M) */
-static unsigned char M_clk_mult[4] = { 0, 1, 2, 4 };
-
-/* Run Mode Frequency to Turbo Mode Frequency Multiplier (N) */
-/* Note: we store the value N * 2 here. */
-static unsigned char N2_clk_mult[8] = { 0, 0, 2, 3, 4, 0, 6, 0 };
-
-/* Crystal clock */
-#define BASE_CLK       3686400
-
-/*
- * Get the clock frequency as reflected by CCCR and the turbo flag.
- * We assume these values have been applied via a fcs.
- * If info is not 0 we also display the current settings.
- */
-unsigned int pxa25x_get_clk_frequency_khz(int info)
-{
-       unsigned long cccr, turbo;
-       unsigned int l, L, m, M, n2, N;
-
-       cccr = CCCR;
-       asm( "mrc\tp14, 0, %0, c6, c0, 0" : "=r" (turbo) );
-
-       l  =  L_clk_mult[(cccr >> 0) & 0x1f];
-       m  =  M_clk_mult[(cccr >> 5) & 0x03];
-       n2 = N2_clk_mult[(cccr >> 7) & 0x07];
-
-       L = l * BASE_CLK;
-       M = m * L;
-       N = n2 * M / 2;
-
-       if(info)
-       {
-               L += 5000;
-               printk( KERN_INFO "Memory clock: %d.%02dMHz (*%d)\n",
-                       L / 1000000, (L % 1000000) / 10000, l );
-               M += 5000;
-               printk( KERN_INFO "Run Mode clock: %d.%02dMHz (*%d)\n",
-                       M / 1000000, (M % 1000000) / 10000, m );
-               N += 5000;
-               printk( KERN_INFO "Turbo Mode clock: %d.%02dMHz (*%d.%d, %sactive)\n",
-                       N / 1000000, (N % 1000000) / 10000, n2 / 2, (n2 % 2) * 5,
-                       (turbo & 1) ? "" : "in" );
-       }
-
-       return (turbo & 1) ? (N/1000) : (M/1000);
-}
-
-static unsigned long clk_pxa25x_mem_getrate(struct clk *clk)
-{
-       return L_clk_mult[(CCCR >> 0) & 0x1f] * BASE_CLK;
-}
-
-static const struct clkops clk_pxa25x_mem_ops = {
-       .enable         = clk_dummy_enable,
-       .disable        = clk_dummy_disable,
-       .getrate        = clk_pxa25x_mem_getrate,
-};
-
-static const struct clkops clk_pxa25x_lcd_ops = {
-       .enable         = clk_pxa2xx_cken_enable,
-       .disable        = clk_pxa2xx_cken_disable,
-       .getrate        = clk_pxa25x_mem_getrate,
-};
-
-static unsigned long gpio12_config_32k[] = {
-       GPIO12_32KHz,
-};
-
-static unsigned long gpio12_config_gpio[] = {
-       GPIO12_GPIO,
-};
-
-static void clk_gpio12_enable(struct clk *clk)
-{
-       pxa2xx_mfp_config(gpio12_config_32k, 1);
-}
-
-static void clk_gpio12_disable(struct clk *clk)
-{
-       pxa2xx_mfp_config(gpio12_config_gpio, 1);
-}
-
-static const struct clkops clk_pxa25x_gpio12_ops = {
-       .enable         = clk_gpio12_enable,
-       .disable        = clk_gpio12_disable,
-};
-
-static unsigned long gpio11_config_3m6[] = {
-       GPIO11_3_6MHz,
-};
-
-static unsigned long gpio11_config_gpio[] = {
-       GPIO11_GPIO,
-};
-
-static void clk_gpio11_enable(struct clk *clk)
-{
-       pxa2xx_mfp_config(gpio11_config_3m6, 1);
-}
-
-static void clk_gpio11_disable(struct clk *clk)
-{
-       pxa2xx_mfp_config(gpio11_config_gpio, 1);
-}
-
-static const struct clkops clk_pxa25x_gpio11_ops = {
-       .enable         = clk_gpio11_enable,
-       .disable        = clk_gpio11_disable,
-};
-
-/*
- * 3.6864MHz -> OST, GPIO, SSP, PWM, PLLs (95.842MHz, 147.456MHz)
- * 95.842MHz -> MMC 19.169MHz, I2C 31.949MHz, FICP 47.923MHz, USB 47.923MHz
- * 147.456MHz -> UART 14.7456MHz, AC97 12.288MHz, I2S 5.672MHz (allegedly)
- */
-
-/*
- * PXA 2xx clock declarations.
- */
-static DEFINE_PXA2_CKEN(pxa25x_hwuart, HWUART, 14745600, 1);
-static DEFINE_PXA2_CKEN(pxa25x_ffuart, FFUART, 14745600, 1);
-static DEFINE_PXA2_CKEN(pxa25x_btuart, BTUART, 14745600, 1);
-static DEFINE_PXA2_CKEN(pxa25x_stuart, STUART, 14745600, 1);
-static DEFINE_PXA2_CKEN(pxa25x_usb, USB, 47923000, 5);
-static DEFINE_PXA2_CKEN(pxa25x_mmc, MMC, 19169000, 0);
-static DEFINE_PXA2_CKEN(pxa25x_i2c, I2C, 31949000, 0);
-static DEFINE_PXA2_CKEN(pxa25x_ssp, SSP, 3686400, 0);
-static DEFINE_PXA2_CKEN(pxa25x_nssp, NSSP, 3686400, 0);
-static DEFINE_PXA2_CKEN(pxa25x_assp, ASSP, 3686400, 0);
-static DEFINE_PXA2_CKEN(pxa25x_pwm0, PWM0, 3686400, 0);
-static DEFINE_PXA2_CKEN(pxa25x_pwm1, PWM1, 3686400, 0);
-static DEFINE_PXA2_CKEN(pxa25x_ac97, AC97, 24576000, 0);
-static DEFINE_PXA2_CKEN(pxa25x_i2s, I2S, 14745600, 0);
-static DEFINE_PXA2_CKEN(pxa25x_ficp, FICP, 47923000, 0);
-
-static DEFINE_CK(pxa25x_lcd, LCD, &clk_pxa25x_lcd_ops);
-static DEFINE_CLK(pxa25x_gpio11, &clk_pxa25x_gpio11_ops, 3686400, 0);
-static DEFINE_CLK(pxa25x_gpio12, &clk_pxa25x_gpio12_ops, 32768, 0);
-static DEFINE_CLK(pxa25x_mem, &clk_pxa25x_mem_ops, 0, 0);
-
-static struct clk_lookup pxa25x_clkregs[] = {
-       INIT_CLKREG(&clk_pxa25x_lcd, "pxa2xx-fb", NULL),
-       INIT_CLKREG(&clk_pxa25x_ffuart, "pxa2xx-uart.0", NULL),
-       INIT_CLKREG(&clk_pxa25x_btuart, "pxa2xx-uart.1", NULL),
-       INIT_CLKREG(&clk_pxa25x_stuart, "pxa2xx-uart.2", NULL),
-       INIT_CLKREG(&clk_pxa25x_usb, "pxa25x-udc", NULL),
-       INIT_CLKREG(&clk_pxa25x_mmc, "pxa2xx-mci.0", NULL),
-       INIT_CLKREG(&clk_pxa25x_i2c, "pxa2xx-i2c.0", NULL),
-       INIT_CLKREG(&clk_pxa25x_ssp, "pxa25x-ssp.0", NULL),
-       INIT_CLKREG(&clk_pxa25x_nssp, "pxa25x-nssp.1", NULL),
-       INIT_CLKREG(&clk_pxa25x_assp, "pxa25x-nssp.2", NULL),
-       INIT_CLKREG(&clk_pxa25x_pwm0, "pxa25x-pwm.0", NULL),
-       INIT_CLKREG(&clk_pxa25x_pwm1, "pxa25x-pwm.1", NULL),
-       INIT_CLKREG(&clk_pxa25x_i2s, "pxa2xx-i2s", NULL),
-       INIT_CLKREG(&clk_pxa25x_stuart, "pxa2xx-ir", "UARTCLK"),
-       INIT_CLKREG(&clk_pxa25x_ficp, "pxa2xx-ir", "FICPCLK"),
-       INIT_CLKREG(&clk_pxa25x_ac97, NULL, "AC97CLK"),
-       INIT_CLKREG(&clk_pxa25x_gpio11, NULL, "GPIO11_CLK"),
-       INIT_CLKREG(&clk_pxa25x_gpio12, NULL, "GPIO12_CLK"),
-       INIT_CLKREG(&clk_pxa25x_mem, "pxa2xx-pcmcia", NULL),
-#ifdef CONFIG_CPU_PXA26x
-       INIT_CLKREG(&clk_dummy, "pxa26x-gpio", NULL),
-#else
-       INIT_CLKREG(&clk_dummy, "pxa25x-gpio", NULL),
-#endif
-       INIT_CLKREG(&clk_dummy, "sa1100-rtc", NULL),
-};
-
-static struct clk_lookup pxa25x_hwuart_clkreg =
-       INIT_CLKREG(&clk_pxa25x_hwuart, "pxa2xx-uart.3", NULL);
-
 #ifdef CONFIG_PM
 
 #define SAVE(x)                sleep_save[SLEEP_SAVE_##x] = x
@@ -374,8 +198,6 @@ static int __init pxa25x_init(void)
 
                reset_status = RCSR;
 
-               clkdev_add_table(pxa25x_clkregs, ARRAY_SIZE(pxa25x_clkregs));
-
                if ((ret = pxa_init_dma(IRQ_DMA, 16)))
                        return ret;
 
@@ -383,7 +205,6 @@ static int __init pxa25x_init(void)
 
                register_syscore_ops(&pxa_irq_syscore_ops);
                register_syscore_ops(&pxa2xx_mfp_syscore_ops);
-               register_syscore_ops(&pxa2xx_clock_syscore_ops);
 
                pxa_register_device(&pxa25x_device_gpio, &pxa25x_gpio_info);
                ret = platform_add_devices(pxa25x_devices,
@@ -392,10 +213,6 @@ static int __init pxa25x_init(void)
                        return ret;
        }
 
-       /* Only add HWUART for PXA255/26x; PXA210/250 do not have it. */
-       if (cpu_is_pxa255())
-               clkdev_add(&pxa25x_hwuart_clkreg);
-
        return ret;
 }
 
index af423a48c2e3bb13bdb6295fd03ccc2332f61eb0..b5abdeb5bb2d17d6e63e4bc844047e0ea1928b05 100644 (file)
@@ -37,7 +37,8 @@
 
 #include "generic.h"
 #include "devices.h"
-#include "clock.h"
+#include <linux/clk-provider.h>
+#include <linux/clkdev.h>
 
 void pxa27x_clear_otgph(void)
 {
@@ -73,174 +74,6 @@ void pxa27x_configure_ac97reset(int reset_gpio, bool to_gpio)
 }
 EXPORT_SYMBOL_GPL(pxa27x_configure_ac97reset);
 
-/* Crystal clock: 13MHz */
-#define BASE_CLK       13000000
-
-/*
- * Get the clock frequency as reflected by CCSR and the turbo flag.
- * We assume these values have been applied via a fcs.
- * If info is not 0 we also display the current settings.
- */
-unsigned int pxa27x_get_clk_frequency_khz(int info)
-{
-       unsigned long ccsr, clkcfg;
-       unsigned int l, L, m, M, n2, N, S;
-               int cccr_a, t, ht, b;
-
-       ccsr = CCSR;
-       cccr_a = CCCR & (1 << 25);
-
-       /* Read clkcfg register: it has turbo, b, half-turbo (and f) */
-       asm( "mrc\tp14, 0, %0, c6, c0, 0" : "=r" (clkcfg) );
-       t  = clkcfg & (1 << 0);
-       ht = clkcfg & (1 << 2);
-       b  = clkcfg & (1 << 3);
-
-       l  = ccsr & 0x1f;
-       n2 = (ccsr>>7) & 0xf;
-       m  = (l <= 10) ? 1 : (l <= 20) ? 2 : 4;
-
-       L  = l * BASE_CLK;
-       N  = (L * n2) / 2;
-       M  = (!cccr_a) ? (L/m) : ((b) ? L : (L/2));
-       S  = (b) ? L : (L/2);
-
-       if (info) {
-               printk( KERN_INFO "Run Mode clock: %d.%02dMHz (*%d)\n",
-                       L / 1000000, (L % 1000000) / 10000, l );
-               printk( KERN_INFO "Turbo Mode clock: %d.%02dMHz (*%d.%d, %sactive)\n",
-                       N / 1000000, (N % 1000000)/10000, n2 / 2, (n2 % 2)*5,
-                       (t) ? "" : "in" );
-               printk( KERN_INFO "Memory clock: %d.%02dMHz (/%d)\n",
-                       M / 1000000, (M % 1000000) / 10000, m );
-               printk( KERN_INFO "System bus clock: %d.%02dMHz \n",
-                       S / 1000000, (S % 1000000) / 10000 );
-       }
-
-       return (t) ? (N/1000) : (L/1000);
-}
-
-/*
- * Return the current mem clock frequency as reflected by CCCR[A], B, and L
- */
-static unsigned long clk_pxa27x_mem_getrate(struct clk *clk)
-{
-       unsigned long ccsr, clkcfg;
-       unsigned int l, L, m, M;
-               int cccr_a, b;
-
-       ccsr = CCSR;
-       cccr_a = CCCR & (1 << 25);
-
-       /* Read clkcfg register: it has turbo, b, half-turbo (and f) */
-       asm( "mrc\tp14, 0, %0, c6, c0, 0" : "=r" (clkcfg) );
-       b = clkcfg & (1 << 3);
-
-       l = ccsr & 0x1f;
-       m = (l <= 10) ? 1 : (l <= 20) ? 2 : 4;
-
-       L = l * BASE_CLK;
-       M = (!cccr_a) ? (L/m) : ((b) ? L : (L/2));
-
-       return M;
-}
-
-static const struct clkops clk_pxa27x_mem_ops = {
-       .enable         = clk_dummy_enable,
-       .disable        = clk_dummy_disable,
-       .getrate        = clk_pxa27x_mem_getrate,
-};
-
-/*
- * Return the current LCD clock frequency in units of 10kHz as
- */
-static unsigned int pxa27x_get_lcdclk_frequency_10khz(void)
-{
-       unsigned long ccsr;
-       unsigned int l, L, k, K;
-
-       ccsr = CCSR;
-
-       l = ccsr & 0x1f;
-       k = (l <= 7) ? 1 : (l <= 16) ? 2 : 4;
-
-       L = l * BASE_CLK;
-       K = L / k;
-
-       return (K / 10000);
-}
-
-static unsigned long clk_pxa27x_lcd_getrate(struct clk *clk)
-{
-       return pxa27x_get_lcdclk_frequency_10khz() * 10000;
-}
-
-static const struct clkops clk_pxa27x_lcd_ops = {
-       .enable         = clk_pxa2xx_cken_enable,
-       .disable        = clk_pxa2xx_cken_disable,
-       .getrate        = clk_pxa27x_lcd_getrate,
-};
-
-static DEFINE_PXA2_CKEN(pxa27x_ffuart, FFUART, 14857000, 1);
-static DEFINE_PXA2_CKEN(pxa27x_btuart, BTUART, 14857000, 1);
-static DEFINE_PXA2_CKEN(pxa27x_stuart, STUART, 14857000, 1);
-static DEFINE_PXA2_CKEN(pxa27x_i2s, I2S, 14682000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_i2c, I2C, 32842000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_usb, USB, 48000000, 5);
-static DEFINE_PXA2_CKEN(pxa27x_mmc, MMC, 19500000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_ficp, FICP, 48000000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_usbhost, USBHOST, 48000000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_pwri2c, PWRI2C, 13000000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_keypad, KEYPAD, 32768, 0);
-static DEFINE_PXA2_CKEN(pxa27x_ssp1, SSP1, 13000000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_ssp2, SSP2, 13000000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_ssp3, SSP3, 13000000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_pwm0, PWM0, 13000000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_pwm1, PWM1, 13000000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_ac97, AC97, 24576000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_ac97conf, AC97CONF, 24576000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_msl, MSL, 48000000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_usim, USIM, 48000000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_memstk, MEMSTK, 19500000, 0);
-static DEFINE_PXA2_CKEN(pxa27x_im, IM, 0, 0);
-static DEFINE_PXA2_CKEN(pxa27x_memc, MEMC, 0, 0);
-
-static DEFINE_CK(pxa27x_lcd, LCD, &clk_pxa27x_lcd_ops);
-static DEFINE_CK(pxa27x_camera, CAMERA, &clk_pxa27x_lcd_ops);
-static DEFINE_CLK(pxa27x_mem, &clk_pxa27x_mem_ops, 0, 0);
-
-static struct clk_lookup pxa27x_clkregs[] = {
-       INIT_CLKREG(&clk_pxa27x_lcd, "pxa2xx-fb", NULL),
-       INIT_CLKREG(&clk_pxa27x_camera, "pxa27x-camera.0", NULL),
-       INIT_CLKREG(&clk_pxa27x_ffuart, "pxa2xx-uart.0", NULL),
-       INIT_CLKREG(&clk_pxa27x_btuart, "pxa2xx-uart.1", NULL),
-       INIT_CLKREG(&clk_pxa27x_stuart, "pxa2xx-uart.2", NULL),
-       INIT_CLKREG(&clk_pxa27x_i2s, "pxa2xx-i2s", NULL),
-       INIT_CLKREG(&clk_pxa27x_i2c, "pxa2xx-i2c.0", NULL),
-       INIT_CLKREG(&clk_pxa27x_usb, "pxa27x-udc", NULL),
-       INIT_CLKREG(&clk_pxa27x_mmc, "pxa2xx-mci.0", NULL),
-       INIT_CLKREG(&clk_pxa27x_stuart, "pxa2xx-ir", "UARTCLK"),
-       INIT_CLKREG(&clk_pxa27x_ficp, "pxa2xx-ir", "FICPCLK"),
-       INIT_CLKREG(&clk_pxa27x_usbhost, "pxa27x-ohci", NULL),
-       INIT_CLKREG(&clk_pxa27x_pwri2c, "pxa2xx-i2c.1", NULL),
-       INIT_CLKREG(&clk_pxa27x_keypad, "pxa27x-keypad", NULL),
-       INIT_CLKREG(&clk_pxa27x_ssp1, "pxa27x-ssp.0", NULL),
-       INIT_CLKREG(&clk_pxa27x_ssp2, "pxa27x-ssp.1", NULL),
-       INIT_CLKREG(&clk_pxa27x_ssp3, "pxa27x-ssp.2", NULL),
-       INIT_CLKREG(&clk_pxa27x_pwm0, "pxa27x-pwm.0", NULL),
-       INIT_CLKREG(&clk_pxa27x_pwm1, "pxa27x-pwm.1", NULL),
-       INIT_CLKREG(&clk_pxa27x_ac97, NULL, "AC97CLK"),
-       INIT_CLKREG(&clk_pxa27x_ac97conf, NULL, "AC97CONFCLK"),
-       INIT_CLKREG(&clk_pxa27x_msl, NULL, "MSLCLK"),
-       INIT_CLKREG(&clk_pxa27x_usim, NULL, "USIMCLK"),
-       INIT_CLKREG(&clk_pxa27x_memstk, NULL, "MSTKCLK"),
-       INIT_CLKREG(&clk_pxa27x_im, NULL, "IMCLK"),
-       INIT_CLKREG(&clk_pxa27x_memc, NULL, "MEMCLK"),
-       INIT_CLKREG(&clk_pxa27x_mem, "pxa2xx-pcmcia", NULL),
-       INIT_CLKREG(&clk_dummy, "pxa27x-gpio", NULL),
-       INIT_CLKREG(&clk_dummy, "sa1100-rtc", NULL),
-};
-
 #ifdef CONFIG_PM
 
 #define SAVE(x)                sleep_save[SLEEP_SAVE_##x] = x
@@ -466,8 +299,6 @@ static int __init pxa27x_init(void)
 
                reset_status = RCSR;
 
-               clkdev_add_table(pxa27x_clkregs, ARRAY_SIZE(pxa27x_clkregs));
-
                if ((ret = pxa_init_dma(IRQ_DMA, 32)))
                        return ret;
 
@@ -475,10 +306,13 @@ static int __init pxa27x_init(void)
 
                register_syscore_ops(&pxa_irq_syscore_ops);
                register_syscore_ops(&pxa2xx_mfp_syscore_ops);
-               register_syscore_ops(&pxa2xx_clock_syscore_ops);
 
-               pxa_register_device(&pxa27x_device_gpio, &pxa27x_gpio_info);
-               ret = platform_add_devices(devices, ARRAY_SIZE(devices));
+               if (!of_have_populated_dt()) {
+                       pxa_register_device(&pxa27x_device_gpio,
+                                           &pxa27x_gpio_info);
+                       ret = platform_add_devices(devices,
+                                                  ARRAY_SIZE(devices));
+               }
        }
 
        return ret;
index 17cbc0c7bdb8dd6572ff9da306c359cfca2b5e20..28c5b5686638fdfa26a8f166f21e88b28693eabf 100644 (file)
@@ -22,7 +22,6 @@
 
 #include "generic.h"
 #include "devices.h"
-#include "clock.h"
 
 static struct mfp_addr_map pxa300_mfp_addr_map[] __initdata = {
 
@@ -84,32 +83,15 @@ static struct mfp_addr_map pxa310_mfp_addr_map[] __initdata = {
        MFP_ADDR_END,
 };
 
-static DEFINE_PXA3_CKEN(common_nand, NAND, 156000000, 0);
-static DEFINE_PXA3_CKEN(gcu, PXA300_GCU, 0, 0);
-
-static struct clk_lookup common_clkregs[] = {
-       INIT_CLKREG(&clk_common_nand, "pxa3xx-nand", NULL),
-       INIT_CLKREG(&clk_gcu, "pxa3xx-gcu", NULL),
-};
-
-static DEFINE_PXA3_CKEN(pxa310_mmc3, MMC3, 19500000, 0);
-
-static struct clk_lookup pxa310_clkregs[] = {
-       INIT_CLKREG(&clk_pxa310_mmc3, "pxa2xx-mci.2", NULL),
-};
-
 static int __init pxa300_init(void)
 {
        if (cpu_is_pxa300() || cpu_is_pxa310()) {
                mfp_init_base(io_p2v(MFPR_BASE));
                mfp_init_addr(pxa300_mfp_addr_map);
-               clkdev_add_table(ARRAY_AND_SIZE(common_clkregs));
        }
 
-       if (cpu_is_pxa310()) {
+       if (cpu_is_pxa310())
                mfp_init_addr(pxa310_mfp_addr_map);
-               clkdev_add_table(ARRAY_AND_SIZE(pxa310_clkregs));
-       }
 
        return 0;
 }
index 6dc99d4f2dc630065398d20a08817df5773e6cc8..2f55bb4b9087f3e683c15c8b34d6ceab2a1537d0 100644 (file)
@@ -22,7 +22,6 @@
 
 #include "generic.h"
 #include "devices.h"
-#include "clock.h"
 
 static struct mfp_addr_map pxa320_mfp_addr_map[] __initdata = {
 
@@ -78,20 +77,11 @@ static struct mfp_addr_map pxa320_mfp_addr_map[] __initdata = {
        MFP_ADDR_END,
 };
 
-static DEFINE_PXA3_CKEN(pxa320_nand, NAND, 104000000, 0);
-static DEFINE_PXA3_CKEN(gcu, PXA320_GCU, 0, 0);
-
-static struct clk_lookup pxa320_clkregs[] = {
-       INIT_CLKREG(&clk_pxa320_nand, "pxa3xx-nand", NULL),
-       INIT_CLKREG(&clk_gcu, "pxa3xx-gcu", NULL),
-};
-
 static int __init pxa320_init(void)
 {
        if (cpu_is_pxa320()) {
                mfp_init_base(io_p2v(MFPR_BASE));
                mfp_init_addr(pxa320_mfp_addr_map);
-               clkdev_add_table(ARRAY_AND_SIZE(pxa320_clkregs));
        }
 
        return 0;
index edcbd9c0bcb2edf1f6ace9805c4b3a04f7671601..bd4cbef15ccf2147a7cce6aa1d51f185cfd57f8f 100644 (file)
 
 #include "generic.h"
 #include "devices.h"
-#include "clock.h"
 
 #define PECR_IE(n)     ((1 << ((n) * 2)) << 28)
 #define PECR_IS(n)     ((1 << ((n) * 2)) << 29)
 
 extern void __init pxa_dt_irq_init(int (*fn)(struct irq_data *, unsigned int));
-
-static DEFINE_PXA3_CKEN(pxa3xx_ffuart, FFUART, 14857000, 1);
-static DEFINE_PXA3_CKEN(pxa3xx_btuart, BTUART, 14857000, 1);
-static DEFINE_PXA3_CKEN(pxa3xx_stuart, STUART, 14857000, 1);
-static DEFINE_PXA3_CKEN(pxa3xx_i2c, I2C, 32842000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_udc, UDC, 48000000, 5);
-static DEFINE_PXA3_CKEN(pxa3xx_usbh, USBH, 48000000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_u2d, USB2, 48000000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_keypad, KEYPAD, 32768, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_ssp1, SSP1, 13000000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_ssp2, SSP2, 13000000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_ssp3, SSP3, 13000000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_ssp4, SSP4, 13000000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_pwm0, PWM0, 13000000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_pwm1, PWM1, 13000000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_mmc1, MMC1, 19500000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_mmc2, MMC2, 19500000, 0);
-static DEFINE_PXA3_CKEN(pxa3xx_gpio, GPIO, 13000000, 0);
-
-static DEFINE_CK(pxa3xx_lcd, LCD, &clk_pxa3xx_hsio_ops);
-static DEFINE_CK(pxa3xx_smemc, SMC, &clk_pxa3xx_smemc_ops);
-static DEFINE_CK(pxa3xx_camera, CAMERA, &clk_pxa3xx_hsio_ops);
-static DEFINE_CK(pxa3xx_ac97, AC97, &clk_pxa3xx_ac97_ops);
-static DEFINE_CLK(pxa3xx_pout, &clk_pxa3xx_pout_ops, 13000000, 70);
-
-static struct clk_lookup pxa3xx_clkregs[] = {
-       INIT_CLKREG(&clk_pxa3xx_pout, NULL, "CLK_POUT"),
-       /* Power I2C clock is always on */
-       INIT_CLKREG(&clk_dummy, "pxa3xx-pwri2c.1", NULL),
-       INIT_CLKREG(&clk_pxa3xx_lcd, "pxa2xx-fb", NULL),
-       INIT_CLKREG(&clk_pxa3xx_camera, NULL, "CAMCLK"),
-       INIT_CLKREG(&clk_pxa3xx_ac97, NULL, "AC97CLK"),
-       INIT_CLKREG(&clk_pxa3xx_ffuart, "pxa2xx-uart.0", NULL),
-       INIT_CLKREG(&clk_pxa3xx_btuart, "pxa2xx-uart.1", NULL),
-       INIT_CLKREG(&clk_pxa3xx_stuart, "pxa2xx-uart.2", NULL),
-       INIT_CLKREG(&clk_pxa3xx_stuart, "pxa2xx-ir", "UARTCLK"),
-       INIT_CLKREG(&clk_pxa3xx_i2c, "pxa2xx-i2c.0", NULL),
-       INIT_CLKREG(&clk_pxa3xx_udc, "pxa27x-udc", NULL),
-       INIT_CLKREG(&clk_pxa3xx_usbh, "pxa27x-ohci", NULL),
-       INIT_CLKREG(&clk_pxa3xx_u2d, "pxa3xx-u2d", NULL),
-       INIT_CLKREG(&clk_pxa3xx_keypad, "pxa27x-keypad", NULL),
-       INIT_CLKREG(&clk_pxa3xx_ssp1, "pxa3xx-ssp.0", NULL),
-       INIT_CLKREG(&clk_pxa3xx_ssp2, "pxa3xx-ssp.1", NULL),
-       INIT_CLKREG(&clk_pxa3xx_ssp3, "pxa3xx-ssp.2", NULL),
-       INIT_CLKREG(&clk_pxa3xx_ssp4, "pxa3xx-ssp.3", NULL),
-       INIT_CLKREG(&clk_pxa3xx_pwm0, "pxa27x-pwm.0", NULL),
-       INIT_CLKREG(&clk_pxa3xx_pwm1, "pxa27x-pwm.1", NULL),
-       INIT_CLKREG(&clk_pxa3xx_mmc1, "pxa2xx-mci.0", NULL),
-       INIT_CLKREG(&clk_pxa3xx_mmc2, "pxa2xx-mci.1", NULL),
-       INIT_CLKREG(&clk_pxa3xx_smemc, "pxa2xx-pcmcia", NULL),
-       INIT_CLKREG(&clk_pxa3xx_gpio, "pxa3xx-gpio", NULL),
-       INIT_CLKREG(&clk_pxa3xx_gpio, "pxa93x-gpio", NULL),
-       INIT_CLKREG(&clk_dummy, "sa1100-rtc", NULL),
-};
-
 #ifdef CONFIG_PM
 
 #define ISRAM_START    0x5c000000
@@ -476,8 +420,6 @@ static int __init pxa3xx_init(void)
                 */
                ASCR &= ~(ASCR_RDH | ASCR_D1S | ASCR_D2S | ASCR_D3S);
 
-               clkdev_add_table(pxa3xx_clkregs, ARRAY_SIZE(pxa3xx_clkregs));
-
                if ((ret = pxa_init_dma(IRQ_DMA, 32)))
                        return ret;
 
@@ -485,7 +427,6 @@ static int __init pxa3xx_init(void)
 
                register_syscore_ops(&pxa_irq_syscore_ops);
                register_syscore_ops(&pxa3xx_mfp_syscore_ops);
-               register_syscore_ops(&pxa3xx_clock_syscore_ops);
 
                if (of_have_populated_dt())
                        return 0;
index 6dc4f025e6743342524cd49f2bef74e9955899e4..88f70c37ad0dddef1fa85e9dd804c3c2fda41459 100644 (file)
@@ -56,7 +56,6 @@
 
 #include "generic.h"
 #include "devices.h"
-#include "clock.h"
 
 /* common GPIO definitions */
 
index 7780d1faa06f563057e68e749e7ccc7a9a8006d6..93bf4ef44d2c831f860489f3350fcb0c7c0a3c66 100644 (file)
@@ -58,7 +58,6 @@
 #include <asm/mach/sharpsl_param.h>
 
 #include "generic.h"
-#include "clock.h"
 #include "devices.h"
 
 static unsigned long tosa_pin_config[] = {
index 0fb484221c90e0eb9c0a5aeefd5df7beac098678..45006479d4617bf3b862eb98147323b216573dfd 100644 (file)
@@ -139,7 +139,7 @@ config MACH_ARMADILLO800EVA
        select ARCH_REQUIRE_GPIOLIB
        select REGULATOR_FIXED_VOLTAGE if REGULATOR
        select SMSC_PHY if SH_ETH
-       select SND_SOC_WM8978 if SND_SIMPLE_CARD
+       select SND_SOC_WM8978 if SND_SIMPLE_CARD && I2C
        select USE_OF
 
 config MACH_BOCKW
@@ -148,7 +148,7 @@ config MACH_BOCKW
        select ARCH_REQUIRE_GPIOLIB
        select REGULATOR_FIXED_VOLTAGE if REGULATOR
        select SND_SOC_AK4554 if SND_SIMPLE_CARD
-       select SND_SOC_AK4642 if SND_SIMPLE_CARD
+       select SND_SOC_AK4642 if SND_SIMPLE_CARD && I2C
        select USE_OF
 
 config MACH_BOCKW_REFERENCE
index b5f8d75d51a0568d603c293df64d403711b77447..90efdeb56be50450dd978e47bbcb9ed5854384d8 100644 (file)
@@ -1,5 +1,6 @@
-config ARCH_SOCFPGA
+menuconfig ARCH_SOCFPGA
        bool "Altera SOCFPGA family" if ARCH_MULTI_V7
+       select ARCH_SUPPORTS_BIG_ENDIAN
        select ARM_AMBA
        select ARM_GIC
        select CACHE_L2X0
@@ -8,3 +9,11 @@ config ARCH_SOCFPGA
        select HAVE_ARM_SCU
        select HAVE_ARM_TWD if SMP
        select MFD_SYSCON
+
+if ARCH_SOCFPGA
+config SOCFPGA_SUSPEND
+       bool "Suspend to RAM on SOCFPGA"
+       help
+         Select this if you want to enable Suspend-to-RAM on SOCFPGA
+         platforms.
+endif
index 6dd7a93a90fea07c472c8cbcbd6f0a0ec5a4d779..b8f9e238e4abc8974a0337365c5e2270599f8077 100644 (file)
@@ -4,3 +4,4 @@
 
 obj-y                                  := socfpga.o
 obj-$(CONFIG_SMP)      += headsmp.o platsmp.o
+obj-$(CONFIG_SOCFPGA_SUSPEND)  += pm.o self-refresh.o
index 767c09e954a0f905f5bb2e791273f1bcc96f370f..7259c37327025bb60ff2e81654a2b338ab1db37d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  * Copyright 2012 Pavel Machek <pavel@denx.de>
- * Copyright (C) 2012 Altera Corporation
+ * Copyright (C) 2012-2015 Altera Corporation
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
 #define SOCFPGA_RSTMGR_MODPERRST       0x14
 #define SOCFPGA_RSTMGR_BRGMODRST       0x1c
 
+#define SOCFPGA_A10_RSTMGR_MODMPURST   0x20
+
 /* System Manager bits */
 #define RSTMGR_CTRL_SWCOLDRSTREQ       0x1     /* Cold Reset */
 #define RSTMGR_CTRL_SWWARMRSTREQ       0x2     /* Warm Reset */
 
 #define RSTMGR_MPUMODRST_CPU1          0x2     /* CPU1 Reset */
 
-extern void __iomem *socfpga_scu_base_addr;
-
 extern void socfpga_init_clocks(void);
 extern void socfpga_sysmgr_init(void);
 
 extern void __iomem *sys_manager_base_addr;
 extern void __iomem *rst_manager_base_addr;
+extern void __iomem *sdr_ctl_base_addr;
+
+u32 socfpga_sdram_self_refresh(u32 sdr_base);
+extern unsigned int socfpga_sdram_self_refresh_sz;
 
-extern struct smp_operations socfpga_smp_ops;
 extern char secondary_trampoline, secondary_trampoline_end;
 
 extern unsigned long socfpga_cpu1start_addr;
index 5bb0164271076eb4b4d0393d0af271493464df88..5d94b7a2fb108dc1bc1c5fcdd4edfa80ab2c0c7f 100644 (file)
@@ -10,6 +10,7 @@
 #include <linux/linkage.h>
 #include <linux/init.h>
 #include <asm/memory.h>
+#include <asm/assembler.h>
 
        .arch   armv7-a
 
@@ -18,12 +19,14 @@ ENTRY(secondary_trampoline)
         * Thus, we can just subtract the PAGE_OFFSET to get the physical
         * address of &cpu1start_addr. This would not work for platforms
         * where the physical memory does not start at 0x0.
-        */
+       */
+ARM_BE8(setend be)
        adr     r0, 1f
        ldmia   r0, {r1, r2}
        sub     r2, r2, #PAGE_OFFSET
        ldr     r3, [r2]
        ldr     r4, [r3]
+ARM_BE8(rev    r4, r4)
        bx      r4
 
        .align
index 79c5336c569ff86aaa7cd7872f2447b766ce365f..c6f1df89f9af7fdf10049805714c4f5045165dc2 100644 (file)
@@ -54,32 +54,43 @@ static int socfpga_boot_secondary(unsigned int cpu, struct task_struct *idle)
        return 0;
 }
 
-/*
- * Initialise the CPU possible map early - this describes the CPUs
- * which may be present or become present in the system.
- */
-static void __init socfpga_smp_init_cpus(void)
+static int socfpga_a10_boot_secondary(unsigned int cpu, struct task_struct *idle)
 {
-       unsigned int i, ncores;
+       int trampoline_size = &secondary_trampoline_end - &secondary_trampoline;
 
-       ncores = scu_get_core_count(socfpga_scu_base_addr);
+       if (socfpga_cpu1start_addr) {
+               writel(RSTMGR_MPUMODRST_CPU1, rst_manager_base_addr +
+                      SOCFPGA_A10_RSTMGR_MODMPURST);
+               memcpy(phys_to_virt(0), &secondary_trampoline, trampoline_size);
 
-       for (i = 0; i < ncores; i++)
-               set_cpu_possible(i, true);
+               writel(virt_to_phys(secondary_startup),
+                      sys_manager_base_addr + (socfpga_cpu1start_addr & 0x00000fff));
 
-       /* sanity check */
-       if (ncores > num_possible_cpus()) {
-               pr_warn("socfpga: no. of cores (%d) greater than configured"
-                       "maximum of %d - clipping\n", ncores, num_possible_cpus());
-               ncores = num_possible_cpus();
+               flush_cache_all();
+               smp_wmb();
+               outer_clean_range(0, trampoline_size);
+
+               /* This will release CPU #1 out of reset. */
+               writel(0, rst_manager_base_addr + SOCFPGA_A10_RSTMGR_MODMPURST);
        }
 
-       for (i = 0; i < ncores; i++)
-               set_cpu_possible(i, true);
+       return 0;
 }
 
 static void __init socfpga_smp_prepare_cpus(unsigned int max_cpus)
 {
+       struct device_node *np;
+       void __iomem *socfpga_scu_base_addr;
+
+       np = of_find_compatible_node(NULL, NULL, "arm,cortex-a9-scu");
+       if (!np) {
+               pr_err("%s: missing scu\n", __func__);
+               return;
+       }
+
+       socfpga_scu_base_addr = of_iomap(np, 0);
+       if (!socfpga_scu_base_addr)
+               return;
        scu_enable(socfpga_scu_base_addr);
 }
 
@@ -95,11 +106,21 @@ static void socfpga_cpu_die(unsigned int cpu)
                cpu_do_idle();
 }
 
-struct smp_operations socfpga_smp_ops __initdata = {
-       .smp_init_cpus          = socfpga_smp_init_cpus,
+static struct smp_operations socfpga_smp_ops __initdata = {
        .smp_prepare_cpus       = socfpga_smp_prepare_cpus,
        .smp_boot_secondary     = socfpga_boot_secondary,
 #ifdef CONFIG_HOTPLUG_CPU
        .cpu_die                = socfpga_cpu_die,
 #endif
 };
+
+static struct smp_operations socfpga_a10_smp_ops __initdata = {
+       .smp_prepare_cpus       = socfpga_smp_prepare_cpus,
+       .smp_boot_secondary     = socfpga_a10_boot_secondary,
+#ifdef CONFIG_HOTPLUG_CPU
+       .cpu_die                = socfpga_cpu_die,
+#endif
+};
+
+CPU_METHOD_OF_DECLARE(socfpga_smp, "altr,socfpga-smp", &socfpga_smp_ops);
+CPU_METHOD_OF_DECLARE(socfpga_a10_smp, "altr,socfpga-a10-smp", &socfpga_a10_smp_ops);
diff --git a/arch/arm/mach-socfpga/pm.c b/arch/arm/mach-socfpga/pm.c
new file mode 100644 (file)
index 0000000..1ed89fc
--- /dev/null
@@ -0,0 +1,149 @@
+/*
+ *  arch/arm/mach-socfpga/pm.c
+ *
+ * Copyright (C) 2014-2015 Altera Corporation. All rights reserved.
+ *
+ * with code from pm-imx6.c
+ * Copyright 2011-2014 Freescale Semiconductor, Inc.
+ * Copyright 2011 Linaro Ltd.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <linux/bitops.h>
+#include <linux/genalloc.h>
+#include <linux/init.h>
+#include <linux/io.h>
+#include <linux/of_platform.h>
+#include <linux/suspend.h>
+#include <asm/suspend.h>
+#include <asm/fncpy.h>
+#include "core.h"
+
+/* Pointer to function copied to ocram */
+static u32 (*socfpga_sdram_self_refresh_in_ocram)(u32 sdr_base);
+
+static int socfpga_setup_ocram_self_refresh(void)
+{
+       struct platform_device *pdev;
+       phys_addr_t ocram_pbase;
+       struct device_node *np;
+       struct gen_pool *ocram_pool;
+       unsigned long ocram_base;
+       void __iomem *suspend_ocram_base;
+       int ret = 0;
+
+       np = of_find_compatible_node(NULL, NULL, "mmio-sram");
+       if (!np) {
+               pr_err("%s: Unable to find mmio-sram in dtb\n", __func__);
+               return -ENODEV;
+       }
+
+       pdev = of_find_device_by_node(np);
+       if (!pdev) {
+               pr_warn("%s: failed to find ocram device!\n", __func__);
+               ret = -ENODEV;
+               goto put_node;
+       }
+
+       ocram_pool = dev_get_gen_pool(&pdev->dev);
+       if (!ocram_pool) {
+               pr_warn("%s: ocram pool unavailable!\n", __func__);
+               ret = -ENODEV;
+               goto put_node;
+       }
+
+       ocram_base = gen_pool_alloc(ocram_pool, socfpga_sdram_self_refresh_sz);
+       if (!ocram_base) {
+               pr_warn("%s: unable to alloc ocram!\n", __func__);
+               ret = -ENOMEM;
+               goto put_node;
+       }
+
+       ocram_pbase = gen_pool_virt_to_phys(ocram_pool, ocram_base);
+
+       suspend_ocram_base = __arm_ioremap_exec(ocram_pbase,
+                                               socfpga_sdram_self_refresh_sz,
+                                               false);
+       if (!suspend_ocram_base) {
+               pr_warn("%s: __arm_ioremap_exec failed!\n", __func__);
+               ret = -ENOMEM;
+               goto put_node;
+       }
+
+       /* Copy the code that puts DDR in self refresh to ocram */
+       socfpga_sdram_self_refresh_in_ocram =
+               (void *)fncpy(suspend_ocram_base,
+                             &socfpga_sdram_self_refresh,
+                             socfpga_sdram_self_refresh_sz);
+
+       WARN(!socfpga_sdram_self_refresh_in_ocram,
+            "could not copy function to ocram");
+       if (!socfpga_sdram_self_refresh_in_ocram)
+               ret = -EFAULT;
+
+put_node:
+       of_node_put(np);
+
+       return ret;
+}
+
+static int socfpga_pm_suspend(unsigned long arg)
+{
+       u32 ret;
+
+       if (!sdr_ctl_base_addr)
+               return -EFAULT;
+
+       ret = socfpga_sdram_self_refresh_in_ocram((u32)sdr_ctl_base_addr);
+
+       pr_debug("%s self-refresh loops request=%d exit=%d\n", __func__,
+                ret & 0xffff, (ret >> 16) & 0xffff);
+
+       return 0;
+}
+
+static int socfpga_pm_enter(suspend_state_t state)
+{
+       switch (state) {
+       case PM_SUSPEND_STANDBY:
+       case PM_SUSPEND_MEM:
+               outer_disable();
+               cpu_suspend(0, socfpga_pm_suspend);
+               outer_resume();
+               break;
+       default:
+               return -EINVAL;
+       }
+       return 0;
+}
+
+static const struct platform_suspend_ops socfpga_pm_ops = {
+       .valid  = suspend_valid_only_mem,
+       .enter  = socfpga_pm_enter,
+};
+
+static int __init socfpga_pm_init(void)
+{
+       int ret;
+
+       ret = socfpga_setup_ocram_self_refresh();
+       if (ret)
+               return ret;
+
+       suspend_set_ops(&socfpga_pm_ops);
+       pr_info("SoCFPGA initialized for DDR self-refresh during suspend.\n");
+
+       return 0;
+}
+arch_initcall(socfpga_pm_init);
diff --git a/arch/arm/mach-socfpga/self-refresh.S b/arch/arm/mach-socfpga/self-refresh.S
new file mode 100644 (file)
index 0000000..f2d7f88
--- /dev/null
@@ -0,0 +1,136 @@
+/*
+ * Copyright (C) 2014-2015 Altera Corporation. All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+#include <linux/linkage.h>
+#include <asm/assembler.h>
+
+#define MAX_LOOP_COUNT         1000
+
+/* Register offset */
+#define SDR_CTRLGRP_LOWPWREQ_ADDR       0x54
+#define SDR_CTRLGRP_LOWPWRACK_ADDR      0x58
+
+/* Bitfield positions */
+#define SELFRSHREQ_POS                  3
+#define SELFRSHREQ_MASK                 0x8
+
+#define SELFRFSHACK_POS                 1
+#define SELFRFSHACK_MASK                0x2
+
+       /*
+        * This code assumes that when the bootloader configured
+        * the sdram controller for the DDR on the board it
+        * configured the following fields depending on the DDR
+        * vendor/configuration:
+        *
+        * sdr.ctrlcfg.lowpwreq.selfrfshmask
+        * sdr.ctrlcfg.lowpwrtiming.clkdisablecycles
+        * sdr.ctrlcfg.dramtiming4.selfrfshexit
+        */
+
+       .arch   armv7-a
+       .text
+       .align 3
+
+       /*
+        * socfpga_sdram_self_refresh
+        *
+        *  r0 : sdr_ctl_base_addr
+        *  r1 : temp storage of return value
+        *  r2 : temp storage of register values
+        *  r3 : loop counter
+        *
+        *  return value: lower 16 bits: loop count going into self refresh
+        *                upper 16 bits: loop count exiting self refresh
+        */
+ENTRY(socfpga_sdram_self_refresh)
+       /* Enable dynamic clock gating in the Power Control Register. */
+       mrc     p15, 0, r2, c15, c0, 0
+       orr     r2, r2, #1
+       mcr     p15, 0, r2, c15, c0, 0
+
+       /* Enable self refresh: set sdr.ctrlgrp.lowpwreq.selfrshreq = 1 */
+       ldr     r2, [r0, #SDR_CTRLGRP_LOWPWREQ_ADDR]
+       orr     r2, r2, #SELFRSHREQ_MASK
+       str     r2, [r0, #SDR_CTRLGRP_LOWPWREQ_ADDR]
+
+       /* Poll until sdr.ctrlgrp.lowpwrack.selfrfshack == 1 or hit max loops */
+       mov     r3, #0
+while_ack_0:
+       ldr     r2, [r0, #SDR_CTRLGRP_LOWPWRACK_ADDR]
+       and     r2, r2, #SELFRFSHACK_MASK
+       cmp     r2, #SELFRFSHACK_MASK
+       beq     ack_1
+
+       add     r3, #1
+       cmp     r3, #MAX_LOOP_COUNT
+       bne     while_ack_0
+
+ack_1:
+       mov     r1, r3
+
+       /*
+        * Execute an ISB instruction to ensure that all of the
+        * CP15 register changes have been committed.
+        */
+       isb
+
+       /*
+        * Execute a barrier instruction to ensure that all cache,
+        * TLB and branch predictor maintenance operations issued
+        * by any CPU in the cluster have completed.
+        */
+       dsb
+       dmb
+
+       wfi
+
+       /* Disable self-refresh: set sdr.ctrlgrp.lowpwreq.selfrshreq = 0 */
+       ldr     r2, [r0, #SDR_CTRLGRP_LOWPWREQ_ADDR]
+       bic     r2, r2, #SELFRSHREQ_MASK
+       str     r2, [r0, #SDR_CTRLGRP_LOWPWREQ_ADDR]
+
+       /* Poll until sdr.ctrlgrp.lowpwrack.selfrfshack == 0 or hit max loops */
+       mov     r3, #0
+while_ack_1:
+       ldr     r2, [r0, #SDR_CTRLGRP_LOWPWRACK_ADDR]
+       and     r2, r2, #SELFRFSHACK_MASK
+       cmp     r2, #SELFRFSHACK_MASK
+       bne     ack_0
+
+       add     r3, #1
+       cmp     r3, #MAX_LOOP_COUNT
+       bne     while_ack_1
+
+ack_0:
+       /*
+        * Prepare return value:
+        * Shift loop count for exiting self refresh into upper 16 bits.
+        * Leave loop count for requesting self refresh in lower 16 bits.
+        */
+       mov     r3, r3, lsl #16
+       add     r1, r1, r3
+
+       /* Disable dynamic clock gating in the Power Control Register. */
+       mrc     p15, 0, r2, c15, c0, 0
+       bic     r2, r2, #1
+       mcr     p15, 0, r2, c15, c0, 0
+
+       mov     r0, r1                  @ return value
+       bx      lr                      @ return
+
+ENDPROC(socfpga_sdram_self_refresh)
+ENTRY(socfpga_sdram_self_refresh_sz)
+       .word   . - socfpga_sdram_self_refresh
index f5e597c207b9e47d26c0a7d021563cc6bdc8bf35..19643a756c48b68b8eb57ca328785d55921ff7d7 100644 (file)
@@ -1,5 +1,5 @@
 /*
- *  Copyright (C) 2012 Altera Corporation
+ *  Copyright (C) 2012-2015 Altera Corporation
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
 
 #include "core.h"
 
-void __iomem *socfpga_scu_base_addr = ((void __iomem *)(SOCFPGA_SCU_VIRT_BASE));
 void __iomem *sys_manager_base_addr;
 void __iomem *rst_manager_base_addr;
+void __iomem *sdr_ctl_base_addr;
 unsigned long socfpga_cpu1start_addr;
 
-static struct map_desc scu_io_desc __initdata = {
-       .virtual        = SOCFPGA_SCU_VIRT_BASE,
-       .pfn            = 0, /* run-time */
-       .length         = SZ_8K,
-       .type           = MT_DEVICE,
-};
-
-static struct map_desc uart_io_desc __initdata = {
-       .virtual        = 0xfec02000,
-       .pfn            = __phys_to_pfn(0xffc02000),
-       .length         = SZ_8K,
-       .type           = MT_DEVICE,
-};
-
-static void __init socfpga_scu_map_io(void)
-{
-       unsigned long base;
-
-       /* Get SCU base */
-       asm("mrc p15, 4, %0, c15, c0, 0" : "=r" (base));
-
-       scu_io_desc.pfn = __phys_to_pfn(base);
-       iotable_init(&scu_io_desc, 1);
-}
-
-static void __init socfpga_map_io(void)
-{
-       socfpga_scu_map_io();
-       iotable_init(&uart_io_desc, 1);
-       early_printk("Early printk initialized\n");
-}
-
 void __init socfpga_sysmgr_init(void)
 {
        struct device_node *np;
@@ -82,6 +50,9 @@ void __init socfpga_sysmgr_init(void)
 
        np = of_find_compatible_node(NULL, NULL, "altr,rst-mgr");
        rst_manager_base_addr = of_iomap(np, 0);
+
+       np = of_find_compatible_node(NULL, NULL, "altr,sdr-ctl");
+       sdr_ctl_base_addr = of_iomap(np, 0);
 }
 
 static void __init socfpga_init_irq(void)
@@ -111,8 +82,6 @@ static const char *altera_dt_match[] = {
 DT_MACHINE_START(SOCFPGA, "Altera SOCFPGA")
        .l2c_aux_val    = 0,
        .l2c_aux_mask   = ~0,
-       .smp            = smp_ops(socfpga_smp_ops),
-       .map_io         = socfpga_map_io,
        .init_irq       = socfpga_init_irq,
        .restart        = socfpga_cyclone5_restart,
        .dt_compat      = altera_dt_match,
diff --git a/arch/arm/mach-stm32/Makefile b/arch/arm/mach-stm32/Makefile
new file mode 100644 (file)
index 0000000..bd0b7b5
--- /dev/null
@@ -0,0 +1 @@
+obj-y += board-dt.o
diff --git a/arch/arm/mach-stm32/Makefile.boot b/arch/arm/mach-stm32/Makefile.boot
new file mode 100644 (file)
index 0000000..eacfc3f
--- /dev/null
@@ -0,0 +1,3 @@
+# Empty file waiting for deletion once Makefile.boot isn't needed any more.
+# Patch waits for application at
+# http://www.arm.linux.org.uk/developer/patches/viewpatch.php?id=7889/1 .
diff --git a/arch/arm/mach-stm32/board-dt.c b/arch/arm/mach-stm32/board-dt.c
new file mode 100644 (file)
index 0000000..f2ad772
--- /dev/null
@@ -0,0 +1,19 @@
+/*
+ * Copyright (C) Maxime Coquelin 2015
+ * Author:  Maxime Coquelin <mcoquelin.stm32@gmail.com>
+ * License terms:  GNU General Public License (GPL), version 2
+ */
+
+#include <linux/kernel.h>
+#include <asm/v7m.h>
+#include <asm/mach/arch.h>
+
+static const char *const stm32_compat[] __initconst = {
+       "st,stm32f429",
+       NULL
+};
+
+DT_MACHINE_START(STM32DT, "STM32 (Device Tree Support)")
+       .dt_compat = stm32_compat,
+       .restart = armv7m_restart,
+MACHINE_END
index 587b0468efcc30f094c45ca6c4e50b91afff122d..e8483ec79d6706c0994b2dcd71a8183cd1e6a787 100644 (file)
@@ -121,3 +121,72 @@ static struct smp_operations sun6i_smp_ops __initdata = {
        .smp_boot_secondary     = sun6i_smp_boot_secondary,
 };
 CPU_METHOD_OF_DECLARE(sun6i_a31_smp, "allwinner,sun6i-a31", &sun6i_smp_ops);
+
+static void __init sun8i_smp_prepare_cpus(unsigned int max_cpus)
+{
+       struct device_node *node;
+
+       node = of_find_compatible_node(NULL, NULL, "allwinner,sun8i-a23-prcm");
+       if (!node) {
+               pr_err("Missing A23 PRCM node in the device tree\n");
+               return;
+       }
+
+       prcm_membase = of_iomap(node, 0);
+       if (!prcm_membase) {
+               pr_err("Couldn't map A23 PRCM registers\n");
+               return;
+       }
+
+       node = of_find_compatible_node(NULL, NULL,
+                                      "allwinner,sun8i-a23-cpuconfig");
+       if (!node) {
+               pr_err("Missing A23 CPU config node in the device tree\n");
+               return;
+       }
+
+       cpucfg_membase = of_iomap(node, 0);
+       if (!cpucfg_membase)
+               pr_err("Couldn't map A23 CPU config registers\n");
+
+}
+
+static int sun8i_smp_boot_secondary(unsigned int cpu,
+                                   struct task_struct *idle)
+{
+       u32 reg;
+
+       if (!(prcm_membase && cpucfg_membase))
+               return -EFAULT;
+
+       spin_lock(&cpu_lock);
+
+       /* Set CPU boot address */
+       writel(virt_to_phys(secondary_startup),
+              cpucfg_membase + CPUCFG_PRIVATE0_REG);
+
+       /* Assert the CPU core in reset */
+       writel(0, cpucfg_membase + CPUCFG_CPU_RST_CTRL_REG(cpu));
+
+       /* Assert the L1 cache in reset */
+       reg = readl(cpucfg_membase + CPUCFG_GEN_CTRL_REG);
+       writel(reg & ~BIT(cpu), cpucfg_membase + CPUCFG_GEN_CTRL_REG);
+
+       /* Clear CPU power-off gating */
+       reg = readl(prcm_membase + PRCM_CPU_PWROFF_REG);
+       writel(reg & ~BIT(cpu), prcm_membase + PRCM_CPU_PWROFF_REG);
+       mdelay(1);
+
+       /* Deassert the CPU core reset */
+       writel(3, cpucfg_membase + CPUCFG_CPU_RST_CTRL_REG(cpu));
+
+       spin_unlock(&cpu_lock);
+
+       return 0;
+}
+
+struct smp_operations sun8i_smp_ops __initdata = {
+       .smp_prepare_cpus       = sun8i_smp_prepare_cpus,
+       .smp_boot_secondary     = sun8i_smp_boot_secondary,
+};
+CPU_METHOD_OF_DECLARE(sun8i_a23_smp, "allwinner,sun8i-a23", &sun8i_smp_ops);
index 88de2dce2e8722820644b752ae8c4cee0c129ec9..7469347b17493890ec43856b2a961a407bc6f7e0 100644 (file)
@@ -34,6 +34,7 @@
 #include "iomap.h"
 #include "irq.h"
 #include "pm.h"
+#include "reset.h"
 #include "sleep.h"
 
 #ifdef CONFIG_PM_SLEEP
@@ -70,15 +71,13 @@ static struct cpuidle_driver tegra_idle_driver = {
 
 #ifdef CONFIG_PM_SLEEP
 #ifdef CONFIG_SMP
-static void __iomem *pmc = IO_ADDRESS(TEGRA_PMC_BASE);
-
 static int tegra20_reset_sleeping_cpu_1(void)
 {
        int ret = 0;
 
        tegra_pen_lock();
 
-       if (readl(pmc + PMC_SCRATCH41) == CPU_RESETTABLE)
+       if (readb(tegra20_cpu1_resettable_status) == CPU_RESETTABLE)
                tegra20_cpu_shutdown(1);
        else
                ret = -EINVAL;
index 71be4af5e975bec078508d1ea920568edf11b289..e3070fdab80b8b7481c0527e2d649ae7d664dc58 100644 (file)
@@ -169,10 +169,10 @@ after_errata:
        cmp     r6, #TEGRA20
        bne     1f
        /* If not CPU0, don't let CPU0 reset CPU1 now that CPU1 is coming up. */
-       mov32   r5, TEGRA_PMC_BASE
-       mov     r0, #0
+       mov32   r5, TEGRA_IRAM_BASE + TEGRA_IRAM_RESET_HANDLER_OFFSET
+       mov     r0, #CPU_NOT_RESETTABLE
        cmp     r10, #0
-       strne   r0, [r5, #PMC_SCRATCH41]
+       strneb  r0, [r5, #__tegra20_cpu1_resettable_status_offset]
 1:
 #endif
 
@@ -281,6 +281,10 @@ __tegra_cpu_reset_handler_data:
        .rept   TEGRA_RESET_DATA_SIZE
        .long   0
        .endr
+       .globl  __tegra20_cpu1_resettable_status_offset
+       .equ    __tegra20_cpu1_resettable_status_offset, \
+                                       . - __tegra_cpu_reset_handler_start
+       .byte   0
        .align L1_CACHE_SHIFT
 
 ENTRY(__tegra_cpu_reset_handler_end)
index 0aee0129f8d7eb8ffea3b33bc471d4ca2aa11ef2..9c479c7925b85fc3e72032bdd9385a51160dc0e0 100644 (file)
@@ -35,6 +35,7 @@ extern unsigned long __tegra_cpu_reset_handler_data[TEGRA_RESET_DATA_SIZE];
 
 void __tegra_cpu_reset_handler_start(void);
 void __tegra_cpu_reset_handler(void);
+void __tegra20_cpu1_resettable_status_offset(void);
 void __tegra_cpu_reset_handler_end(void);
 
 #ifdef CONFIG_PM_SLEEP
@@ -46,6 +47,9 @@ void __tegra_cpu_reset_handler_end(void);
        (IO_ADDRESS(TEGRA_IRAM_BASE + TEGRA_IRAM_RESET_HANDLER_OFFSET + \
        ((u32)&__tegra_cpu_reset_handler_data[TEGRA_RESET_MASK_LP2] - \
         (u32)__tegra_cpu_reset_handler_start)))
+#define tegra20_cpu1_resettable_status \
+       (IO_ADDRESS(TEGRA_IRAM_BASE + TEGRA_IRAM_RESET_HANDLER_OFFSET + \
+        (u32)__tegra20_cpu1_resettable_status_offset))
 #endif
 
 #define tegra_cpu_reset_handler_offset \
index be4bc5f853f5c370ed345bf135d1092b9e94e883..e6b684e14322cef21e44d1b660e4c6e8d0c7ec43 100644 (file)
@@ -97,9 +97,10 @@ ENDPROC(tegra20_hotplug_shutdown)
 ENTRY(tegra20_cpu_shutdown)
        cmp     r0, #0
        reteq   lr                      @ must not be called for CPU 0
-       mov32   r1, TEGRA_PMC_VIRT + PMC_SCRATCH41
+       mov32   r1, TEGRA_IRAM_RESET_BASE_VIRT
+       ldr     r2, =__tegra20_cpu1_resettable_status_offset
        mov     r12, #CPU_RESETTABLE
-       str     r12, [r1]
+       strb    r12, [r1, r2]
 
        cpu_to_halt_reg r1, r0
        ldr     r3, =TEGRA_FLOW_CTRL_VIRT
@@ -182,38 +183,41 @@ ENDPROC(tegra_pen_unlock)
 /*
  * tegra20_cpu_clear_resettable(void)
  *
- * Called to clear the "resettable soon" flag in PMC_SCRATCH41 when
+ * Called to clear the "resettable soon" flag in IRAM variable when
  * it is expected that the secondary CPU will be idle soon.
  */
 ENTRY(tegra20_cpu_clear_resettable)
-       mov32   r1, TEGRA_PMC_VIRT + PMC_SCRATCH41
+       mov32   r1, TEGRA_IRAM_RESET_BASE_VIRT
+       ldr     r2, =__tegra20_cpu1_resettable_status_offset
        mov     r12, #CPU_NOT_RESETTABLE
-       str     r12, [r1]
+       strb    r12, [r1, r2]
        ret     lr
 ENDPROC(tegra20_cpu_clear_resettable)
 
 /*
  * tegra20_cpu_set_resettable_soon(void)
  *
- * Called to set the "resettable soon" flag in PMC_SCRATCH41 when
+ * Called to set the "resettable soon" flag in IRAM variable when
  * it is expected that the secondary CPU will be idle soon.
  */
 ENTRY(tegra20_cpu_set_resettable_soon)
-       mov32   r1, TEGRA_PMC_VIRT + PMC_SCRATCH41
+       mov32   r1, TEGRA_IRAM_RESET_BASE_VIRT
+       ldr     r2, =__tegra20_cpu1_resettable_status_offset
        mov     r12, #CPU_RESETTABLE_SOON
-       str     r12, [r1]
+       strb    r12, [r1, r2]
        ret     lr
 ENDPROC(tegra20_cpu_set_resettable_soon)
 
 /*
  * tegra20_cpu_is_resettable_soon(void)
  *
- * Returns true if the "resettable soon" flag in PMC_SCRATCH41 has been
+ * Returns true if the "resettable soon" flag in IRAM variable has been
  * set because it is expected that the secondary CPU will be idle soon.
  */
 ENTRY(tegra20_cpu_is_resettable_soon)
-       mov32   r1, TEGRA_PMC_VIRT + PMC_SCRATCH41
-       ldr     r12, [r1]
+       mov32   r1, TEGRA_IRAM_RESET_BASE_VIRT
+       ldr     r2, =__tegra20_cpu1_resettable_status_offset
+       ldrb    r12, [r1, r2]
        cmp     r12, #CPU_RESETTABLE_SOON
        moveq   r0, #1
        movne   r0, #0
@@ -256,9 +260,10 @@ ENTRY(tegra20_sleep_cpu_secondary_finish)
        mov     r0, #TEGRA_FLUSH_CACHE_LOUIS
        bl      tegra_disable_clean_inv_dcache
 
-       mov32   r0, TEGRA_PMC_VIRT + PMC_SCRATCH41
+       mov32   r0, TEGRA_IRAM_RESET_BASE_VIRT
+       ldr     r4, =__tegra20_cpu1_resettable_status_offset
        mov     r3, #CPU_RESETTABLE
-       str     r3, [r0]
+       strb    r3, [r0, r4]
 
        bl      tegra_cpu_do_idle
 
@@ -274,10 +279,10 @@ ENTRY(tegra20_sleep_cpu_secondary_finish)
 
        bl      tegra_pen_lock
 
-       mov32   r3, TEGRA_PMC_VIRT
-       add     r0, r3, #PMC_SCRATCH41
+       mov32   r0, TEGRA_IRAM_RESET_BASE_VIRT
+       ldr     r4, =__tegra20_cpu1_resettable_status_offset
        mov     r3, #CPU_NOT_RESETTABLE
-       str     r3, [r0]
+       strb    r3, [r0, r4]
 
        bl      tegra_pen_unlock
 
index 92d46ec1361abba6f8beb6130d753ea634c8933a..0d59360d891da8e244c81241f1cf39c96235919c 100644 (file)
@@ -18,6 +18,7 @@
 #define __MACH_TEGRA_SLEEP_H
 
 #include "iomap.h"
+#include "irammap.h"
 
 #define TEGRA_ARM_PERIF_VIRT (TEGRA_ARM_PERIF_BASE - IO_CPU_PHYS \
                                        + IO_CPU_VIRT)
@@ -29,6 +30,9 @@
                                        + IO_APB_VIRT)
 #define TEGRA_PMC_VIRT (TEGRA_PMC_BASE - IO_APB_PHYS + IO_APB_VIRT)
 
+#define TEGRA_IRAM_RESET_BASE_VIRT (IO_IRAM_VIRT + \
+                               TEGRA_IRAM_RESET_HANDLER_OFFSET)
+
 /* PMC_SCRATCH37-39 and 41 are used for tegra_pen_lock and idle */
 #define PMC_SCRATCH37  0x130
 #define PMC_SCRATCH38  0x134
index 861d88486dbec233d4ab52a42af4f666ab48ba7c..2378fa560a210b4a523d60a230b1b6ca128a42ce 100644 (file)
@@ -163,6 +163,5 @@ DT_MACHINE_START(TEGRA_DT, "NVIDIA Tegra SoC (Flattened Device Tree)")
        .init_irq       = tegra_dt_init_irq,
        .init_machine   = tegra_dt_init,
        .init_late      = tegra_dt_init_late,
-       .restart        = tegra_pmc_restart,
        .dt_compat      = tegra_dt_board_compat,
 MACHINE_END
diff --git a/arch/arm/mach-uniphier/Kconfig b/arch/arm/mach-uniphier/Kconfig
new file mode 100644 (file)
index 0000000..b640458
--- /dev/null
@@ -0,0 +1,11 @@
+config ARCH_UNIPHIER
+       bool "Socionext UniPhier SoCs"
+       depends on ARCH_MULTI_V7
+       select ARM_AMBA
+       select ARM_GLOBAL_TIMER
+       select ARM_GIC
+       select HAVE_ARM_SCU
+       select HAVE_ARM_TWD if SMP
+       help
+         Support for UniPhier SoC family developed by Socionext Inc.
+         (formerly, System LSI Business Division of Panasonic Corporation)
diff --git a/arch/arm/mach-uniphier/Makefile b/arch/arm/mach-uniphier/Makefile
new file mode 100644 (file)
index 0000000..60bd226
--- /dev/null
@@ -0,0 +1,2 @@
+obj-y                  := uniphier.o
+obj-$(CONFIG_SMP)      += platsmp.o
diff --git a/arch/arm/mach-uniphier/platsmp.c b/arch/arm/mach-uniphier/platsmp.c
new file mode 100644 (file)
index 0000000..5943e1c
--- /dev/null
@@ -0,0 +1,90 @@
+/*
+ * Copyright (C) 2015 Masahiro Yamada <yamada.masahiro@socionext.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+
+#include <linux/sizes.h>
+#include <linux/compiler.h>
+#include <linux/init.h>
+#include <linux/io.h>
+#include <linux/regmap.h>
+#include <linux/mfd/syscon.h>
+#include <asm/smp.h>
+#include <asm/smp_scu.h>
+
+static struct regmap *sbcm_regmap;
+
+static void __init uniphier_smp_prepare_cpus(unsigned int max_cpus)
+{
+       static cpumask_t only_cpu_0 = { CPU_BITS_CPU0 };
+       unsigned long scu_base_phys = 0;
+       void __iomem *scu_base;
+
+       sbcm_regmap = syscon_regmap_lookup_by_compatible(
+                       "socionext,uniphier-system-bus-controller-misc");
+       if (IS_ERR(sbcm_regmap)) {
+               pr_err("failed to regmap system-bus-controller-misc\n");
+               goto err;
+       }
+
+       if (scu_a9_has_base())
+               scu_base_phys = scu_a9_get_base();
+
+       if (!scu_base_phys) {
+               pr_err("failed to get scu base\n");
+               goto err;
+       }
+
+       scu_base = ioremap(scu_base_phys, SZ_128);
+       if (!scu_base) {
+               pr_err("failed to remap scu base (0x%08lx)\n", scu_base_phys);
+               goto err;
+       }
+
+       scu_enable(scu_base);
+       iounmap(scu_base);
+
+       return;
+err:
+       pr_warn("disabling SMP\n");
+       init_cpu_present(&only_cpu_0);
+       sbcm_regmap = NULL;
+}
+
+static void __naked uniphier_secondary_startup(void)
+{
+       asm("bl         v7_invalidate_l1\n"
+           "b          secondary_startup\n");
+};
+
+static int uniphier_boot_secondary(unsigned int cpu,
+                                  struct task_struct *idle)
+{
+       int ret;
+
+       if (!sbcm_regmap)
+               return -ENODEV;
+
+       ret = regmap_write(sbcm_regmap, 0x1208,
+                          virt_to_phys(uniphier_secondary_startup));
+       if (!ret)
+               asm("sev"); /* wake up secondary CPU */
+
+       return ret;
+}
+
+struct smp_operations uniphier_smp_ops __initdata = {
+       .smp_prepare_cpus       = uniphier_smp_prepare_cpus,
+       .smp_boot_secondary     = uniphier_boot_secondary,
+};
+CPU_METHOD_OF_DECLARE(uniphier_smp, "socionext,uniphier-smp",
+                     &uniphier_smp_ops);
diff --git a/arch/arm/mach-uniphier/uniphier.c b/arch/arm/mach-uniphier/uniphier.c
new file mode 100644 (file)
index 0000000..9be10ef
--- /dev/null
@@ -0,0 +1,30 @@
+/*
+ * Copyright (C) 2015 Masahiro Yamada <yamada.masahiro@socionext.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+
+#include <asm/mach/arch.h>
+
+static const char * const uniphier_dt_compat[] __initconst = {
+       "socionext,ph1-sld3",
+       "socionext,ph1-ld4",
+       "socionext,ph1-pro4",
+       "socionext,ph1-sld8",
+       "socionext,ph1-pro5",
+       "socionext,proxstream2",
+       "socionext,ph1-ld6b",
+       NULL,
+};
+
+DT_MACHINE_START(UNIPHIER, "Socionext UniPhier")
+       .dt_compat      = uniphier_dt_compat,
+MACHINE_END
diff --git a/arch/arm/mach-zx/Kconfig b/arch/arm/mach-zx/Kconfig
new file mode 100644 (file)
index 0000000..2a910dc
--- /dev/null
@@ -0,0 +1,18 @@
+menuconfig ARCH_ZX
+       bool "ZTE ZX family" if ARCH_MULTI_V7
+       help
+         Support for ZTE ZX-based family of processors. TV
+         set-top-box processor is supported. More will be
+         added soon.
+
+if ARCH_ZX
+
+config SOC_ZX296702
+       def_bool y
+       select ARM_GIC
+       select ARM_GLOBAL_TIMER
+       select HAVE_ARM_SCU if SMP
+       select HAVE_ARM_TWD if SMP
+       help
+         Support for ZTE ZX296702 SoC which is a dual core CortexA9MP
+endif
diff --git a/arch/arm/mach-zx/Makefile b/arch/arm/mach-zx/Makefile
new file mode 100644 (file)
index 0000000..7c2edf6
--- /dev/null
@@ -0,0 +1,2 @@
+obj-$(CONFIG_SOC_ZX296702) += zx296702.o
+obj-$(CONFIG_SMP) += headsmp.o platsmp.o
diff --git a/arch/arm/mach-zx/core.h b/arch/arm/mach-zx/core.h
new file mode 100644 (file)
index 0000000..3efe8e0
--- /dev/null
@@ -0,0 +1,19 @@
+/*
+ * Copyright 2014 Linaro Ltd.
+ * Copyright (C) 2014 ZTE Corporation.
+ *
+ * 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.
+ */
+
+#ifndef __MACH_ZX_CORE_H
+#define __MACH_ZX_CORE_H
+
+extern void zx_resume_jump(void);
+extern size_t zx_suspend_iram_sz;
+extern unsigned long zx_secondary_startup_pa;
+
+void zx_secondary_startup(void);
+
+#endif /* __MACH_ZX_CORE_H */
diff --git a/arch/arm/mach-zx/headsmp.S b/arch/arm/mach-zx/headsmp.S
new file mode 100644 (file)
index 0000000..a1aa402
--- /dev/null
@@ -0,0 +1,33 @@
+/*
+ * Copyright 2014 Linaro Ltd.
+ * Copyright (C) 2014 ZTE Corporation.
+ *
+ * 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/linkage.h>
+
+       .align 3
+       .arm
+
+/* It runs from physical address */
+ENTRY(zx_resume_jump)
+       adr     r1, zx_secondary_startup_pa
+       ldr     r0, [r1]
+       bx      r0
+ENDPROC(zx_resume_jump)
+
+ENTRY(zx_secondary_startup_pa)
+       .word   zx_secondary_startup_pa
+
+ENTRY(zx_suspend_iram_sz)
+        .word  . - zx_resume_jump
+ENDPROC(zx_secondary_startup_pa)
+
+
+ENTRY(zx_secondary_startup)
+       bl      v7_invalidate_l1
+       b       secondary_startup
+ENDPROC(zx_secondary_startup)
diff --git a/arch/arm/mach-zx/platsmp.c b/arch/arm/mach-zx/platsmp.c
new file mode 100644 (file)
index 0000000..a369398
--- /dev/null
@@ -0,0 +1,189 @@
+/*
+ * Copyright 2014 Linaro Ltd.
+ * Copyright (C) 2014 ZTE Corporation.
+ *
+ * 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/delay.h>
+#include <linux/errno.h>
+#include <linux/init.h>
+#include <linux/io.h>
+#include <linux/jiffies.h>
+#include <linux/of.h>
+#include <linux/of_address.h>
+#include <linux/smp.h>
+
+#include <asm/cacheflush.h>
+#include <asm/cp15.h>
+#include <asm/fncpy.h>
+#include <asm/proc-fns.h>
+#include <asm/smp_scu.h>
+#include <asm/smp_plat.h>
+
+#include "core.h"
+
+#define AON_SYS_CTRL_RESERVED1         0xa8
+
+#define BUS_MATRIX_REMAP_CONFIG                0x00
+
+#define PCU_CPU0_CTRL                  0x00
+#define PCU_CPU1_CTRL                  0x04
+#define PCU_CPU1_ST                    0x0c
+#define PCU_GLOBAL_CTRL                        0x14
+#define PCU_EXPEND_CONTROL             0x34
+
+#define ZX_IRAM_BASE                   0x00200000
+
+static void __iomem *pcu_base;
+static void __iomem *matrix_base;
+static void __iomem *scu_base;
+
+void __init zx_smp_prepare_cpus(unsigned int max_cpus)
+{
+       struct device_node *np;
+       unsigned long base = 0;
+       void __iomem *aonsysctrl_base;
+       void __iomem *sys_iram;
+
+       base = scu_a9_get_base();
+       scu_base = ioremap(base, SZ_256);
+       if (!scu_base) {
+               pr_err("%s: failed to map scu\n", __func__);
+               return;
+       }
+
+       scu_enable(scu_base);
+
+       np = of_find_compatible_node(NULL, NULL, "zte,sysctrl");
+       if (!np) {
+               pr_err("%s: failed to find sysctrl node\n", __func__);
+               return;
+       }
+
+       aonsysctrl_base = of_iomap(np, 0);
+       if (!aonsysctrl_base) {
+               pr_err("%s: failed to map aonsysctrl\n", __func__);
+               of_node_put(np);
+               return;
+       }
+
+       /*
+        * Write the address of secondary startup into the
+        * system-wide flags register. The BootMonitor waits
+        * until it receives a soft interrupt, and then the
+        * secondary CPU branches to this address.
+        */
+       __raw_writel(virt_to_phys(zx_secondary_startup),
+                    aonsysctrl_base + AON_SYS_CTRL_RESERVED1);
+
+       iounmap(aonsysctrl_base);
+       of_node_put(np);
+
+       np = of_find_compatible_node(NULL, NULL, "zte,zx296702-pcu");
+       pcu_base = of_iomap(np, 0);
+       of_node_put(np);
+       WARN_ON(!pcu_base);
+
+       np = of_find_compatible_node(NULL, NULL, "zte,zx-bus-matrix");
+       matrix_base = of_iomap(np, 0);
+       of_node_put(np);
+       WARN_ON(!matrix_base);
+
+       /* Map the first 4 KB IRAM for suspend usage */
+       sys_iram = __arm_ioremap_exec(ZX_IRAM_BASE, PAGE_SIZE, false);
+       zx_secondary_startup_pa = virt_to_phys(zx_secondary_startup);
+       fncpy(sys_iram, &zx_resume_jump, zx_suspend_iram_sz);
+}
+
+static int zx_boot_secondary(unsigned int cpu, struct task_struct *idle)
+{
+       static bool first_boot = true;
+
+       if (first_boot) {
+               arch_send_wakeup_ipi_mask(cpumask_of(cpu));
+               first_boot = false;
+               return 0;
+       }
+
+       /* Swap the base address mapping between IRAM and IROM */
+       writel_relaxed(0x1, matrix_base + BUS_MATRIX_REMAP_CONFIG);
+
+       /* Power on CPU1 */
+       writel_relaxed(0x0, pcu_base + PCU_CPU1_CTRL);
+
+       /* Wait for power on ack */
+       while (readl_relaxed(pcu_base + PCU_CPU1_ST) & 0x4)
+               cpu_relax();
+
+       /* Swap back the mapping of IRAM and IROM */
+       writel_relaxed(0x0, matrix_base + BUS_MATRIX_REMAP_CONFIG);
+
+       return 0;
+}
+
+#ifdef CONFIG_HOTPLUG_CPU
+static inline void cpu_enter_lowpower(void)
+{
+       unsigned int v;
+
+       asm volatile(
+               "mcr    p15, 0, %1, c7, c5, 0\n"
+       "       mcr     p15, 0, %1, c7, c10, 4\n"
+       /*
+        * Turn off coherency
+        */
+       "       mrc     p15, 0, %0, c1, c0, 1\n"
+       "       bic     %0, %0, %3\n"
+       "       mcr     p15, 0, %0, c1, c0, 1\n"
+       "       mrc     p15, 0, %0, c1, c0, 0\n"
+       "       bic     %0, %0, %2\n"
+       "       mcr     p15, 0, %0, c1, c0, 0\n"
+         : "=&r" (v)
+         : "r" (0), "Ir" (CR_C), "Ir" (0x40)
+         : "cc");
+}
+
+static int zx_cpu_kill(unsigned int cpu)
+{
+       unsigned long timeout = jiffies + msecs_to_jiffies(2000);
+
+       writel_relaxed(0x2, pcu_base + PCU_CPU1_CTRL);
+
+       while ((readl_relaxed(pcu_base + PCU_CPU1_ST) & 0x3) != 0x0) {
+               if (time_after(jiffies, timeout)) {
+                       pr_err("*** cpu1 poweroff timeout\n");
+                       break;
+               }
+       }
+       return 1;
+}
+
+static void zx_cpu_die(unsigned int cpu)
+{
+       scu_power_mode(scu_base, SCU_PM_POWEROFF);
+       cpu_enter_lowpower();
+
+       while (1)
+               cpu_do_idle();
+}
+#endif
+
+static void zx_secondary_init(unsigned int cpu)
+{
+       scu_power_mode(scu_base, SCU_PM_NORMAL);
+}
+
+struct smp_operations zx_smp_ops __initdata = {
+       .smp_prepare_cpus       = zx_smp_prepare_cpus,
+       .smp_secondary_init     = zx_secondary_init,
+       .smp_boot_secondary     = zx_boot_secondary,
+#ifdef CONFIG_HOTPLUG_CPU
+       .cpu_kill               = zx_cpu_kill,
+       .cpu_die                = zx_cpu_die,
+#endif
+};
+
+CPU_METHOD_OF_DECLARE(zx_smp, "zte,zx296702-smp", &zx_smp_ops);
diff --git a/arch/arm/mach-zx/zx296702.c b/arch/arm/mach-zx/zx296702.c
new file mode 100644 (file)
index 0000000..60bb1a8
--- /dev/null
@@ -0,0 +1,25 @@
+/*
+ * Copyright 2014 Linaro Ltd.
+ * Copyright (C) 2014 ZTE Corporation.
+ *
+ * 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 <asm/mach/arch.h>
+#include <asm/mach/map.h>
+
+#include <linux/of_address.h>
+#include <linux/of_platform.h>
+
+static const char *zx296702_dt_compat[] __initconst = {
+       "zte,zx296702",
+       NULL,
+};
+
+DT_MACHINE_START(ZX, "ZTE ZX296702 (Device Tree)")
+       .dt_compat      = zx296702_dt_compat,
+       .l2c_aux_val    = 0,
+       .l2c_aux_mask   = ~0,
+MACHINE_END
index 58ef2a700414fcca15d58091223778746c1d1c8d..616d5840fc2e4aefe2af918a56aa48a85f3c931c 100644 (file)
@@ -190,11 +190,6 @@ static void __init zynq_irq_init(void)
        irqchip_init();
 }
 
-static void zynq_system_reset(enum reboot_mode mode, const char *cmd)
-{
-       zynq_slcr_system_reset();
-}
-
 static const char * const zynq_dt_match[] = {
        "xlnx,zynq-7000",
        NULL
@@ -212,5 +207,4 @@ DT_MACHINE_START(XILINX_EP107, "Xilinx Zynq Platform")
        .init_time      = zynq_timer_init,
        .dt_compat      = zynq_dt_match,
        .reserve        = zynq_memory_init,
-       .restart        = zynq_system_reset,
 MACHINE_END
index 7038cae95ddcd4769e1b56e383dd270b987923e4..79cda2e5fa4ec4e214c2cdf5a5cb6d79b12d719b 100644 (file)
@@ -19,7 +19,6 @@
 
 extern int zynq_slcr_init(void);
 extern int zynq_early_slcr_init(void);
-extern void zynq_slcr_system_reset(void);
 extern void zynq_slcr_cpu_stop(int cpu);
 extern void zynq_slcr_cpu_start(int cpu);
 extern bool zynq_slcr_cpu_state_read(int cpu);
index c3c24fd8b3062ce32921275bb0434a549b8749d1..26320ebf349349a06c8257aa7ce87e7c7d5c46c9 100644 (file)
@@ -15,6 +15,7 @@
  */
 
 #include <linux/io.h>
+#include <linux/reboot.h>
 #include <linux/mfd/syscon.h>
 #include <linux/of_address.h>
 #include <linux/regmap.h>
@@ -92,19 +93,20 @@ u32 zynq_slcr_get_device_id(void)
 }
 
 /**
- * zynq_slcr_system_reset - Reset the entire system.
+ * zynq_slcr_system_restart - Restart the entire system.
+ *
+ * @nb:                Pointer to restart notifier block (unused)
+ * @action:    Reboot mode (unused)
+ * @data:      Restart handler private data (unused)
+ *
+ * Return:     0 always
  */
-void zynq_slcr_system_reset(void)
+static
+int zynq_slcr_system_restart(struct notifier_block *nb,
+                            unsigned long action, void *data)
 {
        u32 reboot;
 
-       /*
-        * Unlock the SLCR then reset the system.
-        * Note that this seems to require raw i/o
-        * functions or there's a lockup?
-        */
-       zynq_slcr_unlock();
-
        /*
         * Clear 0x0F000000 bits of reboot status register to workaround
         * the FSBL not loading the bitstream after soft-reboot
@@ -113,8 +115,14 @@ void zynq_slcr_system_reset(void)
        zynq_slcr_read(&reboot, SLCR_REBOOT_STATUS_OFFSET);
        zynq_slcr_write(reboot & 0xF0FFFFFF, SLCR_REBOOT_STATUS_OFFSET);
        zynq_slcr_write(1, SLCR_PS_RST_CTRL_OFFSET);
+       return 0;
 }
 
+static struct notifier_block zynq_slcr_restart_nb = {
+       .notifier_call  = zynq_slcr_system_restart,
+       .priority       = 192,
+};
+
 /**
  * zynq_slcr_cpu_start - Start cpu
  * @cpu:       cpu number
@@ -219,6 +227,8 @@ int __init zynq_early_slcr_init(void)
        /* unlock the SLCR so that registers can be changed */
        zynq_slcr_unlock();
 
+       register_restart_handler(&zynq_slcr_restart_nb);
+
        pr_info("%s mapped to %p\n", np->name, zynq_slcr_base);
 
        of_node_put(np);
index 6416e03b448231444d192ca05f44b2d0d5656786..1e460b4ee3b9d591a560c8145226fe067f8b3da2 100644 (file)
 
 #include <linux/omap-dma.h>
 
+#ifdef CONFIG_ARCH_OMAP1
+#include <mach/soc.h>
+#endif
+
 /*
  * MAX_LOGICAL_DMA_CH_COUNT: the maximum number of logical DMA
  * channels that an instance of the SDMA IP block can support.  Used
index e2be70df06c6506459c732596e6bffe18ff3f296..efa6e85619ad824c2d9ea9a2bdb0b2c0eb9a3077 100644 (file)
@@ -389,7 +389,7 @@ static int s3c_adc_probe(struct platform_device *pdev)
        if (ret)
                return ret;
 
-       clk_enable(adc->clk);
+       clk_prepare_enable(adc->clk);
 
        tmp = adc->prescale | S3C2410_ADCCON_PRSCEN;
 
@@ -413,7 +413,7 @@ static int s3c_adc_remove(struct platform_device *pdev)
 {
        struct adc_device *adc = platform_get_drvdata(pdev);
 
-       clk_disable(adc->clk);
+       clk_disable_unprepare(adc->clk);
        regulator_disable(adc->vdd);
 
        return 0;
@@ -475,7 +475,7 @@ static int s3c_adc_resume(struct device *dev)
 #define s3c_adc_resume NULL
 #endif
 
-static struct platform_device_id s3c_adc_driver_ids[] = {
+static const struct platform_device_id s3c_adc_driver_ids[] = {
        {
                .name           = "s3c24xx-adc",
                .driver_data    = TYPE_ADCV1,
index f6e4d56eda007faeb26639fc54a2014b8fae1b58..2a61e4b04600896329bb0ca8f316cb3861ed2cf2 100644 (file)
@@ -445,6 +445,19 @@ static void vfp_enable(void *unused)
        set_copro_access(access | CPACC_FULL(10) | CPACC_FULL(11));
 }
 
+/* Called by platforms on which we want to disable VFP because it may not be
+ * present on all CPUs within a SMP complex. Needs to be called prior to
+ * vfp_init().
+ */
+void vfp_disable(void)
+{
+       if (VFP_arch) {
+               pr_debug("%s: should be called prior to vfp_init\n", __func__);
+               return;
+       }
+       VFP_arch = 1;
+}
+
 #ifdef CONFIG_CPU_PM
 static int vfp_pm_suspend(void)
 {
index 7796af4b1d6f65f6352ed40cd6dfcaf580cfd63d..cb8fa34e1a6c717f78174ba847e354fb92653246 100644 (file)
@@ -181,6 +181,11 @@ config ARCH_FSL_LS2085A
        help
          This enables support for Freescale LS2085A SOC.
 
+config ARCH_HISI
+       bool "Hisilicon SoC Family"
+       help
+         This enables support for Hisilicon ARMv8 SoC family
+
 config ARCH_MEDIATEK
        bool "Mediatek MT65xx & MT81xx ARMv8 SoC"
        select ARM_GIC
index 2ed7449d9273c01b314d59c7a81b12472b4f7948..1d293ea16f468cb007f00724251832e677a27adf 100644 (file)
@@ -33,6 +33,7 @@ CONFIG_MODULE_UNLOAD=y
 # CONFIG_IOSCHED_DEADLINE is not set
 CONFIG_ARCH_EXYNOS7=y
 CONFIG_ARCH_FSL_LS2085A=y
+CONFIG_ARCH_HISI=y
 CONFIG_ARCH_MEDIATEK=y
 CONFIG_ARCH_SEATTLE=y
 CONFIG_ARCH_TEGRA=y
index 738612c45266c1b11f1319ae95275dcc881b8590..f364fa4d24ebffa8b9021036b3e3f22d0018da40 100644 (file)
@@ -91,6 +91,7 @@ static const int gisb_offsets_bcm7445[] = {
 struct brcmstb_gisb_arb_device {
        void __iomem    *base;
        const int       *gisb_offsets;
+       bool            big_endian;
        struct mutex    lock;
        struct list_head next;
        u32 valid_mask;
@@ -108,7 +109,10 @@ static u32 gisb_read(struct brcmstb_gisb_arb_device *gdev, int reg)
        if (offset == -1)
                return 1;
 
-       return ioread32(gdev->base + offset);
+       if (gdev->big_endian)
+               return ioread32be(gdev->base + offset);
+       else
+               return ioread32(gdev->base + offset);
 }
 
 static void gisb_write(struct brcmstb_gisb_arb_device *gdev, u32 val, int reg)
@@ -117,7 +121,11 @@ static void gisb_write(struct brcmstb_gisb_arb_device *gdev, u32 val, int reg)
 
        if (offset == -1)
                return;
-       iowrite32(val, gdev->base + reg);
+
+       if (gdev->big_endian)
+               iowrite32be(val, gdev->base + reg);
+       else
+               iowrite32(val, gdev->base + reg);
 }
 
 static ssize_t gisb_arb_get_timeout(struct device *dev,
@@ -296,6 +304,7 @@ static int __init brcmstb_gisb_arb_probe(struct platform_device *pdev)
                return -EINVAL;
        }
        gdev->gisb_offsets = of_id->data;
+       gdev->big_endian = of_device_is_big_endian(dn);
 
        err = devm_request_irq(&pdev->dev, timeout_irq,
                                brcmstb_gisb_timeout_handler, 0, pdev->name,
index 3d00c25382c53b02e9d461437aa38c5eea77b090..4dcbdd36f24eb552412310c78a482f38e013edcb 100644 (file)
@@ -50,6 +50,7 @@ obj-$(CONFIG_ARCH_BERLIN)             += berlin/
 obj-$(CONFIG_ARCH_HI3xxx)              += hisilicon/
 obj-$(CONFIG_ARCH_HIP04)               += hisilicon/
 obj-$(CONFIG_ARCH_HIX5HD2)             += hisilicon/
+obj-$(CONFIG_ARCH_MXC)                 += imx/
 obj-$(CONFIG_COMMON_CLK_KEYSTONE)      += keystone/
 ifeq ($(CONFIG_COMMON_CLK), y)
 obj-$(CONFIG_ARCH_MMP)                 += mmp/
@@ -72,4 +73,5 @@ obj-$(CONFIG_ARCH_OMAP2PLUS)          += ti/
 obj-$(CONFIG_ARCH_U8500)               += ux500/
 obj-$(CONFIG_COMMON_CLK_VERSATILE)     += versatile/
 obj-$(CONFIG_X86)                      += x86/
+obj-$(CONFIG_ARCH_ZX)                  += zte/
 obj-$(CONFIG_ARCH_ZYNQ)                        += zynq/
diff --git a/drivers/clk/imx/Makefile b/drivers/clk/imx/Makefile
new file mode 100644 (file)
index 0000000..75fae16
--- /dev/null
@@ -0,0 +1,26 @@
+
+obj-y += \
+       clk.o \
+       clk-busy.o \
+       clk-cpu.o \
+       clk-fixup-div.o \
+       clk-fixup-mux.o \
+       clk-gate-exclusive.o \
+       clk-gate2.o \
+       clk-pllv1.o \
+       clk-pllv2.o \
+       clk-pllv3.o \
+       clk-pfd.o
+
+obj-$(CONFIG_SOC_IMX1)   += clk-imx1.o
+obj-$(CONFIG_SOC_IMX21)  += clk-imx21.o
+obj-$(CONFIG_SOC_IMX25)  += clk-imx25.o
+obj-$(CONFIG_SOC_IMX27)  += clk-imx27.o
+obj-$(CONFIG_SOC_IMX31)  += clk-imx31.o
+obj-$(CONFIG_SOC_IMX35)  += clk-imx35.o
+obj-$(CONFIG_SOC_IMX5)   += clk-imx51-imx53.o
+obj-$(CONFIG_SOC_IMX6Q)  += clk-imx6q.o
+obj-$(CONFIG_SOC_IMX6SL) += clk-imx6sl.o
+obj-$(CONFIG_SOC_IMX6SX) += clk-imx6sx.o
+obj-$(CONFIG_SOC_IMX7D)  += clk-imx7d.o
+obj-$(CONFIG_SOC_VF610)  += clk-vf610.o
similarity index 99%
rename from arch/arm/mach-imx/clk-cpu.c
rename to drivers/clk/imx/clk-cpu.c
index aa1c345e2a1911e3a0803aa3782227844b0ff738..9d46eac87f45e7f4ec0e2f72aba0b179b574b9a6 100644 (file)
@@ -12,6 +12,7 @@
 #include <linux/clk.h>
 #include <linux/clk-provider.h>
 #include <linux/slab.h>
+#include "clk.h"
 
 struct clk_cpu {
        struct clk_hw   hw;
similarity index 91%
rename from arch/arm/mach-imx/clk-imx1.c
rename to drivers/clk/imx/clk-imx1.c
index 37c307a8d8962c1c6b80aab4e2650bfe2286d641..c2647fa19f281eb74f65d08553bcbe823aa59979 100644 (file)
 #include <linux/of.h>
 #include <linux/of_address.h>
 #include <dt-bindings/clock/imx1-clock.h>
+#include <soc/imx/timer.h>
+#include <asm/irq.h>
 
 #include "clk.h"
-#include "common.h"
-#include "hardware.h"
+
+#define MX1_CCM_BASE_ADDR      0x0021b000
+#define MX1_TIM1_BASE_ADDR     0x00220000
+#define MX1_TIM1_INT           (NR_IRQS_LEGACY + 59)
 
 static const char *prem_sel_clks[] = { "clk32_premult", "clk16m", };
 static const char *clko_sel_clks[] = { "per1", "hclk", "clk48m", "clk16m",
@@ -50,9 +54,9 @@ static void __init _mx1_clocks_init(unsigned long fref)
        clk[IMX1_CLK_CLK16M] = imx_clk_gate("clk16m", "clk16m_ext", CCM_CSCR, 17);
        clk[IMX1_CLK_CLK32_PREMULT] = imx_clk_fixed_factor("clk32_premult", "clk32", 512, 1);
        clk[IMX1_CLK_PREM] = imx_clk_mux("prem", CCM_CSCR, 16, 1, prem_sel_clks, ARRAY_SIZE(prem_sel_clks));
-       clk[IMX1_CLK_MPLL] = imx_clk_pllv1("mpll", "clk32_premult", CCM_MPCTL0);
+       clk[IMX1_CLK_MPLL] = imx_clk_pllv1(IMX_PLLV1_IMX1, "mpll", "clk32_premult", CCM_MPCTL0);
        clk[IMX1_CLK_MPLL_GATE] = imx_clk_gate("mpll_gate", "mpll", CCM_CSCR, 0);
-       clk[IMX1_CLK_SPLL] = imx_clk_pllv1("spll", "prem", CCM_SPCTL0);
+       clk[IMX1_CLK_SPLL] = imx_clk_pllv1(IMX_PLLV1_IMX1, "spll", "prem", CCM_SPCTL0);
        clk[IMX1_CLK_SPLL_GATE] = imx_clk_gate("spll_gate", "spll", CCM_CSCR, 1);
        clk[IMX1_CLK_MCU] = imx_clk_divider("mcu", "clk32_premult", CCM_CSCR, 15, 1);
        clk[IMX1_CLK_FCLK] = imx_clk_divider("fclk", "mpll_gate", CCM_CSCR, 15, 1);
@@ -75,7 +79,8 @@ static void __init _mx1_clocks_init(unsigned long fref)
 
 int __init mx1_clocks_init(unsigned long fref)
 {
-       ccm = MX1_IO_ADDRESS(MX1_CCM_BASE_ADDR);
+       ccm = ioremap(MX1_CCM_BASE_ADDR, SZ_4K);
+       BUG_ON(!ccm);
 
        _mx1_clocks_init(fref);
 
@@ -98,7 +103,7 @@ int __init mx1_clocks_init(unsigned long fref)
        clk_register_clkdev(clk[IMX1_CLK_DUMMY], "ipg", "imx1-fb.0");
        clk_register_clkdev(clk[IMX1_CLK_DUMMY], "ahb", "imx1-fb.0");
 
-       mxc_timer_init(MX1_IO_ADDRESS(MX1_TIM1_BASE_ADDR), MX1_TIM1_INT);
+       mxc_timer_init(MX1_TIM1_BASE_ADDR, MX1_TIM1_INT, GPT_TYPE_IMX1);
 
        return 0;
 }
similarity index 95%
rename from arch/arm/mach-imx/clk-imx21.c
rename to drivers/clk/imx/clk-imx21.c
index 4b4c75339aa674ab0bc3c6acb8f0de97e49bd7a4..dba987e3b89f687c6b48488b385dd781e4122b37 100644 (file)
 #include <linux/of.h>
 #include <linux/of_address.h>
 #include <dt-bindings/clock/imx21-clock.h>
+#include <soc/imx/timer.h>
+#include <asm/irq.h>
 
 #include "clk.h"
-#include "common.h"
-#include "hardware.h"
+
+#define MX21_CCM_BASE_ADDR     0x10027000
+#define MX21_GPT1_BASE_ADDR    0x10003000
+#define MX21_INT_GPT1          (NR_IRQS_LEGACY + 26)
 
 static void __iomem *ccm __initdata;
 
@@ -63,9 +67,9 @@ static void __init _mx21_clocks_init(unsigned long lref, unsigned long href)
        clk[IMX21_CLK_USB_DIV] = imx_clk_divider("usb_div", "spll_gate", CCM_CSCR, 26, 3);
        clk[IMX21_CLK_FCLK] = imx_clk_divider("fclk", "mpll_gate", CCM_CSCR, 29, 3);
 
-       clk[IMX21_CLK_MPLL] = imx_clk_pllv1("mpll", "mpll_sel", CCM_MPCTL0);
+       clk[IMX21_CLK_MPLL] = imx_clk_pllv1(IMX_PLLV1_IMX21, "mpll", "mpll_sel", CCM_MPCTL0);
 
-       clk[IMX21_CLK_SPLL] = imx_clk_pllv1("spll", "spll_sel", CCM_SPCTL0);
+       clk[IMX21_CLK_SPLL] = imx_clk_pllv1(IMX_PLLV1_IMX21, "spll", "spll_sel", CCM_SPCTL0);
 
        clk[IMX21_CLK_NFC_DIV] = imx_clk_divider("nfc_div", "fclk", CCM_PCDR0, 12, 4);
        clk[IMX21_CLK_SSI1_DIV] = imx_clk_divider("ssi1_div", "ssi1_sel", CCM_PCDR0, 16, 6);
@@ -153,7 +157,7 @@ int __init mx21_clocks_init(unsigned long lref, unsigned long href)
        clk_register_clkdev(clk[IMX21_CLK_I2C_GATE], NULL, "imx21-i2c.0");
        clk_register_clkdev(clk[IMX21_CLK_OWIRE_GATE], NULL, "mxc_w1.0");
 
-       mxc_timer_init(MX21_IO_ADDRESS(MX21_GPT1_BASE_ADDR), MX21_INT_GPT1);
+       mxc_timer_init(MX21_GPT1_BASE_ADDR, MX21_INT_GPT1, GPT_TYPE_IMX21);
 
        return 0;
 }
similarity index 98%
rename from arch/arm/mach-imx/clk-imx25.c
rename to drivers/clk/imx/clk-imx25.c
index 9c2633a9de9f0ec53dfdc20677eb709488b7824a..ec1a4c1dacf171d5f79782b68f15ac8b5a567fa2 100644 (file)
@@ -28,8 +28,6 @@
 #include <linux/of_irq.h>
 
 #include "clk.h"
-#include "common.h"
-#include "hardware.h"
 
 #define CCM_MPCTL      0x00
 #define CCM_UPCTL      0x04
@@ -95,8 +93,8 @@ static int __init __mx25_clocks_init(unsigned long osc_rate,
 
        clk[dummy] = imx_clk_fixed("dummy", 0);
        clk[osc] = imx_clk_fixed("osc", osc_rate);
-       clk[mpll] = imx_clk_pllv1("mpll", "osc", ccm(CCM_MPCTL));
-       clk[upll] = imx_clk_pllv1("upll", "osc", ccm(CCM_UPCTL));
+       clk[mpll] = imx_clk_pllv1(IMX_PLLV1_IMX25, "mpll", "osc", ccm(CCM_MPCTL));
+       clk[upll] = imx_clk_pllv1(IMX_PLLV1_IMX25, "upll", "osc", ccm(CCM_UPCTL));
        clk[mpll_cpu_3_4] = imx_clk_fixed_factor("mpll_cpu_3_4", "mpll", 3, 4);
        clk[cpu_sel] = imx_clk_mux("cpu_sel", ccm(CCM_CCTL), 14, 1, cpu_sel_clks, ARRAY_SIZE(cpu_sel_clks));
        clk[cpu] = imx_clk_divider("cpu", "cpu_sel", ccm(CCM_CCTL), 30, 2);
similarity index 97%
rename from arch/arm/mach-imx/clk-imx27.c
rename to drivers/clk/imx/clk-imx27.c
index ab6349ec23b9b87491222b0bdf24e4f977fee6a3..d9d50d54ef2aeaf5853728cb80b14e79847d78ec 100644 (file)
@@ -5,10 +5,15 @@
 #include <linux/of.h>
 #include <linux/of_address.h>
 #include <dt-bindings/clock/imx27-clock.h>
+#include <soc/imx/revision.h>
+#include <soc/imx/timer.h>
+#include <asm/irq.h>
 
 #include "clk.h"
-#include "common.h"
-#include "hardware.h"
+
+#define MX27_CCM_BASE_ADDR     0x10027000
+#define MX27_GPT1_BASE_ADDR    0x10003000
+#define MX27_INT_GPT1          (NR_IRQS_LEGACY + 26)
 
 static void __iomem *ccm __initdata;
 
@@ -54,8 +59,8 @@ static void __init _mx27_clocks_init(unsigned long fref)
        clk[IMX27_CLK_CKIH_GATE] = imx_clk_gate_dis("ckih_gate", "ckih", CCM_CSCR, 3);
        clk[IMX27_CLK_MPLL_OSC_SEL] = imx_clk_mux("mpll_osc_sel", CCM_CSCR, 4, 1, mpll_osc_sel_clks, ARRAY_SIZE(mpll_osc_sel_clks));
        clk[IMX27_CLK_MPLL_SEL] = imx_clk_mux("mpll_sel", CCM_CSCR, 16, 1, mpll_sel_clks, ARRAY_SIZE(mpll_sel_clks));
-       clk[IMX27_CLK_MPLL] = imx_clk_pllv1("mpll", "mpll_sel", CCM_MPCTL0);
-       clk[IMX27_CLK_SPLL] = imx_clk_pllv1("spll", "ckih_gate", CCM_SPCTL0);
+       clk[IMX27_CLK_MPLL] = imx_clk_pllv1(IMX_PLLV1_IMX27, "mpll", "mpll_sel", CCM_MPCTL0);
+       clk[IMX27_CLK_SPLL] = imx_clk_pllv1(IMX_PLLV1_IMX27, "spll", "ckih_gate", CCM_SPCTL0);
        clk[IMX27_CLK_SPLL_GATE] = imx_clk_gate("spll_gate", "spll", CCM_CSCR, 1);
        clk[IMX27_CLK_MPLL_MAIN2] = imx_clk_fixed_factor("mpll_main2", "mpll", 2, 3);
 
@@ -229,7 +234,7 @@ int __init mx27_clocks_init(unsigned long fref)
        clk_register_clkdev(clk[IMX27_CLK_EMMA_AHB_GATE], "ahb", "m2m-emmaprp.0");
        clk_register_clkdev(clk[IMX27_CLK_EMMA_IPG_GATE], "ipg", "m2m-emmaprp.0");
 
-       mxc_timer_init(MX27_IO_ADDRESS(MX27_GPT1_BASE_ADDR), MX27_INT_GPT1);
+       mxc_timer_init(MX27_GPT1_BASE_ADDR, MX27_INT_GPT1, GPT_TYPE_IMX21);
 
        return 0;
 }
similarity index 91%
rename from arch/arm/mach-imx/clk-imx31.c
rename to drivers/clk/imx/clk-imx31.c
index 286ef422cebc9e3624036fdb4931b4bb36b5702e..fe66c40b7be2d205af090bc42cc0346ca7c5d667 100644 (file)
 #include <linux/io.h>
 #include <linux/err.h>
 #include <linux/of.h>
+#include <soc/imx/revision.h>
+#include <soc/imx/timer.h>
+#include <asm/irq.h>
 
 #include "clk.h"
-#include "common.h"
-#include "crmregs-imx3.h"
-#include "hardware.h"
-#include "mx31.h"
+
+#define MX31_CCM_BASE_ADDR     0x53f80000
+#define MX31_GPT1_BASE_ADDR    0x53f90000
+#define MX31_INT_GPT           (NR_IRQS_LEGACY + 29)
+
+#define MXC_CCM_CCMR           0x00
+#define MXC_CCM_PDR0           0x04
+#define MXC_CCM_PDR1           0x08
+#define MXC_CCM_MPCTL          0x10
+#define MXC_CCM_UPCTL          0x14
+#define MXC_CCM_SRPCTL         0x18
+#define MXC_CCM_CGR0           0x20
+#define MXC_CCM_CGR1           0x24
+#define MXC_CCM_CGR2           0x28
+#define MXC_CCM_PMCR0          0x5c
 
 static const char *mcu_main_sel[] = { "spll", "mpll", };
 static const char *per_sel[] = { "per_div", "ipg", };
@@ -50,15 +64,18 @@ static struct clk_onecell_data clk_data;
 
 int __init mx31_clocks_init(unsigned long fref)
 {
-       void __iomem *base = MX31_IO_ADDRESS(MX31_CCM_BASE_ADDR);
+       void __iomem *base;
        struct device_node *np;
 
+       base = ioremap(MX31_CCM_BASE_ADDR, SZ_4K);
+       BUG_ON(!base);
+
        clk[dummy] = imx_clk_fixed("dummy", 0);
        clk[ckih] = imx_clk_fixed("ckih", fref);
        clk[ckil] = imx_clk_fixed("ckil", 32768);
-       clk[mpll] = imx_clk_pllv1("mpll", "ckih", base + MXC_CCM_MPCTL);
-       clk[spll] = imx_clk_pllv1("spll", "ckih", base + MXC_CCM_SRPCTL);
-       clk[upll] = imx_clk_pllv1("upll", "ckih", base + MXC_CCM_UPCTL);
+       clk[mpll] = imx_clk_pllv1(IMX_PLLV1_IMX31, "mpll", "ckih", base + MXC_CCM_MPCTL);
+       clk[spll] = imx_clk_pllv1(IMX_PLLV1_IMX31, "spll", "ckih", base + MXC_CCM_SRPCTL);
+       clk[upll] = imx_clk_pllv1(IMX_PLLV1_IMX31, "upll", "ckih", base + MXC_CCM_UPCTL);
        clk[mcu_main] = imx_clk_mux("mcu_main", base + MXC_CCM_PMCR0, 31, 1, mcu_main_sel, ARRAY_SIZE(mcu_main_sel));
        clk[hsp] = imx_clk_divider("hsp", "mcu_main", base + MXC_CCM_PDR0, 11, 3);
        clk[ahb] = imx_clk_divider("ahb", "mcu_main", base + MXC_CCM_PDR0, 3, 3);
@@ -182,7 +199,7 @@ int __init mx31_clocks_init(unsigned long fref)
        mx31_revision();
        clk_disable_unprepare(clk[iim_gate]);
 
-       mxc_timer_init(MX31_IO_ADDRESS(MX31_GPT1_BASE_ADDR), MX31_INT_GPT);
+       mxc_timer_init(MX31_GPT1_BASE_ADDR, MX31_INT_GPT, GPT_TYPE_IMX31);
 
        return 0;
 }
similarity index 94%
rename from arch/arm/mach-imx/clk-imx35.c
rename to drivers/clk/imx/clk-imx35.c
index a0d2b57fd376e2d6781c618ca82093d90386c9e5..69138ba3dec7056cbba6e32156fa99df1b3e2690 100644 (file)
 #include <linux/clkdev.h>
 #include <linux/of.h>
 #include <linux/err.h>
+#include <soc/imx/revision.h>
+#include <soc/imx/timer.h>
+#include <asm/irq.h>
 
-#include "crmregs-imx3.h"
 #include "clk.h"
-#include "common.h"
-#include "hardware.h"
+
+#define MX35_CCM_BASE_ADDR     0x53f80000
+#define MX35_GPT1_BASE_ADDR    0x53f90000
+#define MX35_INT_GPT           (NR_IRQS_LEGACY + 29)
+
+#define MXC_CCM_PDR0           0x04
+#define MX35_CCM_PDR2          0x0c
+#define MX35_CCM_PDR3          0x10
+#define MX35_CCM_PDR4          0x14
+#define MX35_CCM_MPCTL         0x1c
+#define MX35_CCM_PPCTL         0x20
+#define MX35_CCM_CGR0          0x2c
+#define MX35_CCM_CGR1          0x30
+#define MX35_CCM_CGR2          0x34
+#define MX35_CCM_CGR3          0x38
 
 struct arm_ahb_div {
        unsigned char arm, ahb, sel;
@@ -71,11 +86,14 @@ static struct clk *clk[clk_max];
 
 int __init mx35_clocks_init(void)
 {
-       void __iomem *base = MX35_IO_ADDRESS(MX35_CCM_BASE_ADDR);
+       void __iomem *base;
        u32 pdr0, consumer_sel, hsp_sel;
        struct arm_ahb_div *aad;
        unsigned char *hsp_div;
 
+       base = ioremap(MX35_CCM_BASE_ADDR, SZ_4K);
+       BUG_ON(!base);
+
        pdr0 = __raw_readl(base + MXC_CCM_PDR0);
        consumer_sel = (pdr0 >> 16) & 0xf;
        aad = &clk_consumer[consumer_sel];
@@ -89,8 +107,8 @@ int __init mx35_clocks_init(void)
        }
 
        clk[ckih] = imx_clk_fixed("ckih", 24000000);
-       clk[mpll] = imx_clk_pllv1("mpll", "ckih", base + MX35_CCM_MPCTL);
-       clk[ppll] = imx_clk_pllv1("ppll", "ckih", base + MX35_CCM_PPCTL);
+       clk[mpll] = imx_clk_pllv1(IMX_PLLV1_IMX35, "mpll", "ckih", base + MX35_CCM_MPCTL);
+       clk[ppll] = imx_clk_pllv1(IMX_PLLV1_IMX35, "ppll", "ckih", base + MX35_CCM_PPCTL);
 
        clk[mpll] = imx_clk_fixed_factor("mpll_075", "mpll", 3, 4);
 
@@ -276,11 +294,7 @@ int __init mx35_clocks_init(void)
 
        imx_print_silicon_rev("i.MX35", mx35_revision());
 
-#ifdef CONFIG_MXC_USE_EPIT
-       epit_timer_init(MX35_IO_ADDRESS(MX35_EPIT1_BASE_ADDR), MX35_INT_EPIT1);
-#else
-       mxc_timer_init(MX35_IO_ADDRESS(MX35_GPT1_BASE_ADDR), MX35_INT_GPT);
-#endif
+       mxc_timer_init(MX35_GPT1_BASE_ADDR, MX35_INT_GPT, GPT_TYPE_IMX31);
 
        return 0;
 }
similarity index 99%
rename from arch/arm/mach-imx/clk-imx51-imx53.c
rename to drivers/clk/imx/clk-imx51-imx53.c
index 0f7e536147cb09d3d86783bb30550b931d971a22..a7e4f394be0d1e6972a4d8fb75f6ce00d948ab5c 100644 (file)
 #include <linux/of.h>
 #include <linux/of_address.h>
 #include <linux/of_irq.h>
+#include <soc/imx/revision.h>
 #include <dt-bindings/clock/imx5-clock.h>
 
 #include "clk.h"
-#include "common.h"
-#include "hardware.h"
 
 #define MX51_DPLL1_BASE                0x83f80000
 #define MX51_DPLL2_BASE                0x83f84000
@@ -133,8 +132,6 @@ static struct clk_onecell_data clk_data;
 
 static void __init mx5_clocks_common_init(void __iomem *ccm_base)
 {
-       imx5_pm_set_ccm_base(ccm_base);
-
        clk[IMX5_CLK_DUMMY]             = imx_clk_fixed("dummy", 0);
        clk[IMX5_CLK_CKIL]              = imx_obtain_fixed_clock("ckil", 0);
        clk[IMX5_CLK_OSC]               = imx_obtain_fixed_clock("osc", 0);
similarity index 98%
rename from arch/arm/mach-imx/clk-imx6q.c
rename to drivers/clk/imx/clk-imx6q.c
index 469a150bf98f98cbb5521343e81d531c7fc34e91..d046f8e43de8d056d1af2cb1ae4bd790019d2d9a 100644 (file)
 #include <linux/of.h>
 #include <linux/of_address.h>
 #include <linux/of_irq.h>
+#include <soc/imx/revision.h>
 #include <dt-bindings/clock/imx6qdl-clock.h>
 
 #include "clk.h"
-#include "common.h"
-#include "hardware.h"
 
 static const char *step_sels[] = { "osc", "pll2_pfd2_396m", };
 static const char *pll1_sw_sels[]      = { "pll1_sys", "step", };
@@ -121,6 +120,16 @@ static unsigned int share_count_ssi2;
 static unsigned int share_count_ssi3;
 static unsigned int share_count_mipi_core_cfg;
 
+static inline int clk_on_imx6q(void)
+{
+       return of_machine_is_compatible("fsl,imx6q");
+}
+
+static inline int clk_on_imx6dl(void)
+{
+       return of_machine_is_compatible("fsl,imx6dl");
+}
+
 static void __init imx6q_clocks_init(struct device_node *ccm_node)
 {
        struct device_node *np;
@@ -141,7 +150,7 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
        WARN_ON(!base);
 
        /* Audio/video PLL post dividers do not work on i.MX6q revision 1.0 */
-       if (cpu_is_imx6q() && imx_get_soc_revision() == IMX_CHIP_REVISION_1_0) {
+       if (clk_on_imx6q() && imx_get_soc_revision() == IMX_CHIP_REVISION_1_0) {
                post_div_table[1].div = 1;
                post_div_table[2].div = 1;
                video_div_table[1].div = 1;
@@ -248,7 +257,7 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
        clk[IMX6QDL_CLK_TWD]       = imx_clk_fixed_factor("twd",       "arm",            1, 2);
        clk[IMX6QDL_CLK_GPT_3M]    = imx_clk_fixed_factor("gpt_3m",    "osc",            1, 8);
        clk[IMX6QDL_CLK_VIDEO_27M] = imx_clk_fixed_factor("video_27m", "pll3_pfd1_540m", 1, 20);
-       if (cpu_is_imx6dl()) {
+       if (clk_on_imx6dl()) {
                clk[IMX6QDL_CLK_GPU2D_AXI] = imx_clk_fixed_factor("gpu2d_axi", "mmdc_ch0_axi_podf", 1, 1);
                clk[IMX6QDL_CLK_GPU3D_AXI] = imx_clk_fixed_factor("gpu3d_axi", "mmdc_ch0_axi_podf", 1, 1);
        }
@@ -262,8 +271,6 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
        base = of_iomap(np, 0);
        WARN_ON(!base);
 
-       imx6q_pm_set_ccm_base(base);
-
        /*                                              name                reg       shift width parent_names     num_parents */
        clk[IMX6QDL_CLK_STEP]             = imx_clk_mux("step",             base + 0xc,  8,  1, step_sels,         ARRAY_SIZE(step_sels));
        clk[IMX6QDL_CLK_PLL1_SW]          = imx_clk_mux("pll1_sw",          base + 0xc,  2,  1, pll1_sw_sels,      ARRAY_SIZE(pll1_sw_sels));
@@ -275,7 +282,7 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
        clk[IMX6QDL_CLK_ESAI_SEL]         = imx_clk_mux("esai_sel",         base + 0x20, 19, 2, audio_sels,        ARRAY_SIZE(audio_sels));
        clk[IMX6QDL_CLK_ASRC_SEL]         = imx_clk_mux("asrc_sel",         base + 0x30, 7,  2, audio_sels,        ARRAY_SIZE(audio_sels));
        clk[IMX6QDL_CLK_SPDIF_SEL]        = imx_clk_mux("spdif_sel",        base + 0x30, 20, 2, audio_sels,        ARRAY_SIZE(audio_sels));
-       if (cpu_is_imx6q()) {
+       if (clk_on_imx6q()) {
                clk[IMX6QDL_CLK_GPU2D_AXI]        = imx_clk_mux("gpu2d_axi",        base + 0x18, 0,  1, gpu_axi_sels,      ARRAY_SIZE(gpu_axi_sels));
                clk[IMX6QDL_CLK_GPU3D_AXI]        = imx_clk_mux("gpu3d_axi",        base + 0x18, 1,  1, gpu_axi_sels,      ARRAY_SIZE(gpu_axi_sels));
        }
@@ -382,7 +389,7 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
        clk[IMX6QDL_CLK_ECSPI2]       = imx_clk_gate2("ecspi2",        "ecspi_root",        base + 0x6c, 2);
        clk[IMX6QDL_CLK_ECSPI3]       = imx_clk_gate2("ecspi3",        "ecspi_root",        base + 0x6c, 4);
        clk[IMX6QDL_CLK_ECSPI4]       = imx_clk_gate2("ecspi4",        "ecspi_root",        base + 0x6c, 6);
-       if (cpu_is_imx6dl())
+       if (clk_on_imx6dl())
                clk[IMX6DL_CLK_I2C4]  = imx_clk_gate2("i2c4",          "ipg_per",           base + 0x6c, 8);
        else
                clk[IMX6Q_CLK_ECSPI5] = imx_clk_gate2("ecspi5",        "ecspi_root",        base + 0x6c, 8);
@@ -392,7 +399,7 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
        clk[IMX6QDL_CLK_ESAI_MEM]     = imx_clk_gate2_shared("esai_mem", "ahb",             base + 0x6c, 16, &share_count_esai);
        clk[IMX6QDL_CLK_GPT_IPG]      = imx_clk_gate2("gpt_ipg",       "ipg",               base + 0x6c, 20);
        clk[IMX6QDL_CLK_GPT_IPG_PER]  = imx_clk_gate2("gpt_ipg_per",   "ipg_per",           base + 0x6c, 22);
-       if (cpu_is_imx6dl())
+       if (clk_on_imx6dl())
                /*
                 * The multiplexer and divider of imx6q clock gpu3d_shader get
                 * redefined/reused as gpu2d_core_sel and gpu2d_core_podf on imx6dl.
@@ -420,7 +427,7 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
        clk[IMX6QDL_CLK_HSI_TX]       = imx_clk_gate2_shared("hsi_tx", "hsi_tx_podf",       base + 0x74, 16, &share_count_mipi_core_cfg);
        clk[IMX6QDL_CLK_MIPI_CORE_CFG] = imx_clk_gate2_shared("mipi_core_cfg", "video_27m", base + 0x74, 16, &share_count_mipi_core_cfg);
        clk[IMX6QDL_CLK_MIPI_IPG]     = imx_clk_gate2_shared("mipi_ipg", "ipg",             base + 0x74, 16, &share_count_mipi_core_cfg);
-       if (cpu_is_imx6dl())
+       if (clk_on_imx6dl())
                /*
                 * The multiplexer and divider of the imx6q clock gpu2d get
                 * redefined/reused as mlb_sys_sel and mlb_sys_clk_podf on imx6dl.
@@ -443,7 +450,7 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
        clk[IMX6QDL_CLK_GPMI_IO]      = imx_clk_gate2("gpmi_io",       "enfc",              base + 0x78, 28);
        clk[IMX6QDL_CLK_GPMI_APB]     = imx_clk_gate2("gpmi_apb",      "usdhc3",            base + 0x78, 30);
        clk[IMX6QDL_CLK_ROM]          = imx_clk_gate2("rom",           "ahb",               base + 0x7c, 0);
-       clk[IMX6QDL_CLK_SATA]         = imx_clk_gate2("sata",          "ipg",               base + 0x7c, 4);
+       clk[IMX6QDL_CLK_SATA]         = imx_clk_gate2("sata",          "ahb",               base + 0x7c, 4);
        clk[IMX6QDL_CLK_SDMA]         = imx_clk_gate2("sdma",          "ahb",               base + 0x7c, 6);
        clk[IMX6QDL_CLK_SPBA]         = imx_clk_gate2("spba",          "ipg",               base + 0x7c, 12);
        clk[IMX6QDL_CLK_SPDIF]        = imx_clk_gate2("spdif",         "spdif_podf",        base + 0x7c, 14);
@@ -470,7 +477,7 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
         * The gpt_3m clock is not available on i.MX6Q TO1.0.  Let's point it
         * to clock gpt_ipg_per to ease the gpt driver code.
         */
-       if (cpu_is_imx6q() && imx_get_soc_revision() == IMX_CHIP_REVISION_1_0)
+       if (clk_on_imx6q() && imx_get_soc_revision() == IMX_CHIP_REVISION_1_0)
                clk[IMX6QDL_CLK_GPT_3M] = clk[IMX6QDL_CLK_GPT_IPG_PER];
 
        imx_check_clocks(clk, ARRAY_SIZE(clk));
@@ -482,7 +489,7 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
        clk_register_clkdev(clk[IMX6QDL_CLK_ENET_REF], "enet_ref", NULL);
 
        if ((imx_get_soc_revision() != IMX_CHIP_REVISION_1_0) ||
-           cpu_is_imx6dl()) {
+           clk_on_imx6dl()) {
                clk_set_parent(clk[IMX6QDL_CLK_LDB_DI0_SEL], clk[IMX6QDL_CLK_PLL5_VIDEO_DIV]);
                clk_set_parent(clk[IMX6QDL_CLK_LDB_DI1_SEL], clk[IMX6QDL_CLK_PLL5_VIDEO_DIV]);
        }
@@ -527,8 +534,5 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
        /* All existing boards with PCIe use LVDS1 */
        if (IS_ENABLED(CONFIG_PCI_IMX6))
                clk_set_parent(clk[IMX6QDL_CLK_LVDS1_SEL], clk[IMX6QDL_CLK_SATA_REF_100M]);
-
-       /* Set initial power mode */
-       imx6q_set_lpm(WAIT_CLOCKED);
 }
 CLK_OF_DECLARE(imx6q, "fsl,imx6q-ccm", imx6q_clocks_init);
similarity index 99%
rename from arch/arm/mach-imx/clk-imx6sl.c
rename to drivers/clk/imx/clk-imx6sl.c
index e982ebe1081410037824999565264044bab9e281..a0d4cf26cfa932831c21c1a0b75447a75609a0ff 100644 (file)
@@ -16,7 +16,6 @@
 #include <dt-bindings/clock/imx6sl-clock.h>
 
 #include "clk.h"
-#include "common.h"
 
 #define CCSR                   0xc
 #define BM_CCSR_PLL1_SW_CLK_SEL        (1 << 2)
@@ -288,9 +287,6 @@ static void __init imx6sl_clocks_init(struct device_node *ccm_node)
        WARN_ON(!base);
        ccm_base = base;
 
-       /* Reuse imx6q pm code */
-       imx6q_pm_set_ccm_base(base);
-
        /*                                              name                reg       shift width parent_names     num_parents */
        clks[IMX6SL_CLK_STEP]             = imx_clk_mux("step",             base + 0xc,  8,  1, step_sels,         ARRAY_SIZE(step_sels));
        clks[IMX6SL_CLK_PLL1_SW]          = imx_clk_mux("pll1_sw",          base + 0xc,  2,  1, pll1_sw_sels,      ARRAY_SIZE(pll1_sw_sels));
@@ -443,8 +439,5 @@ static void __init imx6sl_clocks_init(struct device_node *ccm_node)
 
        clk_set_parent(clks[IMX6SL_CLK_LCDIF_AXI_SEL],
                       clks[IMX6SL_CLK_PLL2_PFD2]);
-
-       /* Set initial power mode */
-       imx6q_set_lpm(WAIT_CLOCKED);
 }
 CLK_OF_DECLARE(imx6sl, "fsl,imx6sl-ccm", imx6sl_clocks_init);
similarity index 99%
rename from arch/arm/mach-imx/clk-imx6sx.c
rename to drivers/clk/imx/clk-imx6sx.c
index 87c5b0911dddc38ab2b0929d256aec17d1361b05..5b95c2c2bf529e85a86b7cab4360731eeda78a36 100644 (file)
@@ -21,7 +21,6 @@
 #include <linux/types.h>
 
 #include "clk.h"
-#include "common.h"
 
 #define CCDR    0x4
 #define BM_CCM_CCDR_MMDC_CH0_MASK       (0x2 << 16)
@@ -268,8 +267,6 @@ static void __init imx6sx_clocks_init(struct device_node *ccm_node)
        base = of_iomap(np, 0);
        WARN_ON(!base);
 
-       imx6q_pm_set_ccm_base(base);
-
        /*                                                name                reg           shift   width   parent_names       num_parents */
        clks[IMX6SX_CLK_STEP]               = imx_clk_mux("step",             base + 0xc,   8,      1,      step_sels,         ARRAY_SIZE(step_sels));
        clks[IMX6SX_CLK_PLL1_SW]            = imx_clk_mux("pll1_sw",          base + 0xc,   2,      1,      pll1_sw_sels,      ARRAY_SIZE(pll1_sw_sels));
@@ -560,8 +557,5 @@ static void __init imx6sx_clocks_init(struct device_node *ccm_node)
 
        clk_set_parent(clks[IMX6SX_CLK_QSPI1_SEL], clks[IMX6SX_CLK_PLL2_BUS]);
        clk_set_parent(clks[IMX6SX_CLK_QSPI2_SEL], clks[IMX6SX_CLK_PLL2_BUS]);
-
-       /* Set initial power mode */
-       imx6q_set_lpm(WAIT_CLOCKED);
 }
 CLK_OF_DECLARE(imx6sx, "fsl,imx6sx-ccm", imx6sx_clocks_init);
diff --git a/drivers/clk/imx/clk-imx7d.c b/drivers/clk/imx/clk-imx7d.c
new file mode 100644 (file)
index 0000000..71f3a94
--- /dev/null
@@ -0,0 +1,860 @@
+/*
+ * Copyright (C) 2014-2015 Freescale Semiconductor, Inc.
+ *
+ * The code contained herein is licensed under the GNU General Public
+ * License. You may obtain a copy of the GNU General Public License
+ * Version 2 or later at the following locations:
+ *
+ * http://www.opensource.org/licenses/gpl-license.html
+ * http://www.gnu.org/copyleft/gpl.html
+ */
+
+#include <dt-bindings/clock/imx7d-clock.h>
+#include <linux/clk.h>
+#include <linux/clkdev.h>
+#include <linux/err.h>
+#include <linux/init.h>
+#include <linux/io.h>
+#include <linux/of.h>
+#include <linux/of_address.h>
+#include <linux/of_irq.h>
+#include <linux/types.h>
+
+#include "clk.h"
+
+static struct clk *clks[IMX7D_CLK_END];
+static const char *arm_a7_sel[] = { "osc", "pll_arm_main_clk",
+       "pll_enet_500m_clk", "pll_dram_main_clk",
+       "pll_sys_main_clk", "pll_sys_pfd0_392m_clk", "pll_audio_main_clk",
+       "pll_usb_main_clk", };
+
+static const char *arm_m4_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_250m_clk", "pll_sys_pfd2_270m_clk",
+       "pll_dram_533m_clk", "pll_audio_main_clk", "pll_video_main_clk",
+       "pll_usb_main_clk", };
+
+static const char *arm_m0_sel[] = { "osc", "pll_sys_main_120m_clk",
+       "pll_enet_125m_clk", "pll_sys_pfd2_135m_clk",
+       "pll_dram_533m_clk", "pll_audio_main_clk", "pll_video_main_clk",
+       "pll_usb_main_clk", };
+
+static const char *axi_sel[] = { "osc", "pll_sys_pfd1_332m_clk",
+       "pll_dram_533m_clk", "pll_enet_250m_clk", "pll_sys_pfd5_clk",
+       "pll_audio_main_clk", "pll_video_main_clk", "pll_sys_pfd7_clk", };
+
+static const char *disp_axi_sel[] = { "osc", "pll_sys_pfd1_332m_clk",
+       "pll_dram_533m_clk", "pll_enet_250m_clk", "pll_sys_pfd6_clk",
+       "pll_sys_pfd7_clk", "pll_audio_main_clk", "pll_video_main_clk", };
+
+static const char *enet_axi_sel[] = { "osc", "pll_sys_pfd2_270m_clk",
+       "pll_dram_533m_clk", "pll_enet_250m_clk",
+       "pll_sys_main_240m_clk", "pll_audio_main_clk", "pll_video_main_clk",
+       "pll_sys_pfd4_clk", };
+
+static const char *nand_usdhc_bus_sel[] = { "osc", "pll_sys_pfd2_270m_clk",
+       "pll_dram_533m_clk", "pll_sys_main_240m_clk",
+       "pll_sys_pfd2_135m_clk", "pll_sys_pfd6_clk", "pll_enet_250m_clk",
+       "pll_audio_main_clk", };
+
+static const char *ahb_channel_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_dram_533m_clk", "pll_sys_pfd0_392m_clk",
+       "pll_enet_125m_clk", "pll_usb_main_clk", "pll_audio_main_clk",
+       "pll_video_main_clk", };
+
+static const char *dram_phym_sel[] = { "pll_dram_main_clk",
+       "dram_phym_alt_clk", };
+
+static const char *dram_sel[] = { "pll_dram_main_clk",
+       "dram_alt_clk", };
+
+static const char *dram_phym_alt_sel[] = { "osc", "pll_dram_533m_clk",
+       "pll_sys_main_clk", "pll_enet_500m_clk",
+       "pll_usb_main_clk", "pll_sys_pfd7_clk", "pll_audio_main_clk",
+       "pll_video_main_clk", };
+
+static const char *dram_alt_sel[] = { "osc", "pll_dram_533m_clk",
+       "pll_sys_main_clk", "pll_enet_500m_clk",
+       "pll_enet_250m_clk", "pll_sys_pfd0_392m_clk",
+       "pll_audio_main_clk", "pll_sys_pfd2_270m_clk", };
+
+static const char *usb_hsic_sel[] = { "osc", "pll_sys_main_clk",
+       "pll_usb_main_clk", "pll_sys_pfd3_clk", "pll_sys_pfd4_clk",
+       "pll_sys_pfd5_clk", "pll_sys_pfd6_clk", "pll_sys_pfd7_clk", };
+
+static const char *pcie_ctrl_sel[] = { "osc", "pll_enet_250m_clk",
+       "pll_sys_main_240m_clk", "pll_sys_pfd2_270m_clk",
+       "pll_dram_533m_clk", "pll_enet_500m_clk",
+       "pll_sys_pfd1_332m_clk", "pll_sys_pfd6_clk", };
+
+static const char *pcie_phy_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_enet_500m_clk", "ext_clk_1", "ext_clk_2", "ext_clk_3",
+       "ext_clk_4", "pll_sys_pfd0_392m_clk", };
+
+static const char *epdc_pixel_sel[] = { "osc", "pll_sys_pfd1_332m_clk",
+       "pll_dram_533m_clk", "pll_sys_main_clk", "pll_sys_pfd5_clk",
+       "pll_sys_pfd6_clk", "pll_sys_pfd7_clk", "pll_video_main_clk", };
+
+static const char *lcdif_pixel_sel[] = { "osc", "pll_sys_pfd5_clk",
+       "pll_dram_533m_clk", "ext_clk_3", "pll_sys_pfd4_clk",
+       "pll_sys_pfd2_270m_clk", "pll_video_main_clk",
+       "pll_usb_main_clk", };
+
+static const char *mipi_dsi_sel[] = { "osc", "pll_sys_pfd5_clk",
+       "pll_sys_pfd3_clk", "pll_sys_main_clk", "pll_sys_pfd0_196m_clk",
+       "pll_dram_533m_clk", "pll_video_main_clk", "pll_audio_main_clk", };
+
+static const char *mipi_csi_sel[] = { "osc", "pll_sys_pfd4_clk",
+       "pll_sys_pfd3_clk", "pll_sys_main_clk", "pll_sys_pfd0_196m_clk",
+       "pll_dram_533m_clk", "pll_video_main_clk", "pll_audio_main_clk", };
+
+static const char *mipi_dphy_sel[] = { "osc", "pll_sys_main_120m_clk",
+       "pll_dram_533m_clk", "pll_sys_pfd5_clk", "ref_1m_clk", "ext_clk_2",
+       "pll_video_main_clk", "ext_clk_3", };
+
+static const char *sai1_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_audio_main_clk", "pll_dram_533m_clk", "pll_video_main_clk",
+       "pll_sys_pfd4_clk", "pll_enet_125m_clk", "ext_clk_2", };
+
+static const char *sai2_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_audio_main_clk", "pll_dram_533m_clk", "pll_video_main_clk",
+       "pll_sys_pfd4_clk", "pll_enet_125m_clk", "ext_clk_2", };
+
+static const char *sai3_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_audio_main_clk", "pll_dram_533m_clk", "pll_video_main_clk",
+       "pll_sys_pfd4_clk", "pll_enet_125m_clk", "ext_clk_3", };
+
+static const char *spdif_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_audio_main_clk", "pll_dram_533m_clk", "pll_video_main_clk",
+       "pll_sys_pfd4_clk", "pll_enet_125m_clk", "ext_3_clk", };
+
+static const char *enet1_ref_sel[] = { "osc", "pll_enet_125m_clk",
+       "pll_enet_50m_clk", "pll_enet_25m_clk",
+       "pll_sys_main_120m_clk", "pll_audio_main_clk", "pll_video_main_clk",
+       "ext_clk_4", };
+
+static const char *enet1_time_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_audio_main_clk", "ext_clk_1", "ext_clk_2", "ext_clk_3",
+       "ext_clk_4", "pll_video_main_clk", };
+
+static const char *enet2_ref_sel[] = { "osc", "pll_enet_125m_clk",
+       "pll_enet_50m_clk", "pll_enet_25m_clk",
+       "pll_sys_main_120m_clk", "pll_audio_main_clk", "pll_video_main_clk",
+       "ext_clk_4", };
+
+static const char *enet2_time_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_audio_main_clk", "ext_clk_1", "ext_clk_2", "ext_clk_3",
+       "ext_clk_4", "pll_video_main_clk", };
+
+static const char *enet_phy_ref_sel[] = { "osc", "pll_enet_25m_clk",
+       "pll_enet_50m_clk", "pll_enet_125m_clk",
+       "pll_dram_533m_clk", "pll_audio_main_clk", "pll_video_main_clk",
+       "pll_sys_pfd3_clk", };
+
+static const char *eim_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_sys_main_120m_clk", "pll_dram_533m_clk",
+       "pll_sys_pfd2_270m_clk", "pll_sys_pfd3_clk", "pll_enet_125m_clk",
+       "pll_usb_main_clk", };
+
+static const char *nand_sel[] = { "osc", "pll_sys_main_clk",
+       "pll_dram_533m_clk", "pll_sys_pfd0_392m_clk", "pll_sys_pfd3_clk",
+       "pll_enet_500m_clk", "pll_enet_250m_clk",
+       "pll_video_main_clk", };
+
+static const char *qspi_sel[] = { "osc", "pll_sys_pfd4_clk",
+       "pll_dram_533m_clk", "pll_enet_500m_clk", "pll_sys_pfd3_clk",
+       "pll_sys_pfd2_270m_clk", "pll_sys_pfd6_clk", "pll_sys_pfd7_clk", };
+
+static const char *usdhc1_sel[] = { "osc", "pll_sys_pfd0_392m_clk",
+       "pll_dram_533m_clk", "pll_enet_500m_clk", "pll_sys_pfd4_clk",
+       "pll_sys_pfd2_270m_clk", "pll_sys_pfd6_clk", "pll_sys_pfd7_clk", };
+
+static const char *usdhc2_sel[] = { "osc", "pll_sys_pfd0_392m_clk",
+       "pll_dram_533m_clk", "pll_enet_500m_clk", "pll_sys_pfd4_clk",
+       "pll_sys_pfd2_270m_clk", "pll_sys_pfd6_clk", "pll_sys_pfd7_clk", };
+
+static const char *usdhc3_sel[] = { "osc", "pll_sys_pfd0_392m_clk",
+       "pll_dram_533m_clk", "pll_enet_500m_clk", "pll_sys_pfd4_clk",
+       "pll_sys_pfd2_270m_clk", "pll_sys_pfd6_clk", "pll_sys_pfd7_clk", };
+
+static const char *can1_sel[] = { "osc", "pll_sys_main_120m_clk",
+       "pll_dram_533m_clk", "pll_sys_main_clk",
+       "pll_enet_40m_clk", "pll_usb_main_clk", "ext_clk_1",
+       "ext_clk_4", };
+
+static const char *can2_sel[] = { "osc", "pll_sys_main_120m_clk",
+       "pll_dram_533m_clk", "pll_sys_main_clk",
+       "pll_enet_40m_clk", "pll_usb_main_clk", "ext_clk_1",
+       "ext_clk_3", };
+
+static const char *i2c1_sel[] = { "osc", "pll_sys_main_120m_clk",
+       "pll_enet_50m_clk", "pll_dram_533m_clk",
+       "pll_audio_main_clk", "pll_video_main_clk", "pll_usb_main_clk",
+       "pll_sys_pfd2_135m_clk", };
+
+static const char *i2c2_sel[] = { "osc", "pll_sys_main_120m_clk",
+       "pll_enet_50m_clk", "pll_dram_533m_clk",
+       "pll_audio_main_clk", "pll_video_main_clk", "pll_usb_main_clk",
+       "pll_sys_pfd2_135m_clk", };
+
+static const char *i2c3_sel[] = { "osc", "pll_sys_main_120m_clk",
+       "pll_enet_50m_clk", "pll_dram_533m_clk",
+       "pll_audio_main_clk", "pll_video_main_clk", "pll_usb_main_clk",
+       "pll_sys_pfd2_135m_clk", };
+
+static const char *i2c4_sel[] = { "osc", "pll_sys_main_120m_clk",
+       "pll_enet_50m_clk", "pll_dram_533m_clk",
+       "pll_audio_main_clk", "pll_video_main_clk", "pll_usb_main_clk",
+       "pll_sys_pfd2_135m_clk", };
+
+static const char *uart1_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_enet_100m_clk",
+       "pll_sys_main_clk", "ext_clk_2", "ext_clk_4",
+       "pll_usb_main_clk", };
+
+static const char *uart2_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_enet_100m_clk",
+       "pll_sys_main_clk", "ext_clk_2", "ext_clk_3",
+       "pll_usb_main_clk", };
+
+static const char *uart3_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_enet_100m_clk",
+       "pll_sys_main_clk", "ext_clk_2", "ext_clk_4",
+       "pll_usb_main_clk", };
+
+static const char *uart4_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_enet_100m_clk",
+       "pll_sys_main_clk", "ext_clk_2", "ext_clk_3",
+       "pll_usb_main_clk", };
+
+static const char *uart5_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_enet_100m_clk",
+       "pll_sys_main_clk", "ext_clk_2", "ext_clk_4",
+       "pll_usb_main_clk", };
+
+static const char *uart6_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_enet_100m_clk",
+       "pll_sys_main_clk", "ext_clk_2", "ext_clk_3",
+       "pll_usb_main_clk", };
+
+static const char *uart7_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_enet_100m_clk",
+       "pll_sys_main_clk", "ext_clk_2", "ext_clk_4",
+       "pll_usb_main_clk", };
+
+static const char *ecspi1_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_sys_main_120m_clk",
+       "pll_sys_main_clk", "pll_sys_pfd4_clk", "pll_enet_250m_clk",
+       "pll_usb_main_clk", };
+
+static const char *ecspi2_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_sys_main_120m_clk",
+       "pll_sys_main_clk", "pll_sys_pfd4_clk", "pll_enet_250m_clk",
+       "pll_usb_main_clk", };
+
+static const char *ecspi3_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_sys_main_120m_clk",
+       "pll_sys_main_clk", "pll_sys_pfd4_clk", "pll_enet_250m_clk",
+       "pll_usb_main_clk", };
+
+static const char *ecspi4_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_enet_40m_clk", "pll_sys_main_120m_clk",
+       "pll_sys_main_clk", "pll_sys_pfd4_clk", "pll_enet_250m_clk",
+       "pll_usb_main_clk", };
+
+static const char *pwm1_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_sys_main_120m_clk", "pll_enet_40m_clk", "pll_audio_main_clk",
+       "ext_clk_1", "ref_1m_clk", "pll_video_main_clk", };
+
+static const char *pwm2_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_sys_main_120m_clk", "pll_enet_40m_clk", "pll_audio_main_clk",
+       "ext_clk_1", "ref_1m_clk", "pll_video_main_clk", };
+
+static const char *pwm3_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_sys_main_120m_clk", "pll_enet_40m_clk", "pll_audio_main_clk",
+       "ext_clk_2", "ref_1m_clk", "pll_video_main_clk", };
+
+static const char *pwm4_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_sys_main_120m_clk", "pll_enet_40m_clk", "pll_audio_main_clk",
+       "ext_clk_2", "ref_1m_clk", "pll_video_main_clk", };
+
+static const char *flextimer1_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_sys_main_120m_clk", "pll_enet_40m_clk", "pll_audio_main_clk",
+       "ext_clk_3", "ref_1m_clk", "pll_video_main_clk", };
+
+static const char *flextimer2_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_sys_main_120m_clk", "pll_enet_40m_clk", "pll_audio_main_clk",
+       "ext_clk_3", "ref_1m_clk", "pll_video_main_clk", };
+
+static const char *sim1_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_sys_main_120m_clk", "pll_dram_533m_clk",
+       "pll_usb_main_clk", "pll_audio_main_clk", "pll_enet_125m_clk",
+       "pll_sys_pfd7_clk", };
+
+static const char *sim2_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_sys_main_120m_clk", "pll_dram_533m_clk",
+       "pll_usb_main_clk", "pll_video_main_clk", "pll_enet_125m_clk",
+       "pll_sys_pfd7_clk", };
+
+static const char *gpt1_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_sys_pfd0_392m_clk", "pll_enet_40m_clk", "pll_video_main_clk",
+       "ref_1m_clk", "pll_audio_main_clk", "ext_clk_1", };
+
+static const char *gpt2_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_sys_pfd0_392m_clk", "pll_enet_40m_clk", "pll_video_main_clk",
+       "ref_1m_clk", "pll_audio_main_clk", "ext_clk_2", };
+
+static const char *gpt3_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_sys_pfd0_392m_clk", "pll_enet_40m_clk", "pll_video_main_clk",
+       "ref_1m_clk", "pll_audio_main_clk", "ext_clk_3", };
+
+static const char *gpt4_sel[] = { "osc", "pll_enet_100m_clk",
+       "pll_sys_pfd0_392m_clk", "pll_enet_40m_clk", "pll_video_main_clk",
+       "ref_1m_clk", "pll_audio_main_clk", "ext_clk_4", };
+
+static const char *trace_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_sys_main_120m_clk", "pll_dram_533m_clk",
+       "pll_enet_125m_clk", "pll_usb_main_clk", "ext_clk_2",
+       "ext_clk_3", };
+
+static const char *wdog_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_sys_main_120m_clk", "pll_dram_533m_clk",
+       "pll_enet_125m_clk", "pll_usb_main_clk", "ref_1m_clk",
+       "pll_sys_pfd1_166m_clk", };
+
+static const char *csi_mclk_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_sys_main_120m_clk", "pll_dram_533m_clk",
+       "pll_enet_125m_clk", "pll_audio_main_clk", "pll_video_main_clk",
+       "pll_usb_main_clk", };
+
+static const char *audio_mclk_sel[] = { "osc", "pll_sys_pfd2_135m_clk",
+       "pll_sys_main_120m_clk", "pll_dram_533m_clk",
+       "pll_enet_125m_clk", "pll_audio_main_clk", "pll_video_main_clk",
+       "pll_usb_main_clk", };
+
+static const char *wrclk_sel[] = { "osc", "pll_enet_40m_clk",
+       "pll_dram_533m_clk", "pll_usb_main_clk",
+       "pll_sys_main_240m_clk", "pll_sys_pfd2_270m_clk",
+       "pll_enet_500m_clk", "pll_sys_pfd7_clk", };
+
+static const char *clko1_sel[] = { "osc", "pll_sys_main_clk",
+       "pll_sys_main_240m_clk", "pll_sys_pfd0_196m_clk", "pll_sys_pfd3_clk",
+       "pll_enet_500m_clk", "pll_dram_533m_clk", "ref_1m_clk", };
+
+static const char *clko2_sel[] = { "osc", "pll_sys_main_240m_clk",
+       "pll_sys_pfd0_392m_clk", "pll_sys_pfd1_166m_clk", "pll_sys_pfd4_clk",
+       "pll_audio_main_clk", "pll_video_main_clk", "osc_32k_clk", };
+
+static const char *lvds1_sel[] = { "pll_arm_main_clk",
+       "pll_sys_main_clk", "pll_sys_pfd0_392m_clk", "pll_sys_pfd1_332m_clk",
+       "pll_sys_pfd2_270m_clk", "pll_sys_pfd3_clk", "pll_sys_pfd4_clk",
+       "pll_sys_pfd5_clk", "pll_sys_pfd6_clk", "pll_sys_pfd7_clk",
+       "pll_audio_main_clk", "pll_video_main_clk", "pll_enet_500m_clk",
+       "pll_enet_250m_clk", "pll_enet_125m_clk", "pll_enet_100m_clk",
+       "pll_enet_50m_clk", "pll_enet_40m_clk", "pll_enet_25m_clk",
+       "pll_dram_main_clk", };
+
+static const char *pll_bypass_src_sel[] = { "osc", "dummy", };
+static const char *pll_arm_bypass_sel[] = { "pll_arm_main", "pll_arm_main_src", };
+static const char *pll_dram_bypass_sel[] = { "pll_dram_main", "pll_dram_main_src", };
+static const char *pll_sys_bypass_sel[] = { "pll_sys_main", "pll_sys_main_src", };
+static const char *pll_enet_bypass_sel[] = { "pll_enet_main", "pll_enet_main_src", };
+static const char *pll_audio_bypass_sel[] = { "pll_audio_main", "pll_audio_main_src", };
+static const char *pll_video_bypass_sel[] = { "pll_video_main", "pll_video_main_src", };
+
+static struct clk_onecell_data clk_data;
+
+static void __init imx7d_clocks_init(struct device_node *ccm_node)
+{
+       struct device_node *np;
+       void __iomem *base;
+       int i;
+
+       clks[IMX7D_CLK_DUMMY] = imx_clk_fixed("dummy", 0);
+       clks[IMX7D_OSC_24M_CLK] = of_clk_get_by_name(ccm_node, "osc");
+
+       np = of_find_compatible_node(NULL, NULL, "fsl,imx7d-anatop");
+       base = of_iomap(np, 0);
+       WARN_ON(!base);
+
+       clks[IMX7D_PLL_ARM_MAIN_SRC]  = imx_clk_mux("pll_arm_main_src", base + 0x60, 14, 2, pll_bypass_src_sel, ARRAY_SIZE(pll_bypass_src_sel));
+       clks[IMX7D_PLL_DRAM_MAIN_SRC] = imx_clk_mux("pll_dram_main_src", base + 0x70, 14, 2, pll_bypass_src_sel, ARRAY_SIZE(pll_bypass_src_sel));
+       clks[IMX7D_PLL_SYS_MAIN_SRC]  = imx_clk_mux("pll_sys_main_src", base + 0xb0, 14, 2, pll_bypass_src_sel, ARRAY_SIZE(pll_bypass_src_sel));
+       clks[IMX7D_PLL_ENET_MAIN_SRC] = imx_clk_mux("pll_enet_main_src", base + 0xe0, 14, 2, pll_bypass_src_sel, ARRAY_SIZE(pll_bypass_src_sel));
+       clks[IMX7D_PLL_AUDIO_MAIN_SRC] = imx_clk_mux("pll_audio_main_src", base + 0xf0, 14, 2, pll_bypass_src_sel, ARRAY_SIZE(pll_bypass_src_sel));
+       clks[IMX7D_PLL_VIDEO_MAIN_SRC] = imx_clk_mux("pll_video_main_src", base + 0x130, 14, 2, pll_bypass_src_sel, ARRAY_SIZE(pll_bypass_src_sel));
+
+       clks[IMX7D_PLL_ARM_MAIN]  = imx_clk_pllv3(IMX_PLLV3_SYS, "pll_arm_main", "pll_arm_main_src", base + 0x60, 0x7f);
+       clks[IMX7D_PLL_DRAM_MAIN] = imx_clk_pllv3(IMX_PLLV3_SYS, "pll_dram_main", "pll_dram_main_src", base + 0x70, 0x7f);
+       clks[IMX7D_PLL_SYS_MAIN]  = imx_clk_pllv3(IMX_PLLV3_GENERIC, "pll_sys_main", "pll_sys_main_src", base + 0xb0, 0x1);
+       clks[IMX7D_PLL_ENET_MAIN] = imx_clk_pllv3(IMX_PLLV3_ENET_IMX7, "pll_enet_main", "pll_enet_main_src", base + 0xe0, 0x0);
+       clks[IMX7D_PLL_AUDIO_MAIN] = imx_clk_pllv3(IMX_PLLV3_AV, "pll_audio_main", "pll_audio_main_src", base + 0xf0, 0x7f);
+       clks[IMX7D_PLL_VIDEO_MAIN] = imx_clk_pllv3(IMX_PLLV3_AV, "pll_video_main", "pll_video_main_src", base + 0x130, 0x7f);
+
+       clks[IMX7D_PLL_ARM_MAIN_BYPASS]  = imx_clk_mux_flags("pll_arm_main_bypass", base + 0x60, 16, 1, pll_arm_bypass_sel, ARRAY_SIZE(pll_arm_bypass_sel), CLK_SET_RATE_PARENT);
+       clks[IMX7D_PLL_DRAM_MAIN_BYPASS] = imx_clk_mux_flags("pll_dram_main_bypass", base + 0x70, 16, 1, pll_dram_bypass_sel, ARRAY_SIZE(pll_dram_bypass_sel), CLK_SET_RATE_PARENT);
+       clks[IMX7D_PLL_SYS_MAIN_BYPASS]  = imx_clk_mux_flags("pll_sys_main_bypass", base + 0xb0, 16, 1, pll_sys_bypass_sel, ARRAY_SIZE(pll_sys_bypass_sel), CLK_SET_RATE_PARENT);
+       clks[IMX7D_PLL_ENET_MAIN_BYPASS] = imx_clk_mux_flags("pll_enet_main_bypass", base + 0xe0, 16, 1, pll_enet_bypass_sel, ARRAY_SIZE(pll_enet_bypass_sel), CLK_SET_RATE_PARENT);
+       clks[IMX7D_PLL_AUDIO_MAIN_BYPASS] = imx_clk_mux_flags("pll_audio_main_bypass", base + 0xf0, 16, 1, pll_audio_bypass_sel, ARRAY_SIZE(pll_audio_bypass_sel), CLK_SET_RATE_PARENT);
+       clks[IMX7D_PLL_VIDEO_MAIN_BYPASS] = imx_clk_mux_flags("pll_video_main_bypass", base + 0x130, 16, 1, pll_video_bypass_sel, ARRAY_SIZE(pll_video_bypass_sel), CLK_SET_RATE_PARENT);
+
+       clk_set_parent(clks[IMX7D_PLL_ARM_MAIN_BYPASS], clks[IMX7D_PLL_ARM_MAIN]);
+       clk_set_parent(clks[IMX7D_PLL_DRAM_MAIN_BYPASS], clks[IMX7D_PLL_DRAM_MAIN]);
+       clk_set_parent(clks[IMX7D_PLL_SYS_MAIN_BYPASS], clks[IMX7D_PLL_SYS_MAIN]);
+       clk_set_parent(clks[IMX7D_PLL_ENET_MAIN_BYPASS], clks[IMX7D_PLL_ENET_MAIN]);
+       clk_set_parent(clks[IMX7D_PLL_AUDIO_MAIN_BYPASS], clks[IMX7D_PLL_AUDIO_MAIN]);
+       clk_set_parent(clks[IMX7D_PLL_VIDEO_MAIN_BYPASS], clks[IMX7D_PLL_VIDEO_MAIN]);
+
+       clks[IMX7D_PLL_ARM_MAIN_CLK] = imx_clk_gate("pll_arm_main_clk", "pll_arm_main_bypass", base + 0x60, 13);
+       clks[IMX7D_PLL_DRAM_MAIN_CLK] = imx_clk_gate("pll_dram_main_clk", "pll_dram_main_bypass", base + 0x70, 13);
+       clks[IMX7D_PLL_SYS_MAIN_CLK] = imx_clk_gate("pll_sys_main_clk", "pll_sys_main_bypass", base + 0xb0, 13);
+       clks[IMX7D_PLL_AUDIO_MAIN_CLK] = imx_clk_gate("pll_audio_main_clk", "pll_audio_main_bypass", base + 0xf0, 13);
+       clks[IMX7D_PLL_VIDEO_MAIN_CLK] = imx_clk_gate("pll_video_main_clk", "pll_video_main_bypass", base + 0x130, 13);
+
+       clks[IMX7D_PLL_SYS_PFD0_392M_CLK] = imx_clk_pfd("pll_sys_pfd0_392m_clk", "pll_sys_main_clk", base + 0xc0, 0);
+       clks[IMX7D_PLL_SYS_PFD1_332M_CLK] = imx_clk_pfd("pll_sys_pfd1_332m_clk", "pll_sys_main_clk", base + 0xc0, 1);
+       clks[IMX7D_PLL_SYS_PFD2_270M_CLK] = imx_clk_pfd("pll_sys_pfd2_270m_clk", "pll_sys_main_clk", base + 0xc0, 2);
+
+       clks[IMX7D_PLL_SYS_PFD3_CLK] = imx_clk_pfd("pll_sys_pfd3_clk", "pll_sys_main_clk", base + 0xc0, 3);
+       clks[IMX7D_PLL_SYS_PFD4_CLK] = imx_clk_pfd("pll_sys_pfd4_clk", "pll_sys_main_clk", base + 0xd0, 0);
+       clks[IMX7D_PLL_SYS_PFD5_CLK] = imx_clk_pfd("pll_sys_pfd5_clk", "pll_sys_main_clk", base + 0xd0, 1);
+       clks[IMX7D_PLL_SYS_PFD6_CLK] = imx_clk_pfd("pll_sys_pfd6_clk", "pll_sys_main_clk", base + 0xd0, 2);
+       clks[IMX7D_PLL_SYS_PFD7_CLK] = imx_clk_pfd("pll_sys_pfd7_clk", "pll_sys_main_clk", base + 0xd0, 3);
+
+       clks[IMX7D_PLL_SYS_MAIN_480M] = imx_clk_fixed_factor("pll_sys_main_480m", "pll_sys_main_clk", 1, 1);
+       clks[IMX7D_PLL_SYS_MAIN_240M] = imx_clk_fixed_factor("pll_sys_main_240m", "pll_sys_main_clk", 1, 2);
+       clks[IMX7D_PLL_SYS_MAIN_120M] = imx_clk_fixed_factor("pll_sys_main_120m", "pll_sys_main_clk", 1, 4);
+       clks[IMX7D_PLL_DRAM_MAIN_533M] = imx_clk_fixed_factor("pll_dram_533m", "pll_dram_main_clk", 1, 2);
+
+       clks[IMX7D_PLL_SYS_MAIN_480M_CLK] = imx_clk_gate_dis("pll_sys_main_480m_clk", "pll_sys_main_480m", base + 0xb0, 4);
+       clks[IMX7D_PLL_SYS_MAIN_240M_CLK] = imx_clk_gate_dis("pll_sys_main_240m_clk", "pll_sys_main_240m", base + 0xb0, 5);
+       clks[IMX7D_PLL_SYS_MAIN_120M_CLK] = imx_clk_gate_dis("pll_sys_main_120m_clk", "pll_sys_main_120m", base + 0xb0, 6);
+       clks[IMX7D_PLL_DRAM_MAIN_533M_CLK] = imx_clk_gate("pll_dram_533m_clk", "pll_dram_533m", base + 0x70, 12);
+
+       clks[IMX7D_PLL_SYS_PFD0_196M] = imx_clk_fixed_factor("pll_sys_pfd0_196m", "pll_sys_pfd0_392m_clk", 1, 2);
+       clks[IMX7D_PLL_SYS_PFD1_166M] = imx_clk_fixed_factor("pll_sys_pfd1_166m", "pll_sys_pfd1_332m_clk", 1, 2);
+       clks[IMX7D_PLL_SYS_PFD2_135M] = imx_clk_fixed_factor("pll_sys_pfd2_135m", "pll_sys_pfd2_270m_clk", 1, 2);
+
+       clks[IMX7D_PLL_SYS_PFD0_196M_CLK] = imx_clk_gate_dis("pll_sys_pfd0_196m_clk", "pll_sys_pfd0_196m", base + 0xb0, 26);
+       clks[IMX7D_PLL_SYS_PFD1_166M_CLK] = imx_clk_gate_dis("pll_sys_pfd1_166m_clk", "pll_sys_pfd1_166m", base + 0xb0, 27);
+       clks[IMX7D_PLL_SYS_PFD2_135M_CLK] = imx_clk_gate_dis("pll_sys_pfd2_135m_clk", "pll_sys_pfd2_135m", base + 0xb0, 28);
+
+       clks[IMX7D_PLL_ENET_MAIN_CLK] = imx_clk_fixed_factor("pll_enet_main_clk", "pll_enet_main_bypass", 1, 1);
+       clks[IMX7D_PLL_ENET_MAIN_500M] = imx_clk_fixed_factor("pll_enet_500m", "pll_enet_main_clk", 1, 2);
+       clks[IMX7D_PLL_ENET_MAIN_250M] = imx_clk_fixed_factor("pll_enet_250m", "pll_enet_main_clk", 1, 4);
+       clks[IMX7D_PLL_ENET_MAIN_125M] = imx_clk_fixed_factor("pll_enet_125m", "pll_enet_main_clk", 1, 8);
+       clks[IMX7D_PLL_ENET_MAIN_100M] = imx_clk_fixed_factor("pll_enet_100m", "pll_enet_main_clk", 1, 10);
+       clks[IMX7D_PLL_ENET_MAIN_50M] = imx_clk_fixed_factor("pll_enet_50m", "pll_enet_main_clk", 1, 20);
+       clks[IMX7D_PLL_ENET_MAIN_40M] = imx_clk_fixed_factor("pll_enet_40m", "pll_enet_main_clk", 1, 25);
+       clks[IMX7D_PLL_ENET_MAIN_25M] = imx_clk_fixed_factor("pll_enet_25m", "pll_enet_main_clk", 1, 40);
+
+       clks[IMX7D_PLL_ENET_MAIN_500M_CLK] = imx_clk_gate("pll_enet_500m_clk", "pll_enet_500m", base + 0xe0, 12);
+       clks[IMX7D_PLL_ENET_MAIN_250M_CLK] = imx_clk_gate("pll_enet_250m_clk", "pll_enet_250m", base + 0xe0, 11);
+       clks[IMX7D_PLL_ENET_MAIN_125M_CLK] = imx_clk_gate("pll_enet_125m_clk", "pll_enet_125m", base + 0xe0, 10);
+       clks[IMX7D_PLL_ENET_MAIN_100M_CLK] = imx_clk_gate("pll_enet_100m_clk", "pll_enet_100m", base + 0xe0, 9);
+       clks[IMX7D_PLL_ENET_MAIN_50M_CLK]  = imx_clk_gate("pll_enet_50m_clk", "pll_enet_50m", base + 0xe0, 8);
+       clks[IMX7D_PLL_ENET_MAIN_40M_CLK]  = imx_clk_gate("pll_enet_40m_clk", "pll_enet_40m", base + 0xe0, 7);
+       clks[IMX7D_PLL_ENET_MAIN_25M_CLK]  = imx_clk_gate("pll_enet_25m_clk", "pll_enet_25m", base + 0xe0, 6);
+
+       clks[IMX7D_LVDS1_OUT_SEL] = imx_clk_mux("lvds1_sel", base + 0x170, 0, 5, lvds1_sel, ARRAY_SIZE(lvds1_sel));
+       clks[IMX7D_LVDS1_OUT_CLK] = imx_clk_gate_exclusive("lvds1_out", "lvds1_sel", base + 0x170, 5, BIT(6));
+
+       np = ccm_node;
+       base = of_iomap(np, 0);
+       WARN_ON(!base);
+
+       clks[IMX7D_ARM_A7_ROOT_SRC] = imx_clk_mux("arm_a7_src", base + 0x8000, 24, 3, arm_a7_sel, ARRAY_SIZE(arm_a7_sel));
+       clks[IMX7D_ARM_M4_ROOT_SRC] = imx_clk_mux("arm_m4_src", base + 0x8080, 24, 3, arm_m4_sel, ARRAY_SIZE(arm_m4_sel));
+       clks[IMX7D_ARM_M0_ROOT_SRC] = imx_clk_mux("arm_m0_src", base + 0x8100, 24, 3, arm_m0_sel, ARRAY_SIZE(arm_m0_sel));
+       clks[IMX7D_MAIN_AXI_ROOT_SRC] = imx_clk_mux("axi_src", base + 0x8800, 24, 3, axi_sel, ARRAY_SIZE(axi_sel));
+       clks[IMX7D_DISP_AXI_ROOT_SRC] = imx_clk_mux("disp_axi_src", base + 0x8880, 24, 3, disp_axi_sel, ARRAY_SIZE(disp_axi_sel));
+       clks[IMX7D_ENET_AXI_ROOT_SRC] = imx_clk_mux("enet_axi_src", base + 0x8900, 24, 3, enet_axi_sel, ARRAY_SIZE(enet_axi_sel));
+       clks[IMX7D_NAND_USDHC_BUS_ROOT_SRC] = imx_clk_mux("nand_usdhc_src", base + 0x8980, 24, 3, nand_usdhc_bus_sel, ARRAY_SIZE(nand_usdhc_bus_sel));
+       clks[IMX7D_AHB_CHANNEL_ROOT_SRC] = imx_clk_mux("ahb_src", base + 0x9000, 24, 3, ahb_channel_sel, ARRAY_SIZE(ahb_channel_sel));
+       clks[IMX7D_DRAM_PHYM_ROOT_SRC] = imx_clk_mux("dram_phym_src", base + 0x9800, 24, 1, dram_phym_sel, ARRAY_SIZE(dram_phym_sel));
+       clks[IMX7D_DRAM_ROOT_SRC] = imx_clk_mux("dram_src", base + 0x9880, 24, 1, dram_sel, ARRAY_SIZE(dram_sel));
+       clks[IMX7D_DRAM_PHYM_ALT_ROOT_SRC] = imx_clk_mux("dram_phym_alt_src", base + 0xa000, 24, 3, dram_phym_alt_sel, ARRAY_SIZE(dram_phym_alt_sel));
+       clks[IMX7D_DRAM_ALT_ROOT_SRC]  = imx_clk_mux("dram_alt_src", base + 0xa080, 24, 3, dram_alt_sel, ARRAY_SIZE(dram_alt_sel));
+       clks[IMX7D_USB_HSIC_ROOT_SRC] = imx_clk_mux("usb_hsic_src", base + 0xa100, 24, 3, usb_hsic_sel, ARRAY_SIZE(usb_hsic_sel));
+       clks[IMX7D_PCIE_CTRL_ROOT_SRC] = imx_clk_mux("pcie_ctrl_src", base + 0xa180, 24, 3, pcie_ctrl_sel, ARRAY_SIZE(pcie_ctrl_sel));
+       clks[IMX7D_PCIE_PHY_ROOT_SRC] = imx_clk_mux("pcie_phy_src", base + 0xa200, 24, 3, pcie_phy_sel, ARRAY_SIZE(pcie_phy_sel));
+       clks[IMX7D_EPDC_PIXEL_ROOT_SRC] = imx_clk_mux("epdc_pixel_src", base + 0xa280, 24, 3, epdc_pixel_sel, ARRAY_SIZE(epdc_pixel_sel));
+       clks[IMX7D_LCDIF_PIXEL_ROOT_SRC] = imx_clk_mux("lcdif_pixel_src", base + 0xa300, 24, 3, lcdif_pixel_sel, ARRAY_SIZE(lcdif_pixel_sel));
+       clks[IMX7D_MIPI_DSI_ROOT_SRC] = imx_clk_mux("mipi_dsi_src", base + 0xa380, 24, 3,  mipi_dsi_sel, ARRAY_SIZE(mipi_dsi_sel));
+       clks[IMX7D_MIPI_CSI_ROOT_SRC] = imx_clk_mux("mipi_csi_src", base + 0xa400, 24, 3, mipi_csi_sel, ARRAY_SIZE(mipi_csi_sel));
+       clks[IMX7D_MIPI_DPHY_ROOT_SRC] = imx_clk_mux("mipi_dphy_src", base + 0xa480, 24, 3, mipi_dphy_sel, ARRAY_SIZE(mipi_dphy_sel));
+       clks[IMX7D_SAI1_ROOT_SRC] = imx_clk_mux("sai1_src", base + 0xa500, 24, 3, sai1_sel, ARRAY_SIZE(sai1_sel));
+       clks[IMX7D_SAI2_ROOT_SRC] = imx_clk_mux("sai2_src", base + 0xa580, 24, 3, sai2_sel, ARRAY_SIZE(sai2_sel));
+       clks[IMX7D_SAI3_ROOT_SRC] = imx_clk_mux("sai3_src", base + 0xa600, 24, 3, sai3_sel, ARRAY_SIZE(sai3_sel));
+       clks[IMX7D_SPDIF_ROOT_SRC] = imx_clk_mux("spdif_src", base + 0xa680, 24, 3, spdif_sel, ARRAY_SIZE(spdif_sel));
+       clks[IMX7D_ENET1_REF_ROOT_SRC] = imx_clk_mux("enet1_ref_src", base + 0xa700, 24, 3, enet1_ref_sel, ARRAY_SIZE(enet1_ref_sel));
+       clks[IMX7D_ENET1_TIME_ROOT_SRC] = imx_clk_mux("enet1_time_src", base + 0xa780, 24, 3, enet1_time_sel, ARRAY_SIZE(enet1_time_sel));
+       clks[IMX7D_ENET2_REF_ROOT_SRC] = imx_clk_mux("enet2_ref_src", base + 0xa800, 24, 3, enet2_ref_sel, ARRAY_SIZE(enet2_ref_sel));
+       clks[IMX7D_ENET2_TIME_ROOT_SRC] = imx_clk_mux("enet2_time_src", base + 0xa880, 24, 3, enet2_time_sel, ARRAY_SIZE(enet2_time_sel));
+       clks[IMX7D_ENET_PHY_REF_ROOT_SRC] = imx_clk_mux("enet_phy_ref_src", base + 0xa900, 24, 3, enet_phy_ref_sel, ARRAY_SIZE(enet_phy_ref_sel));
+       clks[IMX7D_EIM_ROOT_SRC] = imx_clk_mux("eim_src", base + 0xa980, 24, 3, eim_sel, ARRAY_SIZE(eim_sel));
+       clks[IMX7D_NAND_ROOT_SRC] = imx_clk_mux("nand_src", base + 0xaa00, 24, 3, nand_sel, ARRAY_SIZE(nand_sel));
+       clks[IMX7D_QSPI_ROOT_SRC] = imx_clk_mux("qspi_src", base + 0xaa80, 24, 3, qspi_sel, ARRAY_SIZE(qspi_sel));
+       clks[IMX7D_USDHC1_ROOT_SRC] = imx_clk_mux("usdhc1_src", base + 0xab00, 24, 3, usdhc1_sel, ARRAY_SIZE(usdhc1_sel));
+       clks[IMX7D_USDHC2_ROOT_SRC] = imx_clk_mux("usdhc2_src", base + 0xab80, 24, 3, usdhc2_sel, ARRAY_SIZE(usdhc2_sel));
+       clks[IMX7D_USDHC3_ROOT_SRC] = imx_clk_mux("usdhc3_src", base + 0xac00, 24, 3, usdhc3_sel, ARRAY_SIZE(usdhc3_sel));
+       clks[IMX7D_CAN1_ROOT_SRC] = imx_clk_mux("can1_src", base + 0xac80, 24, 3, can1_sel, ARRAY_SIZE(can1_sel));
+       clks[IMX7D_CAN2_ROOT_SRC] = imx_clk_mux("can2_src", base + 0xad00, 24, 3, can2_sel, ARRAY_SIZE(can2_sel));
+       clks[IMX7D_I2C1_ROOT_SRC] = imx_clk_mux("i2c1_src", base + 0xad80, 24, 3, i2c1_sel, ARRAY_SIZE(i2c1_sel));
+       clks[IMX7D_I2C2_ROOT_SRC] = imx_clk_mux("i2c2_src", base + 0xae00, 24, 3, i2c2_sel, ARRAY_SIZE(i2c2_sel));
+       clks[IMX7D_I2C3_ROOT_SRC] = imx_clk_mux("i2c3_src", base + 0xae80, 24, 3, i2c3_sel, ARRAY_SIZE(i2c3_sel));
+       clks[IMX7D_I2C4_ROOT_SRC] = imx_clk_mux("i2c4_src", base + 0xaf00, 24, 3, i2c4_sel, ARRAY_SIZE(i2c4_sel));
+       clks[IMX7D_UART1_ROOT_SRC] = imx_clk_mux("uart1_src", base + 0xaf80, 24, 3, uart1_sel, ARRAY_SIZE(uart1_sel));
+       clks[IMX7D_UART2_ROOT_SRC] = imx_clk_mux("uart2_src", base + 0xb000, 24, 3, uart2_sel, ARRAY_SIZE(uart2_sel));
+       clks[IMX7D_UART3_ROOT_SRC] = imx_clk_mux("uart3_src", base + 0xb080, 24, 3, uart3_sel, ARRAY_SIZE(uart3_sel));
+       clks[IMX7D_UART4_ROOT_SRC] = imx_clk_mux("uart4_src", base + 0xb100, 24, 3, uart4_sel, ARRAY_SIZE(uart4_sel));
+       clks[IMX7D_UART5_ROOT_SRC] = imx_clk_mux("uart5_src", base + 0xb180, 24, 3, uart5_sel, ARRAY_SIZE(uart5_sel));
+       clks[IMX7D_UART6_ROOT_SRC] = imx_clk_mux("uart6_src", base + 0xb200, 24, 3, uart6_sel, ARRAY_SIZE(uart6_sel));
+       clks[IMX7D_UART7_ROOT_SRC] = imx_clk_mux("uart7_src", base + 0xb280, 24, 3, uart7_sel, ARRAY_SIZE(uart7_sel));
+       clks[IMX7D_ECSPI1_ROOT_SRC] = imx_clk_mux("ecspi1_src", base + 0xb300, 24, 3, ecspi1_sel, ARRAY_SIZE(ecspi1_sel));
+       clks[IMX7D_ECSPI2_ROOT_SRC] = imx_clk_mux("ecspi2_src", base + 0xb380, 24, 3, ecspi2_sel, ARRAY_SIZE(ecspi2_sel));
+       clks[IMX7D_ECSPI3_ROOT_SRC] = imx_clk_mux("ecspi3_src", base + 0xb400, 24, 3, ecspi3_sel, ARRAY_SIZE(ecspi3_sel));
+       clks[IMX7D_ECSPI4_ROOT_SRC] = imx_clk_mux("ecspi4_src", base + 0xb480, 24, 3, ecspi4_sel, ARRAY_SIZE(ecspi4_sel));
+       clks[IMX7D_PWM1_ROOT_SRC] = imx_clk_mux("pwm1_src", base + 0xb500, 24, 3, pwm1_sel, ARRAY_SIZE(pwm1_sel));
+       clks[IMX7D_PWM2_ROOT_SRC] = imx_clk_mux("pwm2_src", base + 0xb580, 24, 3, pwm2_sel, ARRAY_SIZE(pwm2_sel));
+       clks[IMX7D_PWM3_ROOT_SRC] = imx_clk_mux("pwm3_src", base + 0xb600, 24, 3, pwm3_sel, ARRAY_SIZE(pwm3_sel));
+       clks[IMX7D_PWM4_ROOT_SRC] = imx_clk_mux("pwm4_src", base + 0xb680, 24, 3, pwm4_sel, ARRAY_SIZE(pwm4_sel));
+       clks[IMX7D_FLEXTIMER1_ROOT_SRC] = imx_clk_mux("flextimer1_src", base + 0xb700, 24, 3, flextimer1_sel, ARRAY_SIZE(flextimer1_sel));
+       clks[IMX7D_FLEXTIMER2_ROOT_SRC] = imx_clk_mux("flextimer2_src", base + 0xb780, 24, 3, flextimer2_sel, ARRAY_SIZE(flextimer2_sel));
+       clks[IMX7D_SIM1_ROOT_SRC] = imx_clk_mux("sim1_src", base + 0xb800, 24, 3, sim1_sel, ARRAY_SIZE(sim1_sel));
+       clks[IMX7D_SIM2_ROOT_SRC] = imx_clk_mux("sim2_src", base + 0xb880, 24, 3, sim2_sel, ARRAY_SIZE(sim2_sel));
+       clks[IMX7D_GPT1_ROOT_SRC] = imx_clk_mux("gpt1_src", base + 0xb900, 24, 3, gpt1_sel, ARRAY_SIZE(gpt1_sel));
+       clks[IMX7D_GPT2_ROOT_SRC] = imx_clk_mux("gpt2_src", base + 0xb980, 24, 3, gpt2_sel, ARRAY_SIZE(gpt2_sel));
+       clks[IMX7D_GPT3_ROOT_SRC] = imx_clk_mux("gpt3_src", base + 0xba00, 24, 3, gpt3_sel, ARRAY_SIZE(gpt3_sel));
+       clks[IMX7D_GPT4_ROOT_SRC] = imx_clk_mux("gpt4_src", base + 0xba80, 24, 3, gpt4_sel, ARRAY_SIZE(gpt4_sel));
+       clks[IMX7D_TRACE_ROOT_SRC] = imx_clk_mux("trace_src", base + 0xbb00, 24, 3, trace_sel, ARRAY_SIZE(trace_sel));
+       clks[IMX7D_WDOG_ROOT_SRC] = imx_clk_mux("wdog_src", base + 0xbb80, 24, 3, wdog_sel, ARRAY_SIZE(wdog_sel));
+       clks[IMX7D_CSI_MCLK_ROOT_SRC] = imx_clk_mux("csi_mclk_src", base + 0xbc00, 24, 3, csi_mclk_sel, ARRAY_SIZE(csi_mclk_sel));
+       clks[IMX7D_AUDIO_MCLK_ROOT_SRC] = imx_clk_mux("audio_mclk_src", base + 0xbc80, 24, 3, audio_mclk_sel, ARRAY_SIZE(audio_mclk_sel));
+       clks[IMX7D_WRCLK_ROOT_SRC] = imx_clk_mux("wrclk_src", base + 0xbd00, 24, 3, wrclk_sel, ARRAY_SIZE(wrclk_sel));
+       clks[IMX7D_CLKO1_ROOT_SRC] = imx_clk_mux("clko1_src", base + 0xbd80, 24, 3, clko1_sel, ARRAY_SIZE(clko1_sel));
+       clks[IMX7D_CLKO2_ROOT_SRC] = imx_clk_mux("clko2_src", base + 0xbe00, 24, 3, clko2_sel, ARRAY_SIZE(clko2_sel));
+
+       clks[IMX7D_ARM_A7_ROOT_CG] = imx_clk_gate("arm_a7_cg", "arm_a7_src", base + 0x8000, 28);
+       clks[IMX7D_ARM_M4_ROOT_CG] = imx_clk_gate("arm_m4_cg", "arm_m4_src", base + 0x8080, 28);
+       clks[IMX7D_ARM_M0_ROOT_CG] = imx_clk_gate("arm_m0_cg", "arm_m0_src", base + 0x8100, 28);
+       clks[IMX7D_MAIN_AXI_ROOT_CG] = imx_clk_gate("axi_cg", "axi_src", base + 0x8800, 28);
+       clks[IMX7D_DISP_AXI_ROOT_CG] = imx_clk_gate("disp_axi_cg", "disp_axi_src", base + 0x8880, 28);
+       clks[IMX7D_ENET_AXI_ROOT_CG] = imx_clk_gate("enet_axi_cg", "enet_axi_src", base + 0x8900, 28);
+       clks[IMX7D_NAND_USDHC_BUS_ROOT_CG] = imx_clk_gate("nand_usdhc_cg", "nand_usdhc_src", base + 0x8980, 28);
+       clks[IMX7D_AHB_CHANNEL_ROOT_CG] = imx_clk_gate("ahb_cg", "ahb_src", base + 0x9000, 28);
+       clks[IMX7D_DRAM_PHYM_ROOT_CG] = imx_clk_gate("dram_phym_cg", "dram_phym_src", base + 0x9800, 28);
+       clks[IMX7D_DRAM_ROOT_CG] = imx_clk_gate("dram_cg", "dram_src", base + 0x9880, 28);
+       clks[IMX7D_DRAM_PHYM_ALT_ROOT_CG] = imx_clk_gate("dram_phym_alt_cg", "dram_phym_alt_src", base + 0xa000, 28);
+       clks[IMX7D_DRAM_ALT_ROOT_CG] = imx_clk_gate("dram_alt_cg", "dram_alt_src", base + 0xa080, 28);
+       clks[IMX7D_USB_HSIC_ROOT_CG] = imx_clk_gate("usb_hsic_cg", "usb_hsic_src", base + 0xa100, 28);
+       clks[IMX7D_PCIE_CTRL_ROOT_CG] = imx_clk_gate("pcie_ctrl_cg", "pcie_ctrl_src", base + 0xa180, 28);
+       clks[IMX7D_PCIE_PHY_ROOT_CG] = imx_clk_gate("pcie_phy_cg", "pcie_phy_src", base + 0xa200, 28);
+       clks[IMX7D_EPDC_PIXEL_ROOT_CG] = imx_clk_gate("epdc_pixel_cg", "epdc_pixel_src", base + 0xa280, 28);
+       clks[IMX7D_LCDIF_PIXEL_ROOT_CG] = imx_clk_gate("lcdif_pixel_cg", "lcdif_pixel_src", base + 0xa300, 28);
+       clks[IMX7D_MIPI_DSI_ROOT_CG] = imx_clk_gate("mipi_dsi_cg", "mipi_dsi_src", base + 0xa380, 28);
+       clks[IMX7D_MIPI_CSI_ROOT_CG] = imx_clk_gate("mipi_csi_cg", "mipi_csi_src", base + 0xa400, 28);
+       clks[IMX7D_MIPI_DPHY_ROOT_CG] = imx_clk_gate("mipi_dphy_cg", "mipi_dphy_src", base + 0xa480, 28);
+       clks[IMX7D_SAI1_ROOT_CG] = imx_clk_gate("sai1_cg", "sai1_src", base + 0xa500, 28);
+       clks[IMX7D_SAI2_ROOT_CG] = imx_clk_gate("sai2_cg", "sai2_src", base + 0xa580, 28);
+       clks[IMX7D_SAI3_ROOT_CG] = imx_clk_gate("sai3_cg", "sai3_src", base + 0xa600, 28);
+       clks[IMX7D_SPDIF_ROOT_CG] = imx_clk_gate("spdif_cg", "spdif_src", base + 0xa680, 28);
+       clks[IMX7D_ENET1_REF_ROOT_CG] = imx_clk_gate("enet1_ref_cg", "enet1_ref_src", base + 0xa700, 28);
+       clks[IMX7D_ENET1_TIME_ROOT_CG] = imx_clk_gate("enet1_time_cg", "enet1_time_src", base + 0xa780, 28);
+       clks[IMX7D_ENET2_REF_ROOT_CG] = imx_clk_gate("enet2_ref_cg", "enet2_ref_src", base + 0xa800, 28);
+       clks[IMX7D_ENET2_TIME_ROOT_CG] = imx_clk_gate("enet2_time_cg", "enet2_time_src", base + 0xa880, 28);
+       clks[IMX7D_ENET_PHY_REF_ROOT_CG] = imx_clk_gate("enet_phy_ref_cg", "enet_phy_ref_src", base + 0xa900, 28);
+       clks[IMX7D_EIM_ROOT_CG] = imx_clk_gate("eim_cg", "eim_src", base + 0xa980, 28);
+       clks[IMX7D_NAND_ROOT_CG] = imx_clk_gate("nand_cg", "nand_src", base + 0xaa00, 28);
+       clks[IMX7D_QSPI_ROOT_CG] = imx_clk_gate("qspi_cg", "qspi_src", base + 0xaa80, 28);
+       clks[IMX7D_USDHC1_ROOT_CG] = imx_clk_gate("usdhc1_cg", "usdhc1_src", base + 0xab00, 28);
+       clks[IMX7D_USDHC2_ROOT_CG] = imx_clk_gate("usdhc2_cg", "usdhc2_src", base + 0xab80, 28);
+       clks[IMX7D_USDHC3_ROOT_CG] = imx_clk_gate("usdhc3_cg", "usdhc3_src", base + 0xac00, 28);
+       clks[IMX7D_CAN1_ROOT_CG] = imx_clk_gate("can1_cg", "can1_src", base + 0xac80, 28);
+       clks[IMX7D_CAN2_ROOT_CG] = imx_clk_gate("can2_cg", "can2_src", base + 0xad00, 28);
+       clks[IMX7D_I2C1_ROOT_CG] = imx_clk_gate("i2c1_cg", "i2c1_src", base + 0xad80, 28);
+       clks[IMX7D_I2C2_ROOT_CG] = imx_clk_gate("i2c2_cg", "i2c2_src", base + 0xae00, 28);
+       clks[IMX7D_I2C3_ROOT_CG] = imx_clk_gate("i2c3_cg", "i2c3_src", base + 0xae80, 28);
+       clks[IMX7D_I2C4_ROOT_CG] = imx_clk_gate("i2c4_cg", "i2c4_src", base + 0xaf00, 28);
+       clks[IMX7D_UART1_ROOT_CG] = imx_clk_gate("uart1_cg", "uart1_src", base + 0xaf80, 28);
+       clks[IMX7D_UART2_ROOT_CG] = imx_clk_gate("uart2_cg", "uart2_src", base + 0xb000, 28);
+       clks[IMX7D_UART3_ROOT_CG] = imx_clk_gate("uart3_cg", "uart3_src", base + 0xb080, 28);
+       clks[IMX7D_UART4_ROOT_CG] = imx_clk_gate("uart4_cg", "uart4_src", base + 0xb100, 28);
+       clks[IMX7D_UART5_ROOT_CG] = imx_clk_gate("uart5_cg", "uart5_src", base + 0xb180, 28);
+       clks[IMX7D_UART6_ROOT_CG] = imx_clk_gate("uart6_cg", "uart6_src", base + 0xb200, 28);
+       clks[IMX7D_UART7_ROOT_CG] = imx_clk_gate("uart7_cg", "uart7_src", base + 0xb280, 28);
+       clks[IMX7D_ECSPI1_ROOT_CG] = imx_clk_gate("ecspi1_cg", "ecspi1_src", base + 0xb300, 28);
+       clks[IMX7D_ECSPI2_ROOT_CG] = imx_clk_gate("ecspi2_cg", "ecspi2_src", base + 0xb380, 28);
+       clks[IMX7D_ECSPI3_ROOT_CG] = imx_clk_gate("ecspi3_cg", "ecspi3_src", base + 0xb400, 28);
+       clks[IMX7D_ECSPI4_ROOT_CG] = imx_clk_gate("ecspi4_cg", "ecspi4_src", base + 0xb480, 28);
+       clks[IMX7D_PWM1_ROOT_CG] = imx_clk_gate("pwm1_cg", "pwm1_src", base + 0xb500, 28);
+       clks[IMX7D_PWM2_ROOT_CG] = imx_clk_gate("pwm2_cg", "pwm2_src", base + 0xb580, 28);
+       clks[IMX7D_PWM3_ROOT_CG] = imx_clk_gate("pwm3_cg", "pwm3_src", base + 0xb600, 28);
+       clks[IMX7D_PWM4_ROOT_CG] = imx_clk_gate("pwm4_cg", "pwm4_src", base + 0xb680, 28);
+       clks[IMX7D_FLEXTIMER1_ROOT_CG] = imx_clk_gate("flextimer1_cg", "flextimer1_src", base + 0xb700, 28);
+       clks[IMX7D_FLEXTIMER2_ROOT_CG] = imx_clk_gate("flextimer2_cg", "flextimer2_src", base + 0xb780, 28);
+       clks[IMX7D_SIM1_ROOT_CG] = imx_clk_gate("sim1_cg", "sim1_src", base + 0xb800, 28);
+       clks[IMX7D_SIM2_ROOT_CG] = imx_clk_gate("sim2_cg", "sim2_src", base + 0xb880, 28);
+       clks[IMX7D_GPT1_ROOT_CG] = imx_clk_gate("gpt1_cg", "gpt1_src", base + 0xb900, 28);
+       clks[IMX7D_GPT2_ROOT_CG] = imx_clk_gate("gpt2_cg", "gpt2_src", base + 0xb980, 28);
+       clks[IMX7D_GPT3_ROOT_CG] = imx_clk_gate("gpt3_cg", "gpt3_src", base + 0xbA00, 28);
+       clks[IMX7D_GPT4_ROOT_CG] = imx_clk_gate("gpt4_cg", "gpt4_src", base + 0xbA80, 28);
+       clks[IMX7D_TRACE_ROOT_CG] = imx_clk_gate("trace_cg", "trace_src", base + 0xbb00, 28);
+       clks[IMX7D_WDOG_ROOT_CG] = imx_clk_gate("wdog_cg", "wdog_src", base + 0xbb80, 28);
+       clks[IMX7D_CSI_MCLK_ROOT_CG] = imx_clk_gate("csi_mclk_cg", "csi_mclk_src", base + 0xbc00, 28);
+       clks[IMX7D_AUDIO_MCLK_ROOT_CG] = imx_clk_gate("audio_mclk_cg", "audio_mclk_src", base + 0xbc80, 28);
+       clks[IMX7D_WRCLK_ROOT_CG] = imx_clk_gate("wrclk_cg", "wrclk_src", base + 0xbd00, 28);
+       clks[IMX7D_CLKO1_ROOT_CG] = imx_clk_gate("clko1_cg", "clko1_src", base + 0xbd80, 28);
+       clks[IMX7D_CLKO2_ROOT_CG] = imx_clk_gate("clko2_cg", "clko2_src", base + 0xbe00, 28);
+
+       clks[IMX7D_MAIN_AXI_ROOT_PRE_DIV] = imx_clk_divider("axi_pre_div", "axi_cg", base + 0x8800, 16, 3);
+       clks[IMX7D_DISP_AXI_ROOT_PRE_DIV] = imx_clk_divider("disp_axi_pre_div", "disp_axi_cg", base + 0x8880, 16, 3);
+       clks[IMX7D_ENET_AXI_ROOT_PRE_DIV] = imx_clk_divider("enet_axi_pre_div", "enet_axi_cg", base + 0x8900, 16, 3);
+       clks[IMX7D_NAND_USDHC_BUS_ROOT_PRE_DIV] = imx_clk_divider("nand_usdhc_pre_div", "nand_usdhc_cg", base + 0x8980, 16, 3);
+       clks[IMX7D_AHB_CHANNEL_ROOT_PRE_DIV] = imx_clk_divider("ahb_pre_div", "ahb_cg", base + 0x9000, 16, 3);
+       clks[IMX7D_DRAM_PHYM_ALT_ROOT_PRE_DIV] = imx_clk_divider("dram_phym_alt_pre_div", "dram_phym_alt_cg", base + 0xa000, 16, 3);
+       clks[IMX7D_DRAM_ALT_ROOT_PRE_DIV] = imx_clk_divider("dram_alt_pre_div", "dram_alt_cg", base + 0xa080, 16, 3);
+       clks[IMX7D_USB_HSIC_ROOT_PRE_DIV] = imx_clk_divider("usb_hsic_pre_div", "usb_hsic_cg", base + 0xa100, 16, 3);
+       clks[IMX7D_PCIE_CTRL_ROOT_PRE_DIV] = imx_clk_divider("pcie_ctrl_pre_div", "pcie_ctrl_cg", base + 0xa180, 16, 3);
+       clks[IMX7D_PCIE_PHY_ROOT_PRE_DIV] = imx_clk_divider("pcie_phy_pre_div", "pcie_phy_cg", base + 0xa200, 16, 3);
+       clks[IMX7D_EPDC_PIXEL_ROOT_PRE_DIV] = imx_clk_divider("epdc_pixel_pre_div", "epdc_pixel_cg", base + 0xa280, 16, 3);
+       clks[IMX7D_LCDIF_PIXEL_ROOT_PRE_DIV] = imx_clk_divider("lcdif_pixel_pre_div", "lcdif_pixel_cg", base + 0xa300, 16, 3);
+       clks[IMX7D_MIPI_DSI_ROOT_PRE_DIV] = imx_clk_divider("mipi_dsi_pre_div", "mipi_dsi_cg", base + 0xa380, 16, 3);
+       clks[IMX7D_MIPI_CSI_ROOT_PRE_DIV] = imx_clk_divider("mipi_csi_pre_div", "mipi_csi_cg", base + 0xa400, 16, 3);
+       clks[IMX7D_MIPI_DPHY_ROOT_PRE_DIV] = imx_clk_divider("mipi_dphy_pre_div", "mipi_dphy_cg", base + 0xa480, 16, 3);
+       clks[IMX7D_SAI1_ROOT_PRE_DIV] = imx_clk_divider("sai1_pre_div", "sai1_cg", base + 0xa500, 16, 3);
+       clks[IMX7D_SAI2_ROOT_PRE_DIV] = imx_clk_divider("sai2_pre_div", "sai2_cg", base + 0xa580, 16, 3);
+       clks[IMX7D_SAI3_ROOT_PRE_DIV] = imx_clk_divider("sai3_pre_div", "sai3_cg", base + 0xa600, 16, 3);
+       clks[IMX7D_SPDIF_ROOT_PRE_DIV] = imx_clk_divider("spdif_pre_div", "spdif_cg", base + 0xa680, 16, 3);
+       clks[IMX7D_ENET1_REF_ROOT_PRE_DIV] = imx_clk_divider("enet1_ref_pre_div", "enet1_ref_cg", base + 0xa700, 16, 3);
+       clks[IMX7D_ENET1_TIME_ROOT_PRE_DIV] = imx_clk_divider("enet1_time_pre_div", "enet1_time_cg", base + 0xa780, 16, 3);
+       clks[IMX7D_ENET2_REF_ROOT_PRE_DIV] = imx_clk_divider("enet2_ref_pre_div", "enet2_ref_cg", base + 0xa800, 16, 3);
+       clks[IMX7D_ENET2_TIME_ROOT_PRE_DIV] = imx_clk_divider("enet2_time_pre_div", "enet2_time_cg", base + 0xa880, 16, 3);
+       clks[IMX7D_ENET_PHY_REF_ROOT_PRE_DIV] = imx_clk_divider("enet_phy_ref_pre_div", "enet_phy_ref_cg", base + 0xa900, 16, 3);
+       clks[IMX7D_EIM_ROOT_PRE_DIV] = imx_clk_divider("eim_pre_div", "eim_cg", base + 0xa980, 16, 3);
+       clks[IMX7D_NAND_ROOT_PRE_DIV] = imx_clk_divider("nand_pre_div", "nand_cg", base + 0xaa00, 16, 3);
+       clks[IMX7D_QSPI_ROOT_PRE_DIV] = imx_clk_divider("qspi_pre_div", "qspi_cg", base + 0xaa80, 16, 3);
+       clks[IMX7D_USDHC1_ROOT_PRE_DIV] = imx_clk_divider("usdhc1_pre_div", "usdhc1_cg", base + 0xab00, 16, 3);
+       clks[IMX7D_USDHC2_ROOT_PRE_DIV] = imx_clk_divider("usdhc2_pre_div", "usdhc2_cg", base + 0xab80, 16, 3);
+       clks[IMX7D_USDHC3_ROOT_PRE_DIV] = imx_clk_divider("usdhc3_pre_div", "usdhc3_cg", base + 0xac00, 16, 3);
+       clks[IMX7D_CAN1_ROOT_PRE_DIV] = imx_clk_divider("can1_pre_div", "can1_cg", base + 0xac80, 16, 3);
+       clks[IMX7D_CAN2_ROOT_PRE_DIV] = imx_clk_divider("can2_pre_div", "can2_cg", base + 0xad00, 16, 3);
+       clks[IMX7D_I2C1_ROOT_PRE_DIV] = imx_clk_divider("i2c1_pre_div", "i2c1_cg", base + 0xad80, 16, 3);
+       clks[IMX7D_I2C2_ROOT_PRE_DIV] = imx_clk_divider("i2c2_pre_div", "i2c2_cg", base + 0xae00, 16, 3);
+       clks[IMX7D_I2C3_ROOT_PRE_DIV] = imx_clk_divider("i2c3_pre_div", "i2c3_cg", base + 0xae80, 16, 3);
+       clks[IMX7D_I2C4_ROOT_PRE_DIV] = imx_clk_divider("i2c4_pre_div", "i2c4_cg", base + 0xaf00, 16, 3);
+       clks[IMX7D_UART1_ROOT_PRE_DIV] = imx_clk_divider("uart1_pre_div", "uart1_cg", base + 0xaf80, 16, 3);
+       clks[IMX7D_UART2_ROOT_PRE_DIV] = imx_clk_divider("uart2_pre_div", "uart2_cg", base + 0xb000, 16, 3);
+       clks[IMX7D_UART3_ROOT_PRE_DIV] = imx_clk_divider("uart3_pre_div", "uart3_cg", base + 0xb080, 16, 3);
+       clks[IMX7D_UART4_ROOT_PRE_DIV] = imx_clk_divider("uart4_pre_div", "uart4_cg", base + 0xb100, 16, 3);
+       clks[IMX7D_UART5_ROOT_PRE_DIV] = imx_clk_divider("uart5_pre_div", "uart5_cg", base + 0xb180, 16, 3);
+       clks[IMX7D_UART6_ROOT_PRE_DIV] = imx_clk_divider("uart6_pre_div", "uart6_cg", base + 0xb200, 16, 3);
+       clks[IMX7D_UART7_ROOT_PRE_DIV] = imx_clk_divider("uart7_pre_div", "uart7_cg", base + 0xb280, 16, 3);
+       clks[IMX7D_ECSPI1_ROOT_PRE_DIV] = imx_clk_divider("ecspi1_pre_div", "ecspi1_cg", base + 0xb300, 16, 3);
+       clks[IMX7D_ECSPI2_ROOT_PRE_DIV] = imx_clk_divider("ecspi2_pre_div", "ecspi2_cg", base + 0xb380, 16, 3);
+       clks[IMX7D_ECSPI3_ROOT_PRE_DIV] = imx_clk_divider("ecspi3_pre_div", "ecspi3_cg", base + 0xb400, 16, 3);
+       clks[IMX7D_ECSPI4_ROOT_PRE_DIV] = imx_clk_divider("ecspi4_pre_div", "ecspi4_cg", base + 0xb480, 16, 3);
+       clks[IMX7D_PWM1_ROOT_PRE_DIV] = imx_clk_divider("pwm1_pre_div", "pwm1_cg", base + 0xb500, 16, 3);
+       clks[IMX7D_PWM2_ROOT_PRE_DIV] = imx_clk_divider("pwm2_pre_div", "pwm2_cg", base + 0xb580, 16, 3);
+       clks[IMX7D_PWM3_ROOT_PRE_DIV] = imx_clk_divider("pwm3_pre_div", "pwm3_cg", base + 0xb600, 16, 3);
+       clks[IMX7D_PWM4_ROOT_PRE_DIV] = imx_clk_divider("pwm4_pre_div", "pwm4_cg", base + 0xb680, 16, 3);
+       clks[IMX7D_FLEXTIMER1_ROOT_PRE_DIV] = imx_clk_divider("flextimer1_pre_div", "flextimer1_cg", base + 0xb700, 16, 3);
+       clks[IMX7D_FLEXTIMER2_ROOT_PRE_DIV] = imx_clk_divider("flextimer2_pre_div", "flextimer2_cg", base + 0xb780, 16, 3);
+       clks[IMX7D_SIM1_ROOT_PRE_DIV] = imx_clk_divider("sim1_pre_div", "sim1_cg", base + 0xb800, 16, 3);
+       clks[IMX7D_SIM2_ROOT_PRE_DIV] = imx_clk_divider("sim2_pre_div", "sim2_cg", base + 0xb880, 16, 3);
+       clks[IMX7D_GPT1_ROOT_PRE_DIV] = imx_clk_divider("gpt1_pre_div", "gpt1_cg", base + 0xb900, 16, 3);
+       clks[IMX7D_GPT2_ROOT_PRE_DIV] = imx_clk_divider("gpt2_pre_div", "gpt2_cg", base + 0xb980, 16, 3);
+       clks[IMX7D_GPT3_ROOT_PRE_DIV] = imx_clk_divider("gpt3_pre_div", "gpt3_cg", base + 0xba00, 16, 3);
+       clks[IMX7D_GPT4_ROOT_PRE_DIV] = imx_clk_divider("gpt4_pre_div", "gpt4_cg", base + 0xba80, 16, 3);
+       clks[IMX7D_TRACE_ROOT_PRE_DIV] = imx_clk_divider("trace_pre_div", "trace_cg", base + 0xbb00, 16, 3);
+       clks[IMX7D_WDOG_ROOT_PRE_DIV] = imx_clk_divider("wdog_pre_div", "wdog_cg", base + 0xbb80, 16, 3);
+       clks[IMX7D_CSI_MCLK_ROOT_PRE_DIV] = imx_clk_divider("csi_mclk_pre_div", "csi_mclk_cg", base + 0xbc00, 16, 3);
+       clks[IMX7D_AUDIO_MCLK_ROOT_PRE_DIV] = imx_clk_divider("audio_mclk_pre_div", "audio_mclk_cg", base + 0xbc80, 16, 3);
+       clks[IMX7D_WRCLK_ROOT_PRE_DIV] = imx_clk_divider("wrclk_pre_div", "wrclk_cg", base + 0xbd00, 16, 3);
+       clks[IMX7D_CLKO1_ROOT_PRE_DIV] = imx_clk_divider("clko1_pre_div", "clko1_cg", base + 0xbd80, 16, 3);
+       clks[IMX7D_CLKO2_ROOT_PRE_DIV] = imx_clk_divider("clko2_pre_div", "clko2_cg", base + 0xbe00, 16, 3);
+
+       clks[IMX7D_ARM_A7_ROOT_DIV] = imx_clk_divider("arm_a7_div", "arm_a7_cg", base + 0x8000, 0, 3);
+       clks[IMX7D_ARM_M4_ROOT_DIV] = imx_clk_divider("arm_m4_div", "arm_m4_cg", base + 0x8080, 0, 3);
+       clks[IMX7D_ARM_M0_ROOT_DIV] = imx_clk_divider("arm_m0_div", "arm_m0_cg", base + 0x8100, 0, 3);
+       clks[IMX7D_MAIN_AXI_ROOT_DIV] = imx_clk_divider("axi_post_div", "axi_pre_div", base + 0x8800, 0, 6);
+       clks[IMX7D_DISP_AXI_ROOT_DIV] = imx_clk_divider("disp_axi_post_div", "disp_axi_pre_div", base + 0x8880, 0, 6);
+       clks[IMX7D_ENET_AXI_ROOT_DIV] = imx_clk_divider("enet_axi_post_div", "enet_axi_pre_div", base + 0x8900, 0, 6);
+       clks[IMX7D_NAND_USDHC_BUS_ROOT_DIV] = imx_clk_divider("nand_usdhc_post_div", "nand_usdhc_pre_div", base + 0x8980, 0, 6);
+       clks[IMX7D_AHB_CHANNEL_ROOT_DIV] = imx_clk_divider("ahb_post_div", "ahb_pre_div", base + 0x9000, 0, 6);
+       clks[IMX7D_DRAM_ROOT_DIV] = imx_clk_divider("dram_post_div", "dram_cg", base + 0x9880, 0, 3);
+       clks[IMX7D_DRAM_PHYM_ALT_ROOT_DIV] = imx_clk_divider("dram_phym_alt_post_div", "dram_phym_alt_pre_div", base + 0xa000, 0, 3);
+       clks[IMX7D_DRAM_ALT_ROOT_DIV] = imx_clk_divider("dram_alt_post_div", "dram_alt_pre_div", base + 0xa080, 0, 3);
+       clks[IMX7D_USB_HSIC_ROOT_DIV] = imx_clk_divider("usb_hsic_post_div", "usb_hsic_pre_div", base + 0xa100, 0, 6);
+       clks[IMX7D_PCIE_CTRL_ROOT_DIV] = imx_clk_divider("pcie_ctrl_post_div", "pcie_ctrl_pre_div", base + 0xa180, 0, 6);
+       clks[IMX7D_PCIE_PHY_ROOT_DIV] = imx_clk_divider("pcie_phy_post_div", "pcie_phy_pre_div", base + 0xa200, 0, 6);
+       clks[IMX7D_EPDC_PIXEL_ROOT_DIV] = imx_clk_divider("epdc_pixel_post_div", "epdc_pixel_pre_div", base + 0xa280, 0, 6);
+       clks[IMX7D_LCDIF_PIXEL_ROOT_DIV] = imx_clk_divider("lcdif_pixel_post_div", "lcdif_pixel_pre_div", base + 0xa300, 0, 6);
+       clks[IMX7D_MIPI_DSI_ROOT_DIV] = imx_clk_divider("mipi_dsi_post_div", "mipi_dsi_pre_div", base + 0xa380, 0, 6);
+       clks[IMX7D_MIPI_CSI_ROOT_DIV] = imx_clk_divider("mipi_csi_post_div", "mipi_csi_pre_div", base + 0xa400, 0, 6);
+       clks[IMX7D_MIPI_DPHY_ROOT_DIV] = imx_clk_divider("mipi_dphy_post_div", "mipi_csi_dphy_div", base + 0xa480, 0, 6);
+       clks[IMX7D_SAI1_ROOT_DIV] = imx_clk_divider("sai1_post_div", "sai1_pre_div", base + 0xa500, 0, 6);
+       clks[IMX7D_SAI2_ROOT_DIV] = imx_clk_divider("sai2_post_div", "sai2_pre_div", base + 0xa580, 0, 6);
+       clks[IMX7D_SAI3_ROOT_DIV] = imx_clk_divider("sai3_post_div", "sai3_pre_div", base + 0xa600, 0, 6);
+       clks[IMX7D_SPDIF_ROOT_DIV] = imx_clk_divider("spdif_post_div", "spdif_pre_div", base + 0xa680, 0, 6);
+       clks[IMX7D_ENET1_REF_ROOT_DIV] = imx_clk_divider("enet1_ref_post_div", "enet1_ref_pre_div", base + 0xa700, 0, 6);
+       clks[IMX7D_ENET1_TIME_ROOT_DIV] = imx_clk_divider("enet1_time_post_div", "enet1_time_pre_div", base + 0xa780, 0, 6);
+       clks[IMX7D_ENET2_REF_ROOT_DIV] = imx_clk_divider("enet2_ref_post_div", "enet2_ref_pre_div", base + 0xa800, 0, 6);
+       clks[IMX7D_ENET2_TIME_ROOT_DIV] = imx_clk_divider("enet2_time_post_div", "enet2_time_pre_div", base + 0xa880, 0, 6);
+       clks[IMX7D_ENET_PHY_REF_ROOT_DIV] = imx_clk_divider("enet_phy_ref_post_div", "enet_phy_ref_pre_div", base + 0xa900, 0, 6);
+       clks[IMX7D_EIM_ROOT_DIV] = imx_clk_divider("eim_post_div", "eim_pre_div", base + 0xa980, 0, 6);
+       clks[IMX7D_NAND_ROOT_DIV] = imx_clk_divider("nand_post_div", "nand_pre_div", base + 0xaa00, 0, 6);
+       clks[IMX7D_QSPI_ROOT_DIV] = imx_clk_divider("qspi_post_div", "qspi_pre_div", base + 0xaa80, 0, 6);
+       clks[IMX7D_USDHC1_ROOT_DIV] = imx_clk_divider("usdhc1_post_div", "usdhc1_pre_div", base + 0xab00, 0, 6);
+       clks[IMX7D_USDHC2_ROOT_DIV] = imx_clk_divider("usdhc2_post_div", "usdhc2_pre_div", base + 0xab80, 0, 6);
+       clks[IMX7D_USDHC3_ROOT_DIV] = imx_clk_divider("usdhc3_post_div", "usdhc3_pre_div", base + 0xac00, 0, 6);
+       clks[IMX7D_CAN1_ROOT_DIV] = imx_clk_divider("can1_post_div", "can1_pre_div", base + 0xac80, 0, 6);
+       clks[IMX7D_CAN2_ROOT_DIV] = imx_clk_divider("can2_post_div", "can2_pre_div", base + 0xad00, 0, 6);
+       clks[IMX7D_I2C1_ROOT_DIV] = imx_clk_divider("i2c1_post_div", "i2c1_pre_div", base + 0xad80, 0, 6);
+       clks[IMX7D_I2C2_ROOT_DIV] = imx_clk_divider("i2c2_post_div", "i2c2_pre_div", base + 0xae00, 0, 6);
+       clks[IMX7D_I2C3_ROOT_DIV] = imx_clk_divider("i2c3_post_div", "i2c3_pre_div", base + 0xae80, 0, 6);
+       clks[IMX7D_I2C4_ROOT_DIV] = imx_clk_divider("i2c4_post_div", "i2c4_pre_div", base + 0xaf00, 0, 6);
+       clks[IMX7D_UART1_ROOT_DIV] = imx_clk_divider("uart1_post_div", "uart1_pre_div", base + 0xaf80, 0, 6);
+       clks[IMX7D_UART2_ROOT_DIV] = imx_clk_divider("uart2_post_div", "uart2_pre_div", base + 0xb000, 0, 6);
+       clks[IMX7D_UART3_ROOT_DIV] = imx_clk_divider("uart3_post_div", "uart3_pre_div", base + 0xb080, 0, 6);
+       clks[IMX7D_UART4_ROOT_DIV] = imx_clk_divider("uart4_post_div", "uart4_pre_div", base + 0xb100, 0, 6);
+       clks[IMX7D_UART5_ROOT_DIV] = imx_clk_divider("uart5_post_div", "uart5_pre_div", base + 0xb180, 0, 6);
+       clks[IMX7D_UART6_ROOT_DIV] = imx_clk_divider("uart6_post_div", "uart6_pre_div", base + 0xb200, 0, 6);
+       clks[IMX7D_UART7_ROOT_DIV] = imx_clk_divider("uart7_post_div", "uart7_pre_div", base + 0xb280, 0, 6);
+       clks[IMX7D_ECSPI1_ROOT_DIV] = imx_clk_divider("ecspi1_post_div", "ecspi1_pre_div", base + 0xb300, 0, 6);
+       clks[IMX7D_ECSPI2_ROOT_DIV] = imx_clk_divider("ecspi2_post_div", "ecspi2_pre_div", base + 0xb380, 0, 6);
+       clks[IMX7D_ECSPI3_ROOT_DIV] = imx_clk_divider("ecspi3_post_div", "ecspi3_pre_div", base + 0xb400, 0, 6);
+       clks[IMX7D_ECSPI4_ROOT_DIV] = imx_clk_divider("ecspi4_post_div", "ecspi4_pre_div", base + 0xb480, 0, 6);
+       clks[IMX7D_PWM1_ROOT_DIV] = imx_clk_divider("pwm1_post_div", "pwm1_pre_div", base + 0xb500, 0, 6);
+       clks[IMX7D_PWM2_ROOT_DIV] = imx_clk_divider("pwm2_post_div", "pwm2_pre_div", base + 0xb580, 0, 6);
+       clks[IMX7D_PWM3_ROOT_DIV] = imx_clk_divider("pwm3_post_div", "pwm3_pre_div", base + 0xb600, 0, 6);
+       clks[IMX7D_PWM4_ROOT_DIV] = imx_clk_divider("pwm4_post_div", "pwm4_pre_div", base + 0xb680, 0, 6);
+       clks[IMX7D_FLEXTIMER1_ROOT_DIV] = imx_clk_divider("flextimer1_post_div", "flextimer1_pre_div", base + 0xb700, 0, 6);
+       clks[IMX7D_FLEXTIMER2_ROOT_DIV] = imx_clk_divider("flextimer2_post_div", "flextimer2_pre_div", base + 0xb780, 0, 6);
+       clks[IMX7D_SIM1_ROOT_DIV] = imx_clk_divider("sim1_post_div", "sim1_pre_div", base + 0xb800, 0, 6);
+       clks[IMX7D_SIM2_ROOT_DIV] = imx_clk_divider("sim2_post_div", "sim2_pre_div", base + 0xb880, 0, 6);
+       clks[IMX7D_GPT1_ROOT_DIV] = imx_clk_divider("gpt1_post_div", "gpt1_pre_div", base + 0xb900, 0, 6);
+       clks[IMX7D_GPT2_ROOT_DIV] = imx_clk_divider("gpt2_post_div", "gpt2_pre_div", base + 0xb980, 0, 6);
+       clks[IMX7D_GPT3_ROOT_DIV] = imx_clk_divider("gpt3_post_div", "gpt3_pre_div", base + 0xba00, 0, 6);
+       clks[IMX7D_GPT4_ROOT_DIV] = imx_clk_divider("gpt4_post_div", "gpt4_pre_div", base + 0xba80, 0, 6);
+       clks[IMX7D_TRACE_ROOT_DIV] = imx_clk_divider("trace_post_div", "trace_pre_div", base + 0xbb00, 0, 6);
+       clks[IMX7D_WDOG_ROOT_DIV] = imx_clk_divider("wdog_post_div", "wdog_pre_div", base + 0xbb80, 0, 6);
+       clks[IMX7D_CSI_MCLK_ROOT_DIV] = imx_clk_divider("csi_mclk_post_div", "csi_mclk_pre_div", base + 0xbc00, 0, 6);
+       clks[IMX7D_AUDIO_MCLK_ROOT_DIV] = imx_clk_divider("audio_mclk_post_div", "audio_mclk_pre_div", base + 0xbc80, 0, 6);
+       clks[IMX7D_WRCLK_ROOT_DIV] = imx_clk_divider("wrclk_post_div", "wrclk_pre_div", base + 0xbd00, 0, 6);
+       clks[IMX7D_CLKO1_ROOT_DIV] = imx_clk_divider("clko1_post_div", "clko1_pre_div", base + 0xbd80, 0, 6);
+       clks[IMX7D_CLKO2_ROOT_DIV] = imx_clk_divider("clko2_post_div", "clko2_pre_div", base + 0xbe00, 0, 6);
+
+       clks[IMX7D_ARM_A7_ROOT_CLK] = imx_clk_gate2("arm_a7_root_clk", "arm_a7_div", base + 0x4000, 0);
+       clks[IMX7D_ARM_M4_ROOT_CLK] = imx_clk_gate2("arm_m4_root_clk", "arm_m4_div", base + 0x4010, 0);
+       clks[IMX7D_ARM_M0_ROOT_CLK] = imx_clk_gate2("arm_m0_root_clk", "arm_m0_div", base + 0x4020, 0);
+       clks[IMX7D_MAIN_AXI_ROOT_CLK] = imx_clk_gate2("main_axi_root_clk", "axi_post_div", base + 0x4040, 0);
+       clks[IMX7D_DISP_AXI_ROOT_CLK] = imx_clk_gate2("disp_axi_root_clk", "disp_axi_post_div", base + 0x4050, 0);
+       clks[IMX7D_ENET_AXI_ROOT_CLK] = imx_clk_gate2("enet_axi_root_clk", "enet_axi_post_div", base + 0x4060, 0);
+       clks[IMX7D_OCRAM_CLK] = imx_clk_gate2("ocram_clk", "axi_post_div", base + 0x4110, 0);
+       clks[IMX7D_OCRAM_S_CLK] = imx_clk_gate2("ocram_s_clk", "ahb_post_div", base + 0x4120, 0);
+       clks[IMX7D_NAND_USDHC_BUS_ROOT_CLK] = imx_clk_gate2("nand_usdhc_root_clk", "nand_usdhc_post_div", base + 0x4130, 0);
+       clks[IMX7D_AHB_CHANNEL_ROOT_CLK] = imx_clk_gate2("ahb_root_clk", "ahb_post_div", base + 0x4200, 0);
+       clks[IMX7D_DRAM_ROOT_CLK] = imx_clk_gate2("dram_root_clk", "dram_post_div", base + 0x4130, 0);
+       clks[IMX7D_DRAM_PHYM_ROOT_CLK] = imx_clk_gate2("dram_phym_root_clk", "dram_phym_cg", base + 0x4130, 0);
+       clks[IMX7D_DRAM_PHYM_ALT_ROOT_CLK] = imx_clk_gate2("dram_phym_alt_root_clk", "dram_phym_alt_post_div", base + 0x4130, 0);
+       clks[IMX7D_DRAM_ALT_ROOT_CLK] = imx_clk_gate2("dram_alt_root_clk", "dram_alt_post_div", base + 0x4130, 0);
+       clks[IMX7D_USB_HSIC_ROOT_CLK] = imx_clk_gate2("usb_hsic_root_clk", "usb_hsic_post_div", base + 0x4420, 0);
+       clks[IMX7D_PCIE_CTRL_ROOT_CLK] = imx_clk_gate2("pcie_ctrl_root_clk", "pcie_ctrl_post_div", base + 0x4600, 0);
+       clks[IMX7D_PCIE_PHY_ROOT_CLK] = imx_clk_gate2("pcie_phy_root_clk", "pcie_phy_post_div", base + 0x4600, 0);
+       clks[IMX7D_EPDC_PIXEL_ROOT_CLK] = imx_clk_gate2("epdc_pixel_root_clk", "epdc_pixel_post_div", base + 0x44a0, 0);
+       clks[IMX7D_LCDIF_PIXEL_ROOT_CLK] = imx_clk_gate2("lcdif_pixel_root_clk", "lcdif_pixel_post_div", base + 0x44b0, 0);
+       clks[IMX7D_MIPI_DSI_ROOT_CLK] = imx_clk_gate2("mipi_dsi_root_clk", "mipi_dsi_post_div", base + 0x4650, 0);
+       clks[IMX7D_MIPI_CSI_ROOT_CLK] = imx_clk_gate2("mipi_csi_root_clk", "mipi_csi_post_div", base + 0x4640, 0);
+       clks[IMX7D_MIPI_DPHY_ROOT_CLK] = imx_clk_gate2("mipi_dphy_root_clk", "mipi_dphy_post_div", base + 0x4660, 0);
+       clks[IMX7D_SAI1_ROOT_CLK] = imx_clk_gate2("sai1_root_clk", "sai1_post_div", base + 0x48c0, 0);
+       clks[IMX7D_SAI2_ROOT_CLK] = imx_clk_gate2("sai2_root_clk", "sai2_post_div", base + 0x48d0, 0);
+       clks[IMX7D_SAI3_ROOT_CLK] = imx_clk_gate2("sai3_root_clk", "sai3_post_div", base + 0x48e0, 0);
+       clks[IMX7D_SPDIF_ROOT_CLK] = imx_clk_gate2("spdif_root_clk", "spdif_post_div", base + 0x44d0, 0);
+       clks[IMX7D_ENET1_REF_ROOT_CLK] = imx_clk_gate2("enet1_ref_root_clk", "enet1_ref_post_div", base + 0x44e0, 0);
+       clks[IMX7D_ENET1_TIME_ROOT_CLK] = imx_clk_gate2("enet1_time_root_clk", "enet1_time_post_div", base + 0x44f0, 0);
+       clks[IMX7D_ENET2_REF_ROOT_CLK] = imx_clk_gate2("enet2_ref_root_clk", "enet2_ref_post_div", base + 0x4500, 0);
+       clks[IMX7D_ENET2_TIME_ROOT_CLK] = imx_clk_gate2("enet2_time_root_clk", "enet2_time_post_div", base + 0x4510, 0);
+       clks[IMX7D_ENET_PHY_REF_ROOT_CLK] = imx_clk_gate2("enet_phy_ref_root_clk", "enet_phy_ref_post_div", base + 0x4520, 0);
+       clks[IMX7D_EIM_ROOT_CLK] = imx_clk_gate2("eim_root_clk", "eim_post_div", base + 0x4160, 0);
+       clks[IMX7D_NAND_ROOT_CLK] = imx_clk_gate2("nand_root_clk", "nand_post_div", base + 0x4140, 0);
+       clks[IMX7D_QSPI_ROOT_CLK] = imx_clk_gate2("qspi_root_clk", "qspi_post_div", base + 0x4150, 0);
+       clks[IMX7D_USDHC1_ROOT_CLK] = imx_clk_gate2("usdhc1_root_clk", "usdhc1_post_div", base + 0x46c0, 0);
+       clks[IMX7D_USDHC2_ROOT_CLK] = imx_clk_gate2("usdhc2_root_clk", "usdhc2_post_div", base + 0x46d0, 0);
+       clks[IMX7D_USDHC3_ROOT_CLK] = imx_clk_gate2("usdhc3_root_clk", "usdhc3_post_div", base + 0x46e0, 0);
+       clks[IMX7D_CAN1_ROOT_CLK] = imx_clk_gate2("can1_root_clk", "can1_post_div", base + 0x4740, 0);
+       clks[IMX7D_CAN2_ROOT_CLK] = imx_clk_gate2("can2_root_clk", "can2_post_div", base + 0x4750, 0);
+       clks[IMX7D_I2C1_ROOT_CLK] = imx_clk_gate2("i2c1_root_clk", "i2c1_post_div", base + 0x4880, 0);
+       clks[IMX7D_I2C2_ROOT_CLK] = imx_clk_gate2("i2c2_root_clk", "i2c2_post_div", base + 0x4890, 0);
+       clks[IMX7D_I2C3_ROOT_CLK] = imx_clk_gate2("i2c3_root_clk", "i2c3_post_div", base + 0x48a0, 0);
+       clks[IMX7D_I2C4_ROOT_CLK] = imx_clk_gate2("i2c4_root_clk", "i2c4_post_div", base + 0x48b0, 0);
+       clks[IMX7D_UART1_ROOT_CLK] = imx_clk_gate2("uart1_root_clk", "uart1_post_div", base + 0x4940, 0);
+       clks[IMX7D_UART2_ROOT_CLK] = imx_clk_gate2("uart2_root_clk", "uart2_post_div", base + 0x4950, 0);
+       clks[IMX7D_UART3_ROOT_CLK] = imx_clk_gate2("uart3_root_clk", "uart3_post_div", base + 0x4960, 0);
+       clks[IMX7D_UART4_ROOT_CLK] = imx_clk_gate2("uart4_root_clk", "uart4_post_div", base + 0x4970, 0);
+       clks[IMX7D_UART5_ROOT_CLK] = imx_clk_gate2("uart5_root_clk", "uart5_post_div", base + 0x4980, 0);
+       clks[IMX7D_UART6_ROOT_CLK] = imx_clk_gate2("uart6_root_clk", "uart6_post_div", base + 0x4990, 0);
+       clks[IMX7D_UART7_ROOT_CLK] = imx_clk_gate2("uart7_root_clk", "uart7_post_div", base + 0x49a0, 0);
+       clks[IMX7D_ECSPI1_ROOT_CLK] = imx_clk_gate2("ecspi1_root_clk", "ecspi1_post_div", base + 0x4780, 0);
+       clks[IMX7D_ECSPI2_ROOT_CLK] = imx_clk_gate2("ecspi2_root_clk", "ecspi2_post_div", base + 0x4790, 0);
+       clks[IMX7D_ECSPI3_ROOT_CLK] = imx_clk_gate2("ecspi3_root_clk", "ecspi3_post_div", base + 0x47a0, 0);
+       clks[IMX7D_ECSPI4_ROOT_CLK] = imx_clk_gate2("ecspi4_root_clk", "ecspi4_post_div", base + 0x47b0, 0);
+       clks[IMX7D_PWM1_ROOT_CLK] = imx_clk_gate2("pwm1_root_clk", "pwm1_post_div", base + 0x4840, 0);
+       clks[IMX7D_PWM2_ROOT_CLK] = imx_clk_gate2("pwm2_root_clk", "pwm2_post_div", base + 0x4850, 0);
+       clks[IMX7D_PWM3_ROOT_CLK] = imx_clk_gate2("pwm3_root_clk", "pwm3_post_div", base + 0x4860, 0);
+       clks[IMX7D_PWM4_ROOT_CLK] = imx_clk_gate2("pwm4_root_clk", "pwm4_post_div", base + 0x4870, 0);
+       clks[IMX7D_FLEXTIMER1_ROOT_CLK] = imx_clk_gate2("flextimer1_root_clk", "flextimer1_post_div", base + 0x4800, 0);
+       clks[IMX7D_FLEXTIMER2_ROOT_CLK] = imx_clk_gate2("flextimer2_root_clk", "flextimer2_post_div", base + 0x4810, 0);
+       clks[IMX7D_SIM1_ROOT_CLK] = imx_clk_gate2("sim1_root_clk", "sim1_post_div", base + 0x4900, 0);
+       clks[IMX7D_SIM2_ROOT_CLK] = imx_clk_gate2("sim2_root_clk", "sim2_post_div", base + 0x4910, 0);
+       clks[IMX7D_GPT1_ROOT_CLK] = imx_clk_gate2("gpt1_root_clk", "gpt1_post_div", base + 0x47c0, 0);
+       clks[IMX7D_GPT2_ROOT_CLK] = imx_clk_gate2("gpt2_root_clk", "gpt2_post_div", base + 0x47d0, 0);
+       clks[IMX7D_GPT3_ROOT_CLK] = imx_clk_gate2("gpt3_root_clk", "gpt3_post_div", base + 0x47e0, 0);
+       clks[IMX7D_GPT4_ROOT_CLK] = imx_clk_gate2("gpt4_root_clk", "gpt4_post_div", base + 0x47f0, 0);
+       clks[IMX7D_TRACE_ROOT_CLK] = imx_clk_gate2("trace_root_clk", "trace_post_div", base + 0x4300, 0);
+       clks[IMX7D_WDOG1_ROOT_CLK] = imx_clk_gate2("wdog1_root_clk", "wdog_post_div", base + 0x49c0, 0);
+       clks[IMX7D_WDOG2_ROOT_CLK] = imx_clk_gate2("wdog2_root_clk", "wdog_post_div", base + 0x49d0, 0);
+       clks[IMX7D_WDOG3_ROOT_CLK] = imx_clk_gate2("wdog3_root_clk", "wdog_post_div", base + 0x49e0, 0);
+       clks[IMX7D_WDOG4_ROOT_CLK] = imx_clk_gate2("wdog4_root_clk", "wdog_post_div", base + 0x49f0, 0);
+       clks[IMX7D_CSI_MCLK_ROOT_CLK] = imx_clk_gate2("csi_mclk_root_clk", "csi_mclk_post_div", base + 0x4490, 0);
+       clks[IMX7D_AUDIO_MCLK_ROOT_CLK] = imx_clk_gate2("audio_mclk_root_clk", "audio_mclk_post_div", base + 0x4790, 0);
+       clks[IMX7D_WRCLK_ROOT_CLK] = imx_clk_gate2("wrclk_root_clk", "wrclk_post_div", base + 0x47a0, 0);
+
+       clks[IMX7D_GPT_3M_CLK] = imx_clk_fixed_factor("gpt_3m", "osc", 1, 8);
+
+       for (i = 0; i < ARRAY_SIZE(clks); i++)
+               if (IS_ERR(clks[i]))
+                       pr_err("i.MX7D clk %d: register failed with %ld\n",
+                                       i, PTR_ERR(clks[i]));
+
+       clk_data.clks = clks;
+       clk_data.clk_num = ARRAY_SIZE(clks);
+       of_clk_add_provider(np, of_clk_src_onecell_get, &clk_data);
+
+       /* TO BE FIXED LATER
+        * Enable all clock to bring up imx7, otherwise system will be halt and block
+        * the other part upstream Because imx7d clock design changed, clock framework
+        * need do a little modify.
+        * Dong Aisheng is working on this. After that, this part need be changed.
+        */
+       for (i = 0; i < IMX7D_CLK_END; i++)
+               clk_prepare_enable(clks[i]);
+
+       /* use old gpt clk setting, gpt1 root clk must be twice as gpt counter freq */
+       clk_set_parent(clks[IMX7D_GPT1_ROOT_SRC], clks[IMX7D_OSC_24M_CLK]);
+
+       /*
+        * init enet clock source:
+        *      AXI clock source is 250MHz
+        *      Phy refrence clock is 25MHz
+        *      1588 time clock source is 100MHz
+        */
+       clk_set_parent(clks[IMX7D_ENET_AXI_ROOT_SRC], clks[IMX7D_PLL_ENET_MAIN_250M_CLK]);
+       clk_set_parent(clks[IMX7D_ENET_PHY_REF_ROOT_SRC], clks[IMX7D_PLL_ENET_MAIN_25M_CLK]);
+       clk_set_parent(clks[IMX7D_ENET1_TIME_ROOT_SRC], clks[IMX7D_PLL_ENET_MAIN_100M_CLK]);
+       clk_set_parent(clks[IMX7D_ENET2_TIME_ROOT_SRC], clks[IMX7D_PLL_ENET_MAIN_100M_CLK]);
+
+       /* set uart module clock's parent clock source that must be great then 80MHz */
+       clk_set_parent(clks[IMX7D_UART1_ROOT_SRC], clks[IMX7D_OSC_24M_CLK]);
+
+}
+CLK_OF_DECLARE(imx7d, "fsl,imx7d-ccm", imx7d_clocks_init);
similarity index 75%
rename from arch/arm/mach-imx/clk-pllv1.c
rename to drivers/clk/imx/clk-pllv1.c
index d21d14ca46c1786b4cc42f47976cbdc6cc384d5d..c34ad8a611dd53e6f1465a82e8ad1c1f783b93f7 100644 (file)
@@ -6,8 +6,6 @@
 #include <linux/err.h>
 
 #include "clk.h"
-#include "common.h"
-#include "hardware.h"
 
 /**
  * pll v1
 struct clk_pllv1 {
        struct clk_hw   hw;
        void __iomem    *base;
+       enum imx_pllv1_type type;
 };
 
 #define to_clk_pllv1(clk) (container_of(clk, struct clk_pllv1, clk))
 
-static inline bool mfn_is_negative(unsigned int mfn)
+static inline bool is_imx1_pllv1(struct clk_pllv1 *pll)
 {
-       return !cpu_is_mx1() && !cpu_is_mx21() && (mfn & MFN_SIGN);
+       return pll->type == IMX_PLLV1_IMX1;
+}
+
+static inline bool is_imx21_pllv1(struct clk_pllv1 *pll)
+{
+       return pll->type == IMX_PLLV1_IMX21;
+}
+
+static inline bool is_imx27_pllv1(struct clk_pllv1 *pll)
+{
+       return pll->type == IMX_PLLV1_IMX27;
+}
+
+static inline bool mfn_is_negative(struct clk_pllv1 *pll, unsigned int mfn)
+{
+       return !is_imx1_pllv1(pll) && !is_imx21_pllv1(pll) && (mfn & MFN_SIGN);
 }
 
 static unsigned long clk_pllv1_recalc_rate(struct clk_hw *hw,
@@ -71,8 +85,8 @@ static unsigned long clk_pllv1_recalc_rate(struct clk_hw *hw,
         * 2's complements number.
         * On i.MX27 the bit 9 is the sign bit.
         */
-       if (mfn_is_negative(mfn)) {
-               if (cpu_is_mx27())
+       if (mfn_is_negative(pll, mfn)) {
+               if (is_imx27_pllv1(pll))
                        mfn_abs = mfn & MFN_MASK;
                else
                        mfn_abs = BIT(MFN_BITS) - mfn;
@@ -85,7 +99,7 @@ static unsigned long clk_pllv1_recalc_rate(struct clk_hw *hw,
 
        do_div(ll, mfd + 1);
 
-       if (mfn_is_negative(mfn))
+       if (mfn_is_negative(pll, mfn))
                ll = -ll;
 
        ll = (rate * mfi) + ll;
@@ -97,8 +111,8 @@ static struct clk_ops clk_pllv1_ops = {
        .recalc_rate = clk_pllv1_recalc_rate,
 };
 
-struct clk *imx_clk_pllv1(const char *name, const char *parent,
-               void __iomem *base)
+struct clk *imx_clk_pllv1(enum imx_pllv1_type type, const char *name,
+               const char *parent, void __iomem *base)
 {
        struct clk_pllv1 *pll;
        struct clk *clk;
@@ -109,6 +123,7 @@ struct clk *imx_clk_pllv1(const char *name, const char *parent,
                return ERR_PTR(-ENOMEM);
 
        pll->base = base;
+       pll->type = type;
 
        init.name = name;
        init.ops = &clk_pllv1_ops;
similarity index 96%
rename from arch/arm/mach-imx/clk-pllv3.c
rename to drivers/clk/imx/clk-pllv3.c
index 641ebc50892044a3da816b8b68cc058563f83543..f0d15fb9d7836d7de34338d31b1edb4fe69923cd 100644 (file)
 
 #define BM_PLL_POWER           (0x1 << 12)
 #define BM_PLL_LOCK            (0x1 << 31)
+#define IMX7_ENET_PLL_POWER    (0x1 << 5)
 
 /**
  * struct clk_pllv3 - IMX PLL clock version 3
  * @clk_hw:     clock source
  * @base:       base address of PLL registers
  * @powerup_set: set POWER bit to power up the PLL
+ * @powerdown:   pll powerdown offset bit
  * @div_mask:   mask of divider bits
  * @div_shift:  shift of divider bits
  *
@@ -40,6 +42,7 @@ struct clk_pllv3 {
        struct clk_hw   hw;
        void __iomem    *base;
        bool            powerup_set;
+       u32             powerdown;
        u32             div_mask;
        u32             div_shift;
 };
@@ -49,7 +52,7 @@ struct clk_pllv3 {
 static int clk_pllv3_wait_lock(struct clk_pllv3 *pll)
 {
        unsigned long timeout = jiffies + msecs_to_jiffies(10);
-       u32 val = readl_relaxed(pll->base) & BM_PLL_POWER;
+       u32 val = readl_relaxed(pll->base) & pll->powerdown;
 
        /* No need to wait for lock when pll is not powered up */
        if ((pll->powerup_set && !val) || (!pll->powerup_set && val))
@@ -215,7 +218,7 @@ static long clk_pllv3_av_round_rate(struct clk_hw *hw, unsigned long rate,
        unsigned long max_rate = parent_rate * 54;
        u32 div;
        u32 mfn, mfd = 1000000;
-       s64 temp64;
+       u64 temp64;
 
        if (rate > max_rate)
                rate = max_rate;
@@ -239,7 +242,7 @@ static int clk_pllv3_av_set_rate(struct clk_hw *hw, unsigned long rate,
        unsigned long max_rate = parent_rate * 54;
        u32 val, div;
        u32 mfn, mfd = 1000000;
-       s64 temp64;
+       u64 temp64;
 
        if (rate < min_rate || rate > max_rate)
                return -EINVAL;
@@ -293,6 +296,8 @@ struct clk *imx_clk_pllv3(enum imx_pllv3_type type, const char *name,
        if (!pll)
                return ERR_PTR(-ENOMEM);
 
+       pll->powerdown = BM_PLL_POWER;
+
        switch (type) {
        case IMX_PLLV3_SYS:
                ops = &clk_pllv3_sys_ops;
@@ -306,6 +311,8 @@ struct clk *imx_clk_pllv3(enum imx_pllv3_type type, const char *name,
        case IMX_PLLV3_AV:
                ops = &clk_pllv3_av_ops;
                break;
+       case IMX_PLLV3_ENET_IMX7:
+               pll->powerdown = IMX7_ENET_PLL_POWER;
        case IMX_PLLV3_ENET:
                ops = &clk_pllv3_enet_ops;
                break;
similarity index 98%
rename from arch/arm/mach-imx/clk-vf610.c
rename to drivers/clk/imx/clk-vf610.c
index 61876ed6e11e975c4e1be56f1f56185bfc8d51db..bff45ead7389976ecac2da81765e44d0753028cf 100644 (file)
@@ -118,6 +118,7 @@ static struct clk_onecell_data clk_data;
 static unsigned int const clks_init_on[] __initconst = {
        VF610_CLK_SYS_BUS,
        VF610_CLK_DDR_SEL,
+       VF610_CLK_DAP,
 };
 
 static struct clk * __init vf610_get_fixed_clock(
@@ -272,6 +273,8 @@ static void __init vf610_clocks_init(struct device_node *ccm_node)
 
        clk[VF610_CLK_I2C0] = imx_clk_gate2("i2c0", "ipg_bus", CCM_CCGR4, CCM_CCGRx_CGn(6));
        clk[VF610_CLK_I2C1] = imx_clk_gate2("i2c1", "ipg_bus", CCM_CCGR4, CCM_CCGRx_CGn(7));
+       clk[VF610_CLK_I2C2] = imx_clk_gate2("i2c2", "ipg_bus", CCM_CCGR10, CCM_CCGRx_CGn(6));
+       clk[VF610_CLK_I2C3] = imx_clk_gate2("i2c3", "ipg_bus", CCM_CCGR10, CCM_CCGRx_CGn(7));
 
        clk[VF610_CLK_DSPI0] = imx_clk_gate2("dspi0", "ipg_bus", CCM_CCGR0, CCM_CCGRx_CGn(12));
        clk[VF610_CLK_DSPI1] = imx_clk_gate2("dspi1", "ipg_bus", CCM_CCGR0, CCM_CCGRx_CGn(13));
@@ -383,6 +386,7 @@ static void __init vf610_clocks_init(struct device_node *ccm_node)
        clk[VF610_CLK_DMAMUX3] = imx_clk_gate2("dmamux3", "platform_bus", CCM_CCGR6, CCM_CCGRx_CGn(2));
 
        clk[VF610_CLK_SNVS] = imx_clk_gate2("snvs-rtc", "ipg_bus", CCM_CCGR6, CCM_CCGRx_CGn(7));
+       clk[VF610_CLK_DAP] = imx_clk_gate("dap", "platform_bus", CCM_CCSR, 24);
 
        imx_check_clocks(clk, ARRAY_SIZE(clk));
 
similarity index 94%
rename from arch/arm/mach-imx/clk.h
rename to drivers/clk/imx/clk.h
index 6a07903a28bc81e8123985fc179d0ca17de9b6e9..1049b0c7d81829eb78ea21c8bec356e15f4dbd2b 100644 (file)
@@ -10,8 +10,17 @@ void imx_check_clocks(struct clk *clks[], unsigned int count);
 
 extern void imx_cscmr1_fixup(u32 *val);
 
-struct clk *imx_clk_pllv1(const char *name, const char *parent,
-               void __iomem *base);
+enum imx_pllv1_type {
+       IMX_PLLV1_IMX1,
+       IMX_PLLV1_IMX21,
+       IMX_PLLV1_IMX25,
+       IMX_PLLV1_IMX27,
+       IMX_PLLV1_IMX31,
+       IMX_PLLV1_IMX35,
+};
+
+struct clk *imx_clk_pllv1(enum imx_pllv1_type type, const char *name,
+               const char *parent, void __iomem *base);
 
 struct clk *imx_clk_pllv2(const char *name, const char *parent,
                void __iomem *base);
@@ -23,6 +32,7 @@ enum imx_pllv3_type {
        IMX_PLLV3_USB_VF610,
        IMX_PLLV3_AV,
        IMX_PLLV3_ENET,
+       IMX_PLLV3_ENET_IMX7,
 };
 
 struct clk *imx_clk_pllv3(enum imx_pllv3_type type, const char *name,
index 5f9b54b024b9e1607b724c8ceb5dcfba7b58c992..9a31b77eed23511545f453022d9263db08b7add8 100644 (file)
@@ -353,6 +353,34 @@ static u8 clk_pxa27x_memory_get_parent(struct clk_hw *hw)
 PARENTS(clk_pxa27x_memory) = { "osc_13mhz", "system_bus", "run" };
 MUX_RO_RATE_RO_OPS(clk_pxa27x_memory, "memory");
 
+#define DUMMY_CLK(_con_id, _dev_id, _parent) \
+       { .con_id = _con_id, .dev_id = _dev_id, .parent = _parent }
+struct dummy_clk {
+       const char *con_id;
+       const char *dev_id;
+       const char *parent;
+};
+static struct dummy_clk dummy_clks[] __initdata = {
+       DUMMY_CLK(NULL, "pxa27x-gpio", "osc_32_768khz"),
+       DUMMY_CLK(NULL, "sa1100-rtc", "osc_32_768khz"),
+       DUMMY_CLK("UARTCLK", "pxa2xx-ir", "STUART"),
+};
+
+static void __init pxa27x_dummy_clocks_init(void)
+{
+       struct clk *clk;
+       struct dummy_clk *d;
+       const char *name;
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(dummy_clks); i++) {
+               d = &dummy_clks[i];
+               name = d->dev_id ? d->dev_id : d->con_id;
+               clk = clk_register_fixed_factor(NULL, name, d->parent, 0, 1, 1);
+               clk_register_clkdev(clk, d->con_id, d->dev_id);
+       }
+}
+
 static void __init pxa27x_base_clocks_init(void)
 {
        pxa27x_register_plls();
@@ -362,12 +390,12 @@ static void __init pxa27x_base_clocks_init(void)
        clk_register_clk_pxa27x_lcd_base();
 }
 
-static int __init pxa27x_clocks_init(void)
+int __init pxa27x_clocks_init(void)
 {
        pxa27x_base_clocks_init();
+       pxa27x_dummy_clocks_init();
        return clk_pxa_cken_init(pxa27x_clocks, ARRAY_SIZE(pxa27x_clocks));
 }
-postcore_initcall(pxa27x_clocks_init);
 
 static void __init pxa27x_dt_clocks_init(struct device_node *np)
 {
diff --git a/drivers/clk/zte/Makefile b/drivers/clk/zte/Makefile
new file mode 100644 (file)
index 0000000..95b707c
--- /dev/null
@@ -0,0 +1,2 @@
+obj-y := clk-pll.o
+obj-$(CONFIG_SOC_ZX296702) += clk-zx296702.o
diff --git a/drivers/clk/zte/clk-pll.c b/drivers/clk/zte/clk-pll.c
new file mode 100644 (file)
index 0000000..c3b221a
--- /dev/null
@@ -0,0 +1,172 @@
+/*
+ * Copyright 2014 Linaro Ltd.
+ * Copyright (C) 2014 ZTE Corporation.
+ *
+ * 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/clk-provider.h>
+#include <linux/err.h>
+#include <linux/io.h>
+#include <linux/iopoll.h>
+#include <linux/slab.h>
+#include <linux/spinlock.h>
+
+#include "clk.h"
+
+#define to_clk_zx_pll(_hw) container_of(_hw, struct clk_zx_pll, hw)
+
+#define CFG0_CFG1_OFFSET 4
+#define LOCK_FLAG BIT(30)
+#define POWER_DOWN BIT(31)
+
+static int rate_to_idx(struct clk_zx_pll *zx_pll, unsigned long rate)
+{
+       const struct zx_pll_config *config = zx_pll->lookup_table;
+       int i;
+
+       for (i = 0; i < zx_pll->count; i++) {
+               if (config[i].rate > rate)
+                       return i > 0 ? i - 1 : 0;
+
+               if (config[i].rate == rate)
+                       return i;
+       }
+
+       return i - 1;
+}
+
+static int hw_to_idx(struct clk_zx_pll *zx_pll)
+{
+       const struct zx_pll_config *config = zx_pll->lookup_table;
+       u32 hw_cfg0, hw_cfg1;
+       int i;
+
+       hw_cfg0 = readl_relaxed(zx_pll->reg_base);
+       hw_cfg1 = readl_relaxed(zx_pll->reg_base + CFG0_CFG1_OFFSET);
+
+       /* For matching the value in lookup table */
+       hw_cfg0 &= ~LOCK_FLAG;
+       hw_cfg0 |= POWER_DOWN;
+
+       for (i = 0; i < zx_pll->count; i++) {
+               if (hw_cfg0 == config[i].cfg0 && hw_cfg1 == config[i].cfg1)
+                       return i;
+       }
+
+       return -EINVAL;
+}
+
+static unsigned long zx_pll_recalc_rate(struct clk_hw *hw,
+                                       unsigned long parent_rate)
+{
+       struct clk_zx_pll *zx_pll = to_clk_zx_pll(hw);
+       int idx;
+
+       idx = hw_to_idx(zx_pll);
+       if (unlikely(idx == -EINVAL))
+               return 0;
+
+       return zx_pll->lookup_table[idx].rate;
+}
+
+static long zx_pll_round_rate(struct clk_hw *hw, unsigned long rate,
+                             unsigned long *prate)
+{
+       struct clk_zx_pll *zx_pll = to_clk_zx_pll(hw);
+       int idx;
+
+       idx = rate_to_idx(zx_pll, rate);
+
+       return zx_pll->lookup_table[idx].rate;
+}
+
+static int zx_pll_set_rate(struct clk_hw *hw, unsigned long rate,
+                          unsigned long parent_rate)
+{
+       /* Assume current cpu is not running on current PLL */
+       struct clk_zx_pll *zx_pll = to_clk_zx_pll(hw);
+       const struct zx_pll_config *config;
+       int idx;
+
+       idx = rate_to_idx(zx_pll, rate);
+       config = &zx_pll->lookup_table[idx];
+
+       writel_relaxed(config->cfg0, zx_pll->reg_base);
+       writel_relaxed(config->cfg1, zx_pll->reg_base + CFG0_CFG1_OFFSET);
+
+       return 0;
+}
+
+static int zx_pll_enable(struct clk_hw *hw)
+{
+       struct clk_zx_pll *zx_pll = to_clk_zx_pll(hw);
+       u32 reg;
+
+       reg = readl_relaxed(zx_pll->reg_base);
+       writel_relaxed(reg & ~POWER_DOWN, zx_pll->reg_base);
+
+       return readl_relaxed_poll_timeout(zx_pll->reg_base, reg,
+                                         reg & LOCK_FLAG, 0, 100);
+}
+
+static void zx_pll_disable(struct clk_hw *hw)
+{
+       struct clk_zx_pll *zx_pll = to_clk_zx_pll(hw);
+       u32 reg;
+
+       reg = readl_relaxed(zx_pll->reg_base);
+       writel_relaxed(reg | POWER_DOWN, zx_pll->reg_base);
+}
+
+static int zx_pll_is_enabled(struct clk_hw *hw)
+{
+       struct clk_zx_pll *zx_pll = to_clk_zx_pll(hw);
+       u32 reg;
+
+       reg = readl_relaxed(zx_pll->reg_base);
+
+       return !(reg & POWER_DOWN);
+}
+
+static const struct clk_ops zx_pll_ops = {
+       .recalc_rate = zx_pll_recalc_rate,
+       .round_rate = zx_pll_round_rate,
+       .set_rate = zx_pll_set_rate,
+       .enable = zx_pll_enable,
+       .disable = zx_pll_disable,
+       .is_enabled = zx_pll_is_enabled,
+};
+
+struct clk *clk_register_zx_pll(const char *name, const char *parent_name,
+       unsigned long flags, void __iomem *reg_base,
+       const struct zx_pll_config *lookup_table, int count, spinlock_t *lock)
+{
+       struct clk_zx_pll *zx_pll;
+       struct clk *clk;
+       struct clk_init_data init;
+
+       zx_pll = kzalloc(sizeof(*zx_pll), GFP_KERNEL);
+       if (!zx_pll)
+               return ERR_PTR(-ENOMEM);
+
+       init.name = name;
+       init.ops = &zx_pll_ops;
+       init.flags = flags;
+       init.parent_names = parent_name ? &parent_name : NULL;
+       init.num_parents = parent_name ? 1 : 0;
+
+       zx_pll->reg_base = reg_base;
+       zx_pll->lookup_table = lookup_table;
+       zx_pll->count = count;
+       zx_pll->lock = lock;
+       zx_pll->hw.init = &init;
+
+       clk = clk_register(NULL, &zx_pll->hw);
+       if (IS_ERR(clk))
+               kfree(zx_pll);
+
+       return clk;
+}
diff --git a/drivers/clk/zte/clk-zx296702.c b/drivers/clk/zte/clk-zx296702.c
new file mode 100644 (file)
index 0000000..929d033
--- /dev/null
@@ -0,0 +1,657 @@
+/*
+ * Copyright 2014 Linaro Ltd.
+ * Copyright (C) 2014 ZTE Corporation.
+ *
+ * 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/clk-provider.h>
+#include <linux/of_address.h>
+#include <dt-bindings/clock/zx296702-clock.h>
+#include "clk.h"
+
+static DEFINE_SPINLOCK(reg_lock);
+
+static void __iomem *topcrm_base;
+static void __iomem *lsp0crpm_base;
+static void __iomem *lsp1crpm_base;
+
+static struct clk *topclk[ZX296702_TOPCLK_END];
+static struct clk *lsp0clk[ZX296702_LSP0CLK_END];
+static struct clk *lsp1clk[ZX296702_LSP1CLK_END];
+
+static struct clk_onecell_data topclk_data;
+static struct clk_onecell_data lsp0clk_data;
+static struct clk_onecell_data lsp1clk_data;
+
+#define CLK_MUX                        (topcrm_base + 0x04)
+#define CLK_DIV                        (topcrm_base + 0x08)
+#define CLK_EN0                        (topcrm_base + 0x0c)
+#define CLK_EN1                        (topcrm_base + 0x10)
+#define VOU_LOCAL_CLKEN                (topcrm_base + 0x68)
+#define VOU_LOCAL_CLKSEL       (topcrm_base + 0x70)
+#define VOU_LOCAL_DIV2_SET     (topcrm_base + 0x74)
+#define CLK_MUX1               (topcrm_base + 0x8c)
+
+#define CLK_SDMMC1             (lsp0crpm_base + 0x0c)
+
+#define CLK_UART0              (lsp1crpm_base + 0x20)
+#define CLK_UART1              (lsp1crpm_base + 0x24)
+#define CLK_SDMMC0             (lsp1crpm_base + 0x2c)
+
+static const struct zx_pll_config pll_a9_config[] = {
+       { .rate = 700000000, .cfg0 = 0x800405d1, .cfg1 = 0x04555555 },
+       { .rate = 800000000, .cfg0 = 0x80040691, .cfg1 = 0x04aaaaaa },
+       { .rate = 900000000, .cfg0 = 0x80040791, .cfg1 = 0x04000000 },
+       { .rate = 1000000000, .cfg0 = 0x80040851, .cfg1 = 0x04555555 },
+       { .rate = 1100000000, .cfg0 = 0x80040911, .cfg1 = 0x04aaaaaa },
+       { .rate = 1200000000, .cfg0 = 0x80040a11, .cfg1 = 0x04000000 },
+};
+
+static const struct clk_div_table main_hlk_div[] = {
+       { .val = 1, .div = 2, },
+       { .val = 3, .div = 4, },
+       { /* sentinel */ }
+};
+
+static const struct clk_div_table a9_as1_aclk_divider[] = {
+       { .val = 0, .div = 1, },
+       { .val = 1, .div = 2, },
+       { .val = 3, .div = 4, },
+       { /* sentinel */ }
+};
+
+static const struct clk_div_table sec_wclk_divider[] = {
+       { .val = 0, .div = 1, },
+       { .val = 1, .div = 2, },
+       { .val = 3, .div = 4, },
+       { .val = 5, .div = 6, },
+       { .val = 7, .div = 8, },
+       { /* sentinel */ }
+};
+
+static const char * matrix_aclk_sel[] = {
+       "pll_mm0_198M",
+       "osc",
+       "clk_148M5",
+       "pll_lsp_104M",
+};
+
+static const char * a9_wclk_sel[] = {
+       "pll_a9",
+       "osc",
+       "clk_500",
+       "clk_250",
+};
+
+static const char * a9_as1_aclk_sel[] = {
+       "clk_250",
+       "osc",
+       "pll_mm0_396M",
+       "pll_mac_333M",
+};
+
+static const char * a9_trace_clkin_sel[] = {
+       "clk_74M25",
+       "pll_mm1_108M",
+       "clk_125",
+       "clk_148M5",
+};
+
+static const char * decppu_aclk_sel[] = {
+       "clk_250",
+       "pll_mm0_198M",
+       "pll_lsp_104M",
+       "pll_audio_294M912",
+};
+
+static const char * vou_main_wclk_sel[] = {
+       "clk_148M5",
+       "clk_74M25",
+       "clk_27",
+       "pll_mm1_54M",
+};
+
+static const char * vou_scaler_wclk_sel[] = {
+       "clk_250",
+       "pll_mac_333M",
+       "pll_audio_294M912",
+       "pll_mm0_198M",
+};
+
+static const char * r2d_wclk_sel[] = {
+       "pll_audio_294M912",
+       "pll_mac_333M",
+       "pll_a9_350M",
+       "pll_mm0_396M",
+};
+
+static const char * ddr_wclk_sel[] = {
+       "pll_mac_333M",
+       "pll_ddr_266M",
+       "pll_audio_294M912",
+       "pll_mm0_198M",
+};
+
+static const char * nand_wclk_sel[] = {
+       "pll_lsp_104M",
+       "osc",
+};
+
+static const char * lsp_26_wclk_sel[] = {
+       "pll_lsp_26M",
+       "osc",
+};
+
+static const char * vl0_sel[] = {
+       "vou_main_channel_div",
+       "vou_aux_channel_div",
+};
+
+static const char * hdmi_sel[] = {
+       "vou_main_channel_wclk",
+       "vou_aux_channel_wclk",
+};
+
+static const char * sdmmc0_wclk_sel[] = {
+       "lsp1_104M_wclk",
+       "lsp1_26M_wclk",
+};
+
+static const char * sdmmc1_wclk_sel[] = {
+       "lsp0_104M_wclk",
+       "lsp0_26M_wclk",
+};
+
+static const char * uart_wclk_sel[] = {
+       "lsp1_104M_wclk",
+       "lsp1_26M_wclk",
+};
+
+static inline struct clk *zx_divtbl(const char *name, const char *parent,
+                                   void __iomem *reg, u8 shift, u8 width,
+                                   const struct clk_div_table *table)
+{
+       return clk_register_divider_table(NULL, name, parent, 0, reg, shift,
+                                         width, 0, table, &reg_lock);
+}
+
+static inline struct clk *zx_div(const char *name, const char *parent,
+                                void __iomem *reg, u8 shift, u8 width)
+{
+       return clk_register_divider(NULL, name, parent, 0,
+                                   reg, shift, width, 0, &reg_lock);
+}
+
+static inline struct clk *zx_mux(const char *name, const char **parents,
+               int num_parents, void __iomem *reg, u8 shift, u8 width)
+{
+       return clk_register_mux(NULL, name, parents, num_parents,
+                               0, reg, shift, width, 0, &reg_lock);
+}
+
+static inline struct clk *zx_gate(const char *name, const char *parent,
+                                 void __iomem *reg, u8 shift)
+{
+       return clk_register_gate(NULL, name, parent, CLK_IGNORE_UNUSED,
+                                reg, shift, 0, &reg_lock);
+}
+
+static void __init zx296702_top_clocks_init(struct device_node *np)
+{
+       struct clk **clk = topclk;
+       int i;
+
+       topcrm_base = of_iomap(np, 0);
+       WARN_ON(!topcrm_base);
+
+       clk[ZX296702_OSC] =
+               clk_register_fixed_rate(NULL, "osc", NULL, CLK_IS_ROOT,
+                               30000000);
+       clk[ZX296702_PLL_A9] =
+               clk_register_zx_pll("pll_a9", "osc", 0, topcrm_base
+                               + 0x01c, pll_a9_config,
+                               ARRAY_SIZE(pll_a9_config), &reg_lock);
+
+       /* TODO: pll_a9_350M look like changeble follow a9 pll */
+       clk[ZX296702_PLL_A9_350M] =
+               clk_register_fixed_rate(NULL, "pll_a9_350M", "osc", 0,
+                               350000000);
+       clk[ZX296702_PLL_MAC_1000M] =
+               clk_register_fixed_rate(NULL, "pll_mac_1000M", "osc", 0,
+                               1000000000);
+       clk[ZX296702_PLL_MAC_333M] =
+               clk_register_fixed_rate(NULL, "pll_mac_333M",    "osc", 0,
+                               333000000);
+       clk[ZX296702_PLL_MM0_1188M] =
+               clk_register_fixed_rate(NULL, "pll_mm0_1188M", "osc", 0,
+                               1188000000);
+       clk[ZX296702_PLL_MM0_396M] =
+               clk_register_fixed_rate(NULL, "pll_mm0_396M",  "osc", 0,
+                               396000000);
+       clk[ZX296702_PLL_MM0_198M] =
+               clk_register_fixed_rate(NULL, "pll_mm0_198M",  "osc", 0,
+                               198000000);
+       clk[ZX296702_PLL_MM1_108M] =
+               clk_register_fixed_rate(NULL, "pll_mm1_108M",  "osc", 0,
+                               108000000);
+       clk[ZX296702_PLL_MM1_72M] =
+               clk_register_fixed_rate(NULL, "pll_mm1_72M",     "osc", 0,
+                               72000000);
+       clk[ZX296702_PLL_MM1_54M] =
+               clk_register_fixed_rate(NULL, "pll_mm1_54M",     "osc", 0,
+                               54000000);
+       clk[ZX296702_PLL_LSP_104M] =
+               clk_register_fixed_rate(NULL, "pll_lsp_104M",  "osc", 0,
+                               104000000);
+       clk[ZX296702_PLL_LSP_26M] =
+               clk_register_fixed_rate(NULL, "pll_lsp_26M",     "osc", 0,
+                               26000000);
+       clk[ZX296702_PLL_DDR_266M] =
+               clk_register_fixed_rate(NULL, "pll_ddr_266M",    "osc", 0,
+                               266000000);
+       clk[ZX296702_PLL_AUDIO_294M912] =
+               clk_register_fixed_rate(NULL, "pll_audio_294M912", "osc", 0,
+                               294912000);
+
+       /* bus clock */
+       clk[ZX296702_MATRIX_ACLK] =
+               zx_mux("matrix_aclk", matrix_aclk_sel,
+                               ARRAY_SIZE(matrix_aclk_sel), CLK_MUX, 2, 2);
+       clk[ZX296702_MAIN_HCLK] =
+               zx_divtbl("main_hclk", "matrix_aclk", CLK_DIV, 0, 2,
+                               main_hlk_div);
+       clk[ZX296702_MAIN_PCLK] =
+               zx_divtbl("main_pclk", "matrix_aclk", CLK_DIV, 2, 2,
+                               main_hlk_div);
+
+       /* cpu clock */
+       clk[ZX296702_CLK_500] =
+               clk_register_fixed_factor(NULL, "clk_500", "pll_mac_1000M", 0,
+                               1, 2);
+       clk[ZX296702_CLK_250] =
+               clk_register_fixed_factor(NULL, "clk_250", "pll_mac_1000M", 0,
+                               1, 4);
+       clk[ZX296702_CLK_125] =
+               clk_register_fixed_factor(NULL, "clk_125", "clk_250", 0, 1, 2);
+       clk[ZX296702_CLK_148M5] =
+               clk_register_fixed_factor(NULL, "clk_148M5", "pll_mm0_1188M", 0,
+                               1, 8);
+       clk[ZX296702_CLK_74M25] =
+               clk_register_fixed_factor(NULL, "clk_74M25", "pll_mm0_1188M", 0,
+                               1, 16);
+       clk[ZX296702_A9_WCLK] =
+               zx_mux("a9_wclk", a9_wclk_sel, ARRAY_SIZE(a9_wclk_sel), CLK_MUX,
+                               0, 2);
+       clk[ZX296702_A9_AS1_ACLK_MUX] =
+               zx_mux("a9_as1_aclk_mux", a9_as1_aclk_sel,
+                               ARRAY_SIZE(a9_as1_aclk_sel), CLK_MUX, 4, 2);
+       clk[ZX296702_A9_TRACE_CLKIN_MUX] =
+               zx_mux("a9_trace_clkin_mux", a9_trace_clkin_sel,
+                               ARRAY_SIZE(a9_trace_clkin_sel), CLK_MUX1, 0, 2);
+       clk[ZX296702_A9_AS1_ACLK_DIV] =
+               zx_divtbl("a9_as1_aclk_div", "a9_as1_aclk_mux", CLK_DIV, 4, 2,
+                               a9_as1_aclk_divider);
+
+       /* multi-media clock */
+       clk[ZX296702_CLK_2] =
+               clk_register_fixed_factor(NULL, "clk_2", "pll_mm1_72M", 0,
+                               1, 36);
+       clk[ZX296702_CLK_27] =
+               clk_register_fixed_factor(NULL, "clk_27", "pll_mm1_54M", 0,
+                               1, 2);
+       clk[ZX296702_DECPPU_ACLK_MUX] =
+               zx_mux("decppu_aclk_mux", decppu_aclk_sel,
+                               ARRAY_SIZE(decppu_aclk_sel), CLK_MUX, 6, 2);
+       clk[ZX296702_PPU_ACLK_MUX] =
+               zx_mux("ppu_aclk_mux", decppu_aclk_sel,
+                               ARRAY_SIZE(decppu_aclk_sel), CLK_MUX, 8, 2);
+       clk[ZX296702_MALI400_ACLK_MUX] =
+               zx_mux("mali400_aclk_mux", decppu_aclk_sel,
+                               ARRAY_SIZE(decppu_aclk_sel), CLK_MUX, 12, 2);
+       clk[ZX296702_VOU_ACLK_MUX] =
+               zx_mux("vou_aclk_mux", decppu_aclk_sel,
+                               ARRAY_SIZE(decppu_aclk_sel), CLK_MUX, 10, 2);
+       clk[ZX296702_VOU_MAIN_WCLK_MUX] =
+               zx_mux("vou_main_wclk_mux", vou_main_wclk_sel,
+                               ARRAY_SIZE(vou_main_wclk_sel), CLK_MUX, 14, 2);
+       clk[ZX296702_VOU_AUX_WCLK_MUX] =
+               zx_mux("vou_aux_wclk_mux", vou_main_wclk_sel,
+                               ARRAY_SIZE(vou_main_wclk_sel), CLK_MUX, 16, 2);
+       clk[ZX296702_VOU_SCALER_WCLK_MUX] =
+               zx_mux("vou_scaler_wclk_mux", vou_scaler_wclk_sel,
+                               ARRAY_SIZE(vou_scaler_wclk_sel), CLK_MUX,
+                               18, 2);
+       clk[ZX296702_R2D_ACLK_MUX] =
+               zx_mux("r2d_aclk_mux", decppu_aclk_sel,
+                               ARRAY_SIZE(decppu_aclk_sel), CLK_MUX, 20, 2);
+       clk[ZX296702_R2D_WCLK_MUX] =
+               zx_mux("r2d_wclk_mux", r2d_wclk_sel,
+                               ARRAY_SIZE(r2d_wclk_sel), CLK_MUX, 22, 2);
+
+       /* other clock */
+       clk[ZX296702_CLK_50] =
+               clk_register_fixed_factor(NULL, "clk_50", "pll_mac_1000M",
+                               0, 1, 20);
+       clk[ZX296702_CLK_25] =
+               clk_register_fixed_factor(NULL, "clk_25", "pll_mac_1000M",
+                               0, 1, 40);
+       clk[ZX296702_CLK_12] =
+               clk_register_fixed_factor(NULL, "clk_12", "pll_mm1_72M",
+                               0, 1, 6);
+       clk[ZX296702_CLK_16M384] =
+               clk_register_fixed_factor(NULL, "clk_16M384",
+                               "pll_audio_294M912", 0, 1, 18);
+       clk[ZX296702_CLK_32K768] =
+               clk_register_fixed_factor(NULL, "clk_32K768", "clk_16M384",
+                               0, 1, 500);
+       clk[ZX296702_SEC_WCLK_DIV] =
+               zx_divtbl("sec_wclk_div", "pll_lsp_104M", CLK_DIV, 6, 3,
+                               sec_wclk_divider);
+       clk[ZX296702_DDR_WCLK_MUX] =
+               zx_mux("ddr_wclk_mux", ddr_wclk_sel,
+                               ARRAY_SIZE(ddr_wclk_sel), CLK_MUX, 24, 2);
+       clk[ZX296702_NAND_WCLK_MUX] =
+               zx_mux("nand_wclk_mux", nand_wclk_sel,
+                               ARRAY_SIZE(nand_wclk_sel), CLK_MUX, 24, 2);
+       clk[ZX296702_LSP_26_WCLK_MUX] =
+               zx_mux("lsp_26_wclk_mux", lsp_26_wclk_sel,
+                               ARRAY_SIZE(lsp_26_wclk_sel), CLK_MUX, 27, 1);
+
+       /* gates */
+       clk[ZX296702_A9_AS0_ACLK] =
+               zx_gate("a9_as0_aclk",  "matrix_aclk",          CLK_EN0, 0);
+       clk[ZX296702_A9_AS1_ACLK] =
+               zx_gate("a9_as1_aclk",  "a9_as1_aclk_div",      CLK_EN0, 1);
+       clk[ZX296702_A9_TRACE_CLKIN] =
+               zx_gate("a9_trace_clkin", "a9_trace_clkin_mux", CLK_EN0, 2);
+       clk[ZX296702_DECPPU_AXI_M_ACLK] =
+               zx_gate("decppu_axi_m_aclk", "decppu_aclk_mux", CLK_EN0, 3);
+       clk[ZX296702_DECPPU_AHB_S_HCLK] =
+               zx_gate("decppu_ahb_s_hclk",    "main_hclk",    CLK_EN0, 4);
+       clk[ZX296702_PPU_AXI_M_ACLK] =
+               zx_gate("ppu_axi_m_aclk",       "ppu_aclk_mux", CLK_EN0, 5);
+       clk[ZX296702_PPU_AHB_S_HCLK] =
+               zx_gate("ppu_ahb_s_hclk",       "main_hclk",    CLK_EN0, 6);
+       clk[ZX296702_VOU_AXI_M_ACLK] =
+               zx_gate("vou_axi_m_aclk",       "vou_aclk_mux", CLK_EN0, 7);
+       clk[ZX296702_VOU_APB_PCLK] =
+               zx_gate("vou_apb_pclk", "main_pclk",            CLK_EN0, 8);
+       clk[ZX296702_VOU_MAIN_CHANNEL_WCLK] =
+               zx_gate("vou_main_channel_wclk", "vou_main_wclk_mux",
+                               CLK_EN0, 9);
+       clk[ZX296702_VOU_AUX_CHANNEL_WCLK] =
+               zx_gate("vou_aux_channel_wclk", "vou_aux_wclk_mux",
+                               CLK_EN0, 10);
+       clk[ZX296702_VOU_HDMI_OSCLK_CEC] =
+               zx_gate("vou_hdmi_osclk_cec", "clk_2",          CLK_EN0, 11);
+       clk[ZX296702_VOU_SCALER_WCLK] =
+               zx_gate("vou_scaler_wclk", "vou_scaler_wclk_mux", CLK_EN0, 12);
+       clk[ZX296702_MALI400_AXI_M_ACLK] =
+               zx_gate("mali400_axi_m_aclk", "mali400_aclk_mux", CLK_EN0, 13);
+       clk[ZX296702_MALI400_APB_PCLK] =
+               zx_gate("mali400_apb_pclk",     "main_pclk",    CLK_EN0, 14);
+       clk[ZX296702_R2D_WCLK] =
+               zx_gate("r2d_wclk",             "r2d_wclk_mux", CLK_EN0, 15);
+       clk[ZX296702_R2D_AXI_M_ACLK] =
+               zx_gate("r2d_axi_m_aclk",       "r2d_aclk_mux", CLK_EN0, 16);
+       clk[ZX296702_R2D_AHB_HCLK] =
+               zx_gate("r2d_ahb_hclk",         "main_hclk",    CLK_EN0, 17);
+       clk[ZX296702_DDR3_AXI_S0_ACLK] =
+               zx_gate("ddr3_axi_s0_aclk",     "matrix_aclk",  CLK_EN0, 18);
+       clk[ZX296702_DDR3_APB_PCLK] =
+               zx_gate("ddr3_apb_pclk",        "main_pclk",    CLK_EN0, 19);
+       clk[ZX296702_DDR3_WCLK] =
+               zx_gate("ddr3_wclk",            "ddr_wclk_mux", CLK_EN0, 20);
+       clk[ZX296702_USB20_0_AHB_HCLK] =
+               zx_gate("usb20_0_ahb_hclk",     "main_hclk",    CLK_EN0, 21);
+       clk[ZX296702_USB20_0_EXTREFCLK] =
+               zx_gate("usb20_0_extrefclk",    "clk_12",       CLK_EN0, 22);
+       clk[ZX296702_USB20_1_AHB_HCLK] =
+               zx_gate("usb20_1_ahb_hclk",     "main_hclk",    CLK_EN0, 23);
+       clk[ZX296702_USB20_1_EXTREFCLK] =
+               zx_gate("usb20_1_extrefclk",    "clk_12",       CLK_EN0, 24);
+       clk[ZX296702_USB20_2_AHB_HCLK] =
+               zx_gate("usb20_2_ahb_hclk",     "main_hclk",    CLK_EN0, 25);
+       clk[ZX296702_USB20_2_EXTREFCLK] =
+               zx_gate("usb20_2_extrefclk",    "clk_12",       CLK_EN0, 26);
+       clk[ZX296702_GMAC_AXI_M_ACLK] =
+               zx_gate("gmac_axi_m_aclk",      "matrix_aclk",  CLK_EN0, 27);
+       clk[ZX296702_GMAC_APB_PCLK] =
+               zx_gate("gmac_apb_pclk",        "main_pclk",    CLK_EN0, 28);
+       clk[ZX296702_GMAC_125_CLKIN] =
+               zx_gate("gmac_125_clkin",       "clk_125",      CLK_EN0, 29);
+       clk[ZX296702_GMAC_RMII_CLKIN] =
+               zx_gate("gmac_rmii_clkin",      "clk_50",       CLK_EN0, 30);
+       clk[ZX296702_GMAC_25M_CLK] =
+               zx_gate("gmac_25M_clk",         "clk_25",       CLK_EN0, 31);
+       clk[ZX296702_NANDFLASH_AHB_HCLK] =
+               zx_gate("nandflash_ahb_hclk", "main_hclk",      CLK_EN1, 0);
+       clk[ZX296702_NANDFLASH_WCLK] =
+               zx_gate("nandflash_wclk",     "nand_wclk_mux",  CLK_EN1, 1);
+       clk[ZX296702_LSP0_APB_PCLK] =
+               zx_gate("lsp0_apb_pclk",        "main_pclk",    CLK_EN1, 2);
+       clk[ZX296702_LSP0_AHB_HCLK] =
+               zx_gate("lsp0_ahb_hclk",        "main_hclk",    CLK_EN1, 3);
+       clk[ZX296702_LSP0_26M_WCLK] =
+               zx_gate("lsp0_26M_wclk",   "lsp_26_wclk_mux",   CLK_EN1, 4);
+       clk[ZX296702_LSP0_104M_WCLK] =
+               zx_gate("lsp0_104M_wclk",       "pll_lsp_104M", CLK_EN1, 5);
+       clk[ZX296702_LSP0_16M384_WCLK] =
+               zx_gate("lsp0_16M384_wclk",     "clk_16M384",   CLK_EN1, 6);
+       clk[ZX296702_LSP1_APB_PCLK] =
+               zx_gate("lsp1_apb_pclk",        "main_pclk",    CLK_EN1, 7);
+       /* FIXME: wclk enable bit is bit8. We hack it as reserved 31 for
+        * UART does not work after parent clk is disabled/enabled */
+       clk[ZX296702_LSP1_26M_WCLK] =
+               zx_gate("lsp1_26M_wclk",     "lsp_26_wclk_mux", CLK_EN1, 31);
+       clk[ZX296702_LSP1_104M_WCLK] =
+               zx_gate("lsp1_104M_wclk",    "pll_lsp_104M",    CLK_EN1, 9);
+       clk[ZX296702_LSP1_32K_CLK] =
+               zx_gate("lsp1_32K_clk", "clk_32K768",           CLK_EN1, 10);
+       clk[ZX296702_AON_HCLK] =
+               zx_gate("aon_hclk",             "main_hclk",    CLK_EN1, 11);
+       clk[ZX296702_SYS_CTRL_PCLK] =
+               zx_gate("sys_ctrl_pclk",        "main_pclk",    CLK_EN1, 12);
+       clk[ZX296702_DMA_PCLK] =
+               zx_gate("dma_pclk",             "main_pclk",    CLK_EN1, 13);
+       clk[ZX296702_DMA_ACLK] =
+               zx_gate("dma_aclk",             "matrix_aclk",  CLK_EN1, 14);
+       clk[ZX296702_SEC_HCLK] =
+               zx_gate("sec_hclk",             "main_hclk",    CLK_EN1, 15);
+       clk[ZX296702_AES_WCLK] =
+               zx_gate("aes_wclk",             "sec_wclk_div", CLK_EN1, 16);
+       clk[ZX296702_DES_WCLK] =
+               zx_gate("des_wclk",             "sec_wclk_div", CLK_EN1, 17);
+       clk[ZX296702_IRAM_ACLK] =
+               zx_gate("iram_aclk",            "matrix_aclk",  CLK_EN1, 18);
+       clk[ZX296702_IROM_ACLK] =
+               zx_gate("irom_aclk",            "matrix_aclk",  CLK_EN1, 19);
+       clk[ZX296702_BOOT_CTRL_HCLK] =
+               zx_gate("boot_ctrl_hclk",       "main_hclk",    CLK_EN1, 20);
+       clk[ZX296702_EFUSE_CLK_30] =
+               zx_gate("efuse_clk_30", "osc",                  CLK_EN1, 21);
+
+       /* TODO: add VOU Local clocks */
+       clk[ZX296702_VOU_MAIN_CHANNEL_DIV] =
+               zx_div("vou_main_channel_div", "vou_main_channel_wclk",
+                               VOU_LOCAL_DIV2_SET, 1, 1);
+       clk[ZX296702_VOU_AUX_CHANNEL_DIV] =
+               zx_div("vou_aux_channel_div", "vou_aux_channel_wclk",
+                               VOU_LOCAL_DIV2_SET, 0, 1);
+       clk[ZX296702_VOU_TV_ENC_HD_DIV] =
+               zx_div("vou_tv_enc_hd_div", "vou_tv_enc_hd_mux",
+                               VOU_LOCAL_DIV2_SET, 3, 1);
+       clk[ZX296702_VOU_TV_ENC_SD_DIV] =
+               zx_div("vou_tv_enc_sd_div", "vou_tv_enc_sd_mux",
+                               VOU_LOCAL_DIV2_SET, 2, 1);
+       clk[ZX296702_VL0_MUX] =
+               zx_mux("vl0_mux", vl0_sel, ARRAY_SIZE(vl0_sel),
+                               VOU_LOCAL_CLKSEL, 8, 1);
+       clk[ZX296702_VL1_MUX] =
+               zx_mux("vl1_mux", vl0_sel, ARRAY_SIZE(vl0_sel),
+                               VOU_LOCAL_CLKSEL, 9, 1);
+       clk[ZX296702_VL2_MUX] =
+               zx_mux("vl2_mux", vl0_sel, ARRAY_SIZE(vl0_sel),
+                               VOU_LOCAL_CLKSEL, 10, 1);
+       clk[ZX296702_GL0_MUX] =
+               zx_mux("gl0_mux", vl0_sel, ARRAY_SIZE(vl0_sel),
+                               VOU_LOCAL_CLKSEL, 5, 1);
+       clk[ZX296702_GL1_MUX] =
+               zx_mux("gl1_mux", vl0_sel, ARRAY_SIZE(vl0_sel),
+                               VOU_LOCAL_CLKSEL, 6, 1);
+       clk[ZX296702_GL2_MUX] =
+               zx_mux("gl2_mux", vl0_sel, ARRAY_SIZE(vl0_sel),
+                               VOU_LOCAL_CLKSEL, 7, 1);
+       clk[ZX296702_WB_MUX] =
+               zx_mux("wb_mux",  vl0_sel, ARRAY_SIZE(vl0_sel),
+                               VOU_LOCAL_CLKSEL, 11, 1);
+       clk[ZX296702_HDMI_MUX] =
+               zx_mux("hdmi_mux", hdmi_sel, ARRAY_SIZE(hdmi_sel),
+                               VOU_LOCAL_CLKSEL, 4, 1);
+       clk[ZX296702_VOU_TV_ENC_HD_MUX] =
+               zx_mux("vou_tv_enc_hd_mux", hdmi_sel, ARRAY_SIZE(hdmi_sel),
+                               VOU_LOCAL_CLKSEL, 3, 1);
+       clk[ZX296702_VOU_TV_ENC_SD_MUX] =
+               zx_mux("vou_tv_enc_sd_mux", hdmi_sel, ARRAY_SIZE(hdmi_sel),
+                               VOU_LOCAL_CLKSEL, 2, 1);
+       clk[ZX296702_VL0_CLK] =
+               zx_gate("vl0_clk", "vl0_mux", VOU_LOCAL_CLKEN, 8);
+       clk[ZX296702_VL1_CLK] =
+               zx_gate("vl1_clk", "vl1_mux", VOU_LOCAL_CLKEN, 9);
+       clk[ZX296702_VL2_CLK] =
+               zx_gate("vl2_clk", "vl2_mux", VOU_LOCAL_CLKEN, 10);
+       clk[ZX296702_GL0_CLK] =
+               zx_gate("gl0_clk", "gl0_mux", VOU_LOCAL_CLKEN, 5);
+       clk[ZX296702_GL1_CLK] =
+               zx_gate("gl1_clk", "gl1_mux", VOU_LOCAL_CLKEN, 6);
+       clk[ZX296702_GL2_CLK] =
+               zx_gate("gl2_clk", "gl2_mux", VOU_LOCAL_CLKEN, 7);
+       clk[ZX296702_WB_CLK] =
+               zx_gate("wb_clk", "wb_mux", VOU_LOCAL_CLKEN, 11);
+       clk[ZX296702_CL_CLK] =
+               zx_gate("cl_clk", "vou_main_channel_div", VOU_LOCAL_CLKEN, 12);
+       clk[ZX296702_MAIN_MIX_CLK] =
+               zx_gate("main_mix_clk", "vou_main_channel_div",
+                               VOU_LOCAL_CLKEN, 4);
+       clk[ZX296702_AUX_MIX_CLK] =
+               zx_gate("aux_mix_clk", "vou_aux_channel_div",
+                               VOU_LOCAL_CLKEN, 3);
+       clk[ZX296702_HDMI_CLK] =
+               zx_gate("hdmi_clk", "hdmi_mux", VOU_LOCAL_CLKEN, 2);
+       clk[ZX296702_VOU_TV_ENC_HD_DAC_CLK] =
+               zx_gate("vou_tv_enc_hd_dac_clk", "vou_tv_enc_hd_div",
+                               VOU_LOCAL_CLKEN, 1);
+       clk[ZX296702_VOU_TV_ENC_SD_DAC_CLK] =
+               zx_gate("vou_tv_enc_sd_dac_clk", "vou_tv_enc_sd_div",
+                               VOU_LOCAL_CLKEN, 0);
+
+       /* CA9 PERIPHCLK = a9_wclk / 2 */
+       clk[ZX296702_A9_PERIPHCLK] =
+               clk_register_fixed_factor(NULL, "a9_periphclk", "a9_wclk",
+                               0, 1, 2);
+
+       for (i = 0; i < ARRAY_SIZE(topclk); i++) {
+               if (IS_ERR(clk[i])) {
+                       pr_err("zx296702 clk %d: register failed with %ld\n",
+                               i, PTR_ERR(clk[i]));
+                       return;
+               }
+       }
+
+       topclk_data.clks = topclk;
+       topclk_data.clk_num = ARRAY_SIZE(topclk);
+       of_clk_add_provider(np, of_clk_src_onecell_get, &topclk_data);
+}
+CLK_OF_DECLARE(zx296702_top_clk, "zte,zx296702-topcrm-clk",
+               zx296702_top_clocks_init);
+
+static void __init zx296702_lsp0_clocks_init(struct device_node *np)
+{
+       struct clk **clk = lsp0clk;
+       int i;
+
+       lsp0crpm_base = of_iomap(np, 0);
+       WARN_ON(!lsp0crpm_base);
+
+       /* SDMMC1 */
+       clk[ZX296702_SDMMC1_WCLK_MUX] =
+               zx_mux("sdmmc1_wclk_mux", sdmmc1_wclk_sel,
+                               ARRAY_SIZE(sdmmc1_wclk_sel), CLK_SDMMC1, 4, 1);
+       clk[ZX296702_SDMMC1_WCLK_DIV] =
+               zx_div("sdmmc1_wclk_div", "sdmmc1_wclk_mux", CLK_SDMMC1, 12, 4);
+       clk[ZX296702_SDMMC1_WCLK] =
+               zx_gate("sdmmc1_wclk", "sdmmc1_wclk_div", CLK_SDMMC1, 1);
+       clk[ZX296702_SDMMC1_PCLK] =
+               zx_gate("sdmmc1_pclk", "lsp1_apb_pclk", CLK_SDMMC1, 0);
+
+       for (i = 0; i < ARRAY_SIZE(lsp0clk); i++) {
+               if (IS_ERR(clk[i])) {
+                       pr_err("zx296702 clk %d: register failed with %ld\n",
+                               i, PTR_ERR(clk[i]));
+                       return;
+               }
+       }
+
+       lsp0clk_data.clks = lsp0clk;
+       lsp0clk_data.clk_num = ARRAY_SIZE(lsp0clk);
+       of_clk_add_provider(np, of_clk_src_onecell_get, &lsp0clk_data);
+}
+CLK_OF_DECLARE(zx296702_lsp0_clk, "zte,zx296702-lsp0crpm-clk",
+               zx296702_lsp0_clocks_init);
+
+static void __init zx296702_lsp1_clocks_init(struct device_node *np)
+{
+       struct clk **clk = lsp1clk;
+       int i;
+
+       lsp1crpm_base = of_iomap(np, 0);
+       WARN_ON(!lsp1crpm_base);
+
+       /* UART0 */
+       clk[ZX296702_UART0_WCLK_MUX] =
+               zx_mux("uart0_wclk_mux", uart_wclk_sel,
+                               ARRAY_SIZE(uart_wclk_sel), CLK_UART0, 4, 1);
+       /* FIXME: uart wclk enable bit is bit1 in. We hack it as reserved 31 for
+        * UART does not work after parent clk is disabled/enabled */
+       clk[ZX296702_UART0_WCLK] =
+               zx_gate("uart0_wclk", "uart0_wclk_mux", CLK_UART0, 31);
+       clk[ZX296702_UART0_PCLK] =
+               zx_gate("uart0_pclk", "lsp1_apb_pclk", CLK_UART0, 0);
+
+       /* UART1 */
+       clk[ZX296702_UART1_WCLK_MUX] =
+               zx_mux("uart1_wclk_mux", uart_wclk_sel,
+                               ARRAY_SIZE(uart_wclk_sel), CLK_UART1, 4, 1);
+       clk[ZX296702_UART1_WCLK] =
+               zx_gate("uart1_wclk", "uart1_wclk_mux", CLK_UART1, 1);
+       clk[ZX296702_UART1_PCLK] =
+               zx_gate("uart1_pclk", "lsp1_apb_pclk", CLK_UART1, 0);
+
+       /* SDMMC0 */
+       clk[ZX296702_SDMMC0_WCLK_MUX] =
+               zx_mux("sdmmc0_wclk_mux", sdmmc0_wclk_sel,
+                               ARRAY_SIZE(sdmmc0_wclk_sel), CLK_SDMMC0, 4, 1);
+       clk[ZX296702_SDMMC0_WCLK_DIV] =
+               zx_div("sdmmc0_wclk_div", "sdmmc0_wclk_mux", CLK_SDMMC0, 12, 4);
+       clk[ZX296702_SDMMC0_WCLK] =
+               zx_gate("sdmmc0_wclk", "sdmmc0_wclk_div", CLK_SDMMC0, 1);
+       clk[ZX296702_SDMMC0_PCLK] =
+               zx_gate("sdmmc0_pclk", "lsp1_apb_pclk", CLK_SDMMC0, 0);
+
+       for (i = 0; i < ARRAY_SIZE(lsp1clk); i++) {
+               if (IS_ERR(clk[i])) {
+                       pr_err("zx296702 clk %d: register failed with %ld\n",
+                               i, PTR_ERR(clk[i]));
+                       return;
+               }
+       }
+
+       lsp1clk_data.clks = lsp1clk;
+       lsp1clk_data.clk_num = ARRAY_SIZE(lsp1clk);
+       of_clk_add_provider(np, of_clk_src_onecell_get, &lsp1clk_data);
+}
+CLK_OF_DECLARE(zx296702_lsp1_clk, "zte,zx296702-lsp1crpm-clk",
+               zx296702_lsp1_clocks_init);
diff --git a/drivers/clk/zte/clk.h b/drivers/clk/zte/clk.h
new file mode 100644 (file)
index 0000000..0914a82
--- /dev/null
@@ -0,0 +1,32 @@
+/*
+ * Copyright 2015 Linaro Ltd.
+ * Copyright (C) 2014 ZTE Corporation.
+ *
+ * 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.
+ */
+
+#ifndef __ZTE_CLK_H
+#define __ZTE_CLK_H
+#include <linux/clk-provider.h>
+#include <linux/spinlock.h>
+
+struct zx_pll_config {
+       unsigned long rate;
+       u32 cfg0;
+       u32 cfg1;
+};
+
+struct clk_zx_pll {
+       struct clk_hw hw;
+       void __iomem *reg_base;
+       const struct zx_pll_config *lookup_table; /* order by rate asc */
+       int count;
+       spinlock_t *lock;
+};
+
+struct clk *clk_register_zx_pll(const char *name, const char *parent_name,
+       unsigned long flags, void __iomem *reg_base,
+       const struct zx_pll_config *lookup_table, int count, spinlock_t *lock);
+#endif
index 51d7865fdddb6d59ae7a9406ae8d88cb4da30066..618102e5aa2ae79ff8caacb0dfe76a3ad2ae5963 100644 (file)
@@ -258,4 +258,10 @@ config CLKSRC_PXA
        help
          This enables OST0 support available on PXA and SA-11x0
          platforms.
+
+config CLKSRC_IMX_GPT
+       bool "Clocksource using i.MX GPT" if COMPILE_TEST
+       depends on ARM && CLKDEV_LOOKUP
+       select CLKSRC_MMIO
+
 endmenu
index 5b85f6adb25834c807c24aafa08ed0529b2e8a53..fce332cac646087e3884c7ad3902d1aa21235b77 100644 (file)
@@ -51,4 +51,5 @@ obj-$(CONFIG_ARCH_KEYSTONE)           += timer-keystone.o
 obj-$(CONFIG_ARCH_INTEGRATOR_AP)       += timer-integrator-ap.o
 obj-$(CONFIG_CLKSRC_VERSATILE)         += versatile.o
 obj-$(CONFIG_CLKSRC_MIPS_GIC)          += mips-gic-timer.o
+obj-$(CONFIG_CLKSRC_IMX_GPT)           += timer-imx-gpt.o
 obj-$(CONFIG_ASM9260_TIMER)            += asm9260_timer.o
diff --git a/drivers/clocksource/timer-imx-gpt.c b/drivers/clocksource/timer-imx-gpt.c
new file mode 100644 (file)
index 0000000..879c784
--- /dev/null
@@ -0,0 +1,540 @@
+/*
+ *  linux/arch/arm/plat-mxc/time.c
+ *
+ *  Copyright (C) 2000-2001 Deep Blue Solutions
+ *  Copyright (C) 2002 Shane Nay (shane@minirl.com)
+ *  Copyright (C) 2006-2007 Pavel Pisa (ppisa@pikron.com)
+ *  Copyright (C) 2008 Juergen Beisert (kernel@pengutronix.de)
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
+
+#include <linux/interrupt.h>
+#include <linux/irq.h>
+#include <linux/clockchips.h>
+#include <linux/clk.h>
+#include <linux/delay.h>
+#include <linux/err.h>
+#include <linux/sched_clock.h>
+#include <linux/slab.h>
+#include <linux/of.h>
+#include <linux/of_address.h>
+#include <linux/of_irq.h>
+#include <soc/imx/timer.h>
+
+/*
+ * There are 4 versions of the timer hardware on Freescale MXC hardware.
+ *  - MX1/MXL
+ *  - MX21, MX27.
+ *  - MX25, MX31, MX35, MX37, MX51, MX6Q(rev1.0)
+ *  - MX6DL, MX6SX, MX6Q(rev1.1+)
+ */
+
+/* defines common for all i.MX */
+#define MXC_TCTL               0x00
+#define MXC_TCTL_TEN           (1 << 0) /* Enable module */
+#define MXC_TPRER              0x04
+
+/* MX1, MX21, MX27 */
+#define MX1_2_TCTL_CLK_PCLK1   (1 << 1)
+#define MX1_2_TCTL_IRQEN       (1 << 4)
+#define MX1_2_TCTL_FRR         (1 << 8)
+#define MX1_2_TCMP             0x08
+#define MX1_2_TCN              0x10
+#define MX1_2_TSTAT            0x14
+
+/* MX21, MX27 */
+#define MX2_TSTAT_CAPT         (1 << 1)
+#define MX2_TSTAT_COMP         (1 << 0)
+
+/* MX31, MX35, MX25, MX5, MX6 */
+#define V2_TCTL_WAITEN         (1 << 3) /* Wait enable mode */
+#define V2_TCTL_CLK_IPG                (1 << 6)
+#define V2_TCTL_CLK_PER                (2 << 6)
+#define V2_TCTL_CLK_OSC_DIV8   (5 << 6)
+#define V2_TCTL_FRR            (1 << 9)
+#define V2_TCTL_24MEN          (1 << 10)
+#define V2_TPRER_PRE24M                12
+#define V2_IR                  0x0c
+#define V2_TSTAT               0x08
+#define V2_TSTAT_OF1           (1 << 0)
+#define V2_TCN                 0x24
+#define V2_TCMP                        0x10
+
+#define V2_TIMER_RATE_OSC_DIV8 3000000
+
+struct imx_timer {
+       enum imx_gpt_type type;
+       void __iomem *base;
+       int irq;
+       struct clk *clk_per;
+       struct clk *clk_ipg;
+       const struct imx_gpt_data *gpt;
+       struct clock_event_device ced;
+       enum clock_event_mode cem;
+       struct irqaction act;
+};
+
+struct imx_gpt_data {
+       int reg_tstat;
+       int reg_tcn;
+       int reg_tcmp;
+       void (*gpt_setup_tctl)(struct imx_timer *imxtm);
+       void (*gpt_irq_enable)(struct imx_timer *imxtm);
+       void (*gpt_irq_disable)(struct imx_timer *imxtm);
+       void (*gpt_irq_acknowledge)(struct imx_timer *imxtm);
+       int (*set_next_event)(unsigned long evt,
+                             struct clock_event_device *ced);
+};
+
+static inline struct imx_timer *to_imx_timer(struct clock_event_device *ced)
+{
+       return container_of(ced, struct imx_timer, ced);
+}
+
+static void imx1_gpt_irq_disable(struct imx_timer *imxtm)
+{
+       unsigned int tmp;
+
+       tmp = readl_relaxed(imxtm->base + MXC_TCTL);
+       writel_relaxed(tmp & ~MX1_2_TCTL_IRQEN, imxtm->base + MXC_TCTL);
+}
+#define imx21_gpt_irq_disable imx1_gpt_irq_disable
+
+static void imx31_gpt_irq_disable(struct imx_timer *imxtm)
+{
+       writel_relaxed(0, imxtm->base + V2_IR);
+}
+#define imx6dl_gpt_irq_disable imx31_gpt_irq_disable
+
+static void imx1_gpt_irq_enable(struct imx_timer *imxtm)
+{
+       unsigned int tmp;
+
+       tmp = readl_relaxed(imxtm->base + MXC_TCTL);
+       writel_relaxed(tmp | MX1_2_TCTL_IRQEN, imxtm->base + MXC_TCTL);
+}
+#define imx21_gpt_irq_enable imx1_gpt_irq_enable
+
+static void imx31_gpt_irq_enable(struct imx_timer *imxtm)
+{
+       writel_relaxed(1<<0, imxtm->base + V2_IR);
+}
+#define imx6dl_gpt_irq_enable imx31_gpt_irq_enable
+
+static void imx1_gpt_irq_acknowledge(struct imx_timer *imxtm)
+{
+       writel_relaxed(0, imxtm->base + MX1_2_TSTAT);
+}
+
+static void imx21_gpt_irq_acknowledge(struct imx_timer *imxtm)
+{
+       writel_relaxed(MX2_TSTAT_CAPT | MX2_TSTAT_COMP,
+                               imxtm->base + MX1_2_TSTAT);
+}
+
+static void imx31_gpt_irq_acknowledge(struct imx_timer *imxtm)
+{
+       writel_relaxed(V2_TSTAT_OF1, imxtm->base + V2_TSTAT);
+}
+#define imx6dl_gpt_irq_acknowledge imx31_gpt_irq_acknowledge
+
+static void __iomem *sched_clock_reg;
+
+static u64 notrace mxc_read_sched_clock(void)
+{
+       return sched_clock_reg ? readl_relaxed(sched_clock_reg) : 0;
+}
+
+static struct delay_timer imx_delay_timer;
+
+static unsigned long imx_read_current_timer(void)
+{
+       return readl_relaxed(sched_clock_reg);
+}
+
+static int __init mxc_clocksource_init(struct imx_timer *imxtm)
+{
+       unsigned int c = clk_get_rate(imxtm->clk_per);
+       void __iomem *reg = imxtm->base + imxtm->gpt->reg_tcn;
+
+       imx_delay_timer.read_current_timer = &imx_read_current_timer;
+       imx_delay_timer.freq = c;
+       register_current_timer_delay(&imx_delay_timer);
+
+       sched_clock_reg = reg;
+
+       sched_clock_register(mxc_read_sched_clock, 32, c);
+       return clocksource_mmio_init(reg, "mxc_timer1", c, 200, 32,
+                       clocksource_mmio_readl_up);
+}
+
+/* clock event */
+
+static int mx1_2_set_next_event(unsigned long evt,
+                             struct clock_event_device *ced)
+{
+       struct imx_timer *imxtm = to_imx_timer(ced);
+       unsigned long tcmp;
+
+       tcmp = readl_relaxed(imxtm->base + MX1_2_TCN) + evt;
+
+       writel_relaxed(tcmp, imxtm->base + MX1_2_TCMP);
+
+       return (int)(tcmp - readl_relaxed(imxtm->base + MX1_2_TCN)) < 0 ?
+                               -ETIME : 0;
+}
+
+static int v2_set_next_event(unsigned long evt,
+                             struct clock_event_device *ced)
+{
+       struct imx_timer *imxtm = to_imx_timer(ced);
+       unsigned long tcmp;
+
+       tcmp = readl_relaxed(imxtm->base + V2_TCN) + evt;
+
+       writel_relaxed(tcmp, imxtm->base + V2_TCMP);
+
+       return evt < 0x7fffffff &&
+               (int)(tcmp - readl_relaxed(imxtm->base + V2_TCN)) < 0 ?
+                               -ETIME : 0;
+}
+
+#ifdef DEBUG
+static const char *clock_event_mode_label[] = {
+       [CLOCK_EVT_MODE_PERIODIC] = "CLOCK_EVT_MODE_PERIODIC",
+       [CLOCK_EVT_MODE_ONESHOT]  = "CLOCK_EVT_MODE_ONESHOT",
+       [CLOCK_EVT_MODE_SHUTDOWN] = "CLOCK_EVT_MODE_SHUTDOWN",
+       [CLOCK_EVT_MODE_UNUSED]   = "CLOCK_EVT_MODE_UNUSED",
+       [CLOCK_EVT_MODE_RESUME]   = "CLOCK_EVT_MODE_RESUME",
+};
+#endif /* DEBUG */
+
+static void mxc_set_mode(enum clock_event_mode mode,
+                               struct clock_event_device *ced)
+{
+       struct imx_timer *imxtm = to_imx_timer(ced);
+       unsigned long flags;
+
+       /*
+        * The timer interrupt generation is disabled at least
+        * for enough time to call mxc_set_next_event()
+        */
+       local_irq_save(flags);
+
+       /* Disable interrupt in GPT module */
+       imxtm->gpt->gpt_irq_disable(imxtm);
+
+       if (mode != imxtm->cem) {
+               u32 tcn = readl_relaxed(imxtm->base + imxtm->gpt->reg_tcn);
+               /* Set event time into far-far future */
+               writel_relaxed(tcn - 3, imxtm->base + imxtm->gpt->reg_tcmp);
+
+               /* Clear pending interrupt */
+               imxtm->gpt->gpt_irq_acknowledge(imxtm);
+       }
+
+#ifdef DEBUG
+       printk(KERN_INFO "mxc_set_mode: changing mode from %s to %s\n",
+               clock_event_mode_label[imxtm->cem],
+               clock_event_mode_label[mode]);
+#endif /* DEBUG */
+
+       /* Remember timer mode */
+       imxtm->cem = mode;
+       local_irq_restore(flags);
+
+       switch (mode) {
+       case CLOCK_EVT_MODE_PERIODIC:
+               printk(KERN_ERR"mxc_set_mode: Periodic mode is not "
+                               "supported for i.MX\n");
+               break;
+       case CLOCK_EVT_MODE_ONESHOT:
+       /*
+        * Do not put overhead of interrupt enable/disable into
+        * mxc_set_next_event(), the core has about 4 minutes
+        * to call mxc_set_next_event() or shutdown clock after
+        * mode switching
+        */
+               local_irq_save(flags);
+               imxtm->gpt->gpt_irq_enable(imxtm);
+               local_irq_restore(flags);
+               break;
+       case CLOCK_EVT_MODE_SHUTDOWN:
+       case CLOCK_EVT_MODE_UNUSED:
+       case CLOCK_EVT_MODE_RESUME:
+               /* Left event sources disabled, no more interrupts appear */
+               break;
+       }
+}
+
+/*
+ * IRQ handler for the timer
+ */
+static irqreturn_t mxc_timer_interrupt(int irq, void *dev_id)
+{
+       struct clock_event_device *ced = dev_id;
+       struct imx_timer *imxtm = to_imx_timer(ced);
+       uint32_t tstat;
+
+       tstat = readl_relaxed(imxtm->base + imxtm->gpt->reg_tstat);
+
+       imxtm->gpt->gpt_irq_acknowledge(imxtm);
+
+       ced->event_handler(ced);
+
+       return IRQ_HANDLED;
+}
+
+static int __init mxc_clockevent_init(struct imx_timer *imxtm)
+{
+       struct clock_event_device *ced = &imxtm->ced;
+       struct irqaction *act = &imxtm->act;
+
+       imxtm->cem = CLOCK_EVT_MODE_UNUSED;
+
+       ced->name = "mxc_timer1";
+       ced->features = CLOCK_EVT_FEAT_ONESHOT;
+       ced->set_mode = mxc_set_mode;
+       ced->set_next_event = imxtm->gpt->set_next_event;
+       ced->rating = 200;
+       ced->cpumask = cpumask_of(0);
+       clockevents_config_and_register(ced, clk_get_rate(imxtm->clk_per),
+                                       0xff, 0xfffffffe);
+
+       act->name = "i.MX Timer Tick";
+       act->flags = IRQF_TIMER | IRQF_IRQPOLL;
+       act->handler = mxc_timer_interrupt;
+       act->dev_id = ced;
+
+       return setup_irq(imxtm->irq, act);
+}
+
+static void imx1_gpt_setup_tctl(struct imx_timer *imxtm)
+{
+       u32 tctl_val;
+
+       tctl_val = MX1_2_TCTL_FRR | MX1_2_TCTL_CLK_PCLK1 | MXC_TCTL_TEN;
+       writel_relaxed(tctl_val, imxtm->base + MXC_TCTL);
+}
+#define imx21_gpt_setup_tctl imx1_gpt_setup_tctl
+
+static void imx31_gpt_setup_tctl(struct imx_timer *imxtm)
+{
+       u32 tctl_val;
+
+       tctl_val = V2_TCTL_FRR | V2_TCTL_WAITEN | MXC_TCTL_TEN;
+       if (clk_get_rate(imxtm->clk_per) == V2_TIMER_RATE_OSC_DIV8)
+               tctl_val |= V2_TCTL_CLK_OSC_DIV8;
+       else
+               tctl_val |= V2_TCTL_CLK_PER;
+
+       writel_relaxed(tctl_val, imxtm->base + MXC_TCTL);
+}
+
+static void imx6dl_gpt_setup_tctl(struct imx_timer *imxtm)
+{
+       u32 tctl_val;
+
+       tctl_val = V2_TCTL_FRR | V2_TCTL_WAITEN | MXC_TCTL_TEN;
+       if (clk_get_rate(imxtm->clk_per) == V2_TIMER_RATE_OSC_DIV8) {
+               tctl_val |= V2_TCTL_CLK_OSC_DIV8;
+               /* 24 / 8 = 3 MHz */
+               writel_relaxed(7 << V2_TPRER_PRE24M, imxtm->base + MXC_TPRER);
+               tctl_val |= V2_TCTL_24MEN;
+       } else {
+               tctl_val |= V2_TCTL_CLK_PER;
+       }
+
+       writel_relaxed(tctl_val, imxtm->base + MXC_TCTL);
+}
+
+static const struct imx_gpt_data imx1_gpt_data = {
+       .reg_tstat = MX1_2_TSTAT,
+       .reg_tcn = MX1_2_TCN,
+       .reg_tcmp = MX1_2_TCMP,
+       .gpt_irq_enable = imx1_gpt_irq_enable,
+       .gpt_irq_disable = imx1_gpt_irq_disable,
+       .gpt_irq_acknowledge = imx1_gpt_irq_acknowledge,
+       .gpt_setup_tctl = imx1_gpt_setup_tctl,
+       .set_next_event = mx1_2_set_next_event,
+};
+
+static const struct imx_gpt_data imx21_gpt_data = {
+       .reg_tstat = MX1_2_TSTAT,
+       .reg_tcn = MX1_2_TCN,
+       .reg_tcmp = MX1_2_TCMP,
+       .gpt_irq_enable = imx21_gpt_irq_enable,
+       .gpt_irq_disable = imx21_gpt_irq_disable,
+       .gpt_irq_acknowledge = imx21_gpt_irq_acknowledge,
+       .gpt_setup_tctl = imx21_gpt_setup_tctl,
+       .set_next_event = mx1_2_set_next_event,
+};
+
+static const struct imx_gpt_data imx31_gpt_data = {
+       .reg_tstat = V2_TSTAT,
+       .reg_tcn = V2_TCN,
+       .reg_tcmp = V2_TCMP,
+       .gpt_irq_enable = imx31_gpt_irq_enable,
+       .gpt_irq_disable = imx31_gpt_irq_disable,
+       .gpt_irq_acknowledge = imx31_gpt_irq_acknowledge,
+       .gpt_setup_tctl = imx31_gpt_setup_tctl,
+       .set_next_event = v2_set_next_event,
+};
+
+static const struct imx_gpt_data imx6dl_gpt_data = {
+       .reg_tstat = V2_TSTAT,
+       .reg_tcn = V2_TCN,
+       .reg_tcmp = V2_TCMP,
+       .gpt_irq_enable = imx6dl_gpt_irq_enable,
+       .gpt_irq_disable = imx6dl_gpt_irq_disable,
+       .gpt_irq_acknowledge = imx6dl_gpt_irq_acknowledge,
+       .gpt_setup_tctl = imx6dl_gpt_setup_tctl,
+       .set_next_event = v2_set_next_event,
+};
+
+static void __init _mxc_timer_init(struct imx_timer *imxtm)
+{
+       switch (imxtm->type) {
+       case GPT_TYPE_IMX1:
+               imxtm->gpt = &imx1_gpt_data;
+               break;
+       case GPT_TYPE_IMX21:
+               imxtm->gpt = &imx21_gpt_data;
+               break;
+       case GPT_TYPE_IMX31:
+               imxtm->gpt = &imx31_gpt_data;
+               break;
+       case GPT_TYPE_IMX6DL:
+               imxtm->gpt = &imx6dl_gpt_data;
+               break;
+       default:
+               BUG();
+       }
+
+       if (IS_ERR(imxtm->clk_per)) {
+               pr_err("i.MX timer: unable to get clk\n");
+               return;
+       }
+
+       if (!IS_ERR(imxtm->clk_ipg))
+               clk_prepare_enable(imxtm->clk_ipg);
+
+       clk_prepare_enable(imxtm->clk_per);
+
+       /*
+        * Initialise to a known state (all timers off, and timing reset)
+        */
+
+       writel_relaxed(0, imxtm->base + MXC_TCTL);
+       writel_relaxed(0, imxtm->base + MXC_TPRER); /* see datasheet note */
+
+       imxtm->gpt->gpt_setup_tctl(imxtm);
+
+       /* init and register the timer to the framework */
+       mxc_clocksource_init(imxtm);
+       mxc_clockevent_init(imxtm);
+}
+
+void __init mxc_timer_init(unsigned long pbase, int irq, enum imx_gpt_type type)
+{
+       struct imx_timer *imxtm;
+
+       imxtm = kzalloc(sizeof(*imxtm), GFP_KERNEL);
+       BUG_ON(!imxtm);
+
+       imxtm->clk_per = clk_get_sys("imx-gpt.0", "per");
+       imxtm->clk_ipg = clk_get_sys("imx-gpt.0", "ipg");
+
+       imxtm->base = ioremap(pbase, SZ_4K);
+       BUG_ON(!imxtm->base);
+
+       imxtm->type = type;
+
+       _mxc_timer_init(imxtm);
+}
+
+static void __init mxc_timer_init_dt(struct device_node *np,  enum imx_gpt_type type)
+{
+       struct imx_timer *imxtm;
+       static int initialized;
+
+       /* Support one instance only */
+       if (initialized)
+               return;
+
+       imxtm = kzalloc(sizeof(*imxtm), GFP_KERNEL);
+       BUG_ON(!imxtm);
+
+       imxtm->base = of_iomap(np, 0);
+       WARN_ON(!imxtm->base);
+       imxtm->irq = irq_of_parse_and_map(np, 0);
+
+       imxtm->clk_ipg = of_clk_get_by_name(np, "ipg");
+
+       /* Try osc_per first, and fall back to per otherwise */
+       imxtm->clk_per = of_clk_get_by_name(np, "osc_per");
+       if (IS_ERR(imxtm->clk_per))
+               imxtm->clk_per = of_clk_get_by_name(np, "per");
+
+       imxtm->type = type;
+
+       _mxc_timer_init(imxtm);
+
+       initialized = 1;
+}
+
+static void __init imx1_timer_init_dt(struct device_node *np)
+{
+       mxc_timer_init_dt(np, GPT_TYPE_IMX1);
+}
+
+static void __init imx21_timer_init_dt(struct device_node *np)
+{
+       mxc_timer_init_dt(np, GPT_TYPE_IMX21);
+}
+
+static void __init imx31_timer_init_dt(struct device_node *np)
+{
+       enum imx_gpt_type type = GPT_TYPE_IMX31;
+
+       /*
+        * We were using the same compatible string for i.MX6Q/D and i.MX6DL/S
+        * GPT device, while they actually have different programming model.
+        * This is a workaround to keep the existing i.MX6DL/S DTBs continue
+        * working with the new kernel.
+        */
+       if (of_machine_is_compatible("fsl,imx6dl"))
+               type = GPT_TYPE_IMX6DL;
+
+       mxc_timer_init_dt(np, type);
+}
+
+static void __init imx6dl_timer_init_dt(struct device_node *np)
+{
+       mxc_timer_init_dt(np, GPT_TYPE_IMX6DL);
+}
+
+CLOCKSOURCE_OF_DECLARE(imx1_timer, "fsl,imx1-gpt", imx1_timer_init_dt);
+CLOCKSOURCE_OF_DECLARE(imx21_timer, "fsl,imx21-gpt", imx21_timer_init_dt);
+CLOCKSOURCE_OF_DECLARE(imx31_timer, "fsl,imx31-gpt", imx31_timer_init_dt);
+CLOCKSOURCE_OF_DECLARE(imx25_timer, "fsl,imx25-gpt", imx31_timer_init_dt);
+CLOCKSOURCE_OF_DECLARE(imx50_timer, "fsl,imx50-gpt", imx31_timer_init_dt);
+CLOCKSOURCE_OF_DECLARE(imx51_timer, "fsl,imx51-gpt", imx31_timer_init_dt);
+CLOCKSOURCE_OF_DECLARE(imx53_timer, "fsl,imx53-gpt", imx31_timer_init_dt);
+CLOCKSOURCE_OF_DECLARE(imx6q_timer, "fsl,imx6q-gpt", imx31_timer_init_dt);
+CLOCKSOURCE_OF_DECLARE(imx6dl_timer, "fsl,imx6dl-gpt", imx6dl_timer_init_dt);
+CLOCKSOURCE_OF_DECLARE(imx6sl_timer, "fsl,imx6sl-gpt", imx6dl_timer_init_dt);
+CLOCKSOURCE_OF_DECLARE(imx6sx_timer, "fsl,imx6sx-gpt", imx6dl_timer_init_dt);
index 6de62a96e79c80e9d442ca07f53549cf334f8c7c..99b9a979297531e67960a75d35917e93c2223368 100644 (file)
@@ -30,6 +30,7 @@ config ARM_GIC_V3_ITS
 config ARM_NVIC
        bool
        select IRQ_DOMAIN
+       select IRQ_DOMAIN_HIERARCHY
        select GENERIC_IRQ_CHIP
 
 config ARM_VIC
index 4ff0805fca017376ea879f918517b9d61abf5ff6..5fac9100f6cbee9f7abf144eb4dcb9efeb3aaee0 100644 (file)
@@ -49,6 +49,31 @@ nvic_handle_irq(irq_hw_number_t hwirq, struct pt_regs *regs)
        handle_IRQ(irq, regs);
 }
 
+static int nvic_irq_domain_alloc(struct irq_domain *domain, unsigned int virq,
+                               unsigned int nr_irqs, void *arg)
+{
+       int i, ret;
+       irq_hw_number_t hwirq;
+       unsigned int type = IRQ_TYPE_NONE;
+       struct of_phandle_args *irq_data = arg;
+
+       ret = irq_domain_xlate_onecell(domain, irq_data->np, irq_data->args,
+                                  irq_data->args_count, &hwirq, &type);
+       if (ret)
+               return ret;
+
+       for (i = 0; i < nr_irqs; i++)
+               irq_map_generic_chip(domain, virq + i, hwirq + i);
+
+       return 0;
+}
+
+static const struct irq_domain_ops nvic_irq_domain_ops = {
+       .xlate = irq_domain_xlate_onecell,
+       .alloc = nvic_irq_domain_alloc,
+       .free = irq_domain_free_irqs_top,
+};
+
 static int __init nvic_of_init(struct device_node *node,
                               struct device_node *parent)
 {
@@ -70,7 +95,8 @@ static int __init nvic_of_init(struct device_node *node,
                irqs = NVIC_MAX_IRQ;
 
        nvic_irq_domain =
-               irq_domain_add_linear(node, irqs, &irq_generic_chip_ops, NULL);
+               irq_domain_add_linear(node, irqs, &nvic_irq_domain_ops, NULL);
+
        if (!nvic_irq_domain) {
                pr_warn("Failed to allocate irq domain\n");
                return -ENOMEM;
index 9521057d47448a4f290df3d760e7df044968c427..b932ecb7b730f37058904cca791ac4c1df8a09ce 100644 (file)
@@ -47,6 +47,7 @@ struct vf610_mscm_ir_chip_data {
        void __iomem *mscm_ir_base;
        u16 cpu_mask;
        u16 saved_irsprc[MSCM_IRSPRC_NUM];
+       bool is_nvic;
 };
 
 static struct vf610_mscm_ir_chip_data *mscm_ir_data;
@@ -101,7 +102,7 @@ static void vf610_mscm_ir_enable(struct irq_data *data)
        writew_relaxed(chip_data->cpu_mask,
                       chip_data->mscm_ir_base + MSCM_IRSPRC(hwirq));
 
-       irq_chip_unmask_parent(data);
+       irq_chip_enable_parent(data);
 }
 
 static void vf610_mscm_ir_disable(struct irq_data *data)
@@ -111,7 +112,7 @@ static void vf610_mscm_ir_disable(struct irq_data *data)
 
        writew_relaxed(0x0, chip_data->mscm_ir_base + MSCM_IRSPRC(hwirq));
 
-       irq_chip_mask_parent(data);
+       irq_chip_disable_parent(data);
 }
 
 static struct irq_chip vf610_mscm_ir_irq_chip = {
@@ -143,10 +144,17 @@ static int vf610_mscm_ir_domain_alloc(struct irq_domain *domain, unsigned int vi
                                              domain->host_data);
 
        gic_data.np = domain->parent->of_node;
-       gic_data.args_count = 3;
-       gic_data.args[0] = GIC_SPI;
-       gic_data.args[1] = irq_data->args[0];
-       gic_data.args[2] = irq_data->args[1];
+
+       if (mscm_ir_data->is_nvic) {
+               gic_data.args_count = 1;
+               gic_data.args[0] = irq_data->args[0];
+       } else {
+               gic_data.args_count = 3;
+               gic_data.args[0] = GIC_SPI;
+               gic_data.args[1] = irq_data->args[0];
+               gic_data.args[2] = irq_data->args[1];
+       }
+
        return irq_domain_alloc_irqs_parent(domain, virq, nr_irqs, &gic_data);
 }
 
@@ -199,6 +207,9 @@ static int __init vf610_mscm_ir_of_init(struct device_node *node,
                goto out_unmap;
        }
 
+       if (of_device_is_compatible(domain->parent->of_node, "arm,armv7m-nvic"))
+               mscm_ir_data->is_nvic = true;
+
        cpu_pm_register_notifier(&mscm_ir_notifier_block);
 
        return 0;
index 868036f70f8f126c0e81e16fe8bd4af63319909a..8406c668ecdc49161795f578e773afeb132058e8 100644 (file)
@@ -49,6 +49,14 @@ config OMAP_GPMC
          interfacing to a variety of asynchronous as well as synchronous
          memory drives like NOR, NAND, OneNAND, SRAM.
 
+config OMAP_GPMC_DEBUG
+       bool
+       depends on OMAP_GPMC
+       help
+         Enables verbose debugging mostly to decode the bootloader provided
+         timings. Enable this during development to configure devices
+         connected to the GPMC bus.
+
 config MVEBU_DEVBUS
        bool "Marvell EBU Device Bus Controller"
        default y
index c94ea0d687467f176e19d44dae06ebe0efaef899..8911e51d410ab3c6e8d14af25fb5c1ff7751b47d 100644 (file)
@@ -403,7 +403,7 @@ static void gpmc_cs_bool_timings(int cs, const struct gpmc_bool_timings *p)
                           p->cycle2cyclediffcsen);
 }
 
-#ifdef DEBUG
+#ifdef CONFIG_OMAP_GPMC_DEBUG
 /**
  * get_gpmc_timing_reg - read a timing parameter and print DTS settings for it.
  * @cs:      Chip Select Region
@@ -612,7 +612,7 @@ static int set_gpmc_timing_reg(int cs, int reg, int st_bit, int end_bit, int max
        }
 
        l = gpmc_cs_read_reg(cs, reg);
-#ifdef DEBUG
+#ifdef CONFIG_OMAP_GPMC_DEBUG
        pr_info(
                "GPMC CS%d: %-17s: %3d ticks, %3lu ns (was %3i ticks) %3d ns\n",
               cs, name, ticks, gpmc_get_clk_period(cs, cd) * ticks / 1000,
@@ -767,7 +767,7 @@ int gpmc_cs_set_timings(int cs, const struct gpmc_timings *t,
                            GPMC_CONFIG1_CLKACTIVATIONTIME_MAX,
                            clk_activation, GPMC_CD_FCLK);
 
-#ifdef DEBUG
+#ifdef CONFIG_OMAP_GPMC_DEBUG
        pr_info("GPMC CS%d CLK period is %lu ns (div %d)\n",
                        cs, (div * gpmc_get_fclk_period()) / 1000, div);
 #endif
index 5eff6f097f980ceb1c5de96b114c7fc686663293..6acc2c44ee2c9afd70bf121786a7267819a86c88 100644 (file)
@@ -59,6 +59,7 @@ static u32 tegra20_fuse_readl(const unsigned int offset)
        int ret;
        u32 val = 0;
        struct dma_async_tx_descriptor *dma_desc;
+       unsigned long time_left;
 
        mutex_lock(&apb_dma_lock);
 
@@ -82,9 +83,10 @@ static u32 tegra20_fuse_readl(const unsigned int offset)
 
        dmaengine_submit(dma_desc);
        dma_async_issue_pending(apb_dma_chan);
-       ret = wait_for_completion_timeout(&apb_dma_wait, msecs_to_jiffies(50));
+       time_left = wait_for_completion_timeout(&apb_dma_wait,
+                                               msecs_to_jiffies(50));
 
-       if (WARN(ret == 0, "apb read dma timed out"))
+       if (WARN(time_left == 0, "apb read dma timed out"))
                dmaengine_terminate_all(apb_dma_chan);
        else
                val = *apb_buffer;
index c956395cf46f961beaf6f56674d20f58b2c717b6..cc119d15dd1616feeef9821ecf98c94fc19ecfec 100644 (file)
@@ -377,13 +377,10 @@ int tegra_pmc_cpu_remove_clamping(int cpuid)
 }
 #endif /* CONFIG_SMP */
 
-/**
- * tegra_pmc_restart() - reboot the system
- * @mode: which mode to reboot in
- * @cmd: reboot command
- */
-void tegra_pmc_restart(enum reboot_mode mode, const char *cmd)
+static int tegra_pmc_restart_notify(struct notifier_block *this,
+                                   unsigned long action, void *data)
 {
+       const char *cmd = data;
        u32 value;
 
        value = tegra_pmc_readl(PMC_SCRATCH0);
@@ -405,8 +402,15 @@ void tegra_pmc_restart(enum reboot_mode mode, const char *cmd)
        value = tegra_pmc_readl(0);
        value |= 0x10;
        tegra_pmc_writel(value, 0);
+
+       return NOTIFY_DONE;
 }
 
+static struct notifier_block tegra_pmc_restart_handler = {
+       .notifier_call = tegra_pmc_restart_notify,
+       .priority = 128,
+};
+
 static int powergate_show(struct seq_file *s, void *data)
 {
        unsigned int i;
@@ -837,6 +841,13 @@ static int tegra_pmc_probe(struct platform_device *pdev)
                        return err;
        }
 
+       err = register_restart_handler(&tegra_pmc_restart_handler);
+       if (err) {
+               dev_err(&pdev->dev, "unable to register restart handler, %d\n",
+                       err);
+               return err;
+       }
+
        return 0;
 }
 
index 2b5a9bbf80b7e08989040d9b46d890ff54b06813..7116968dee12944ebca036127aedc136825f2dda 100644 (file)
  * option) any later version.
  */
 
+#include <linux/delay.h>
+#include <linux/reboot.h>
 #include <linux/types.h>
 #include <linux/module.h>
 #include <linux/io.h>
 #include <linux/watchdog.h>
 #include <linux/platform_device.h>
 #include <linux/of_address.h>
+#include <linux/of_platform.h>
 
 #define PM_RSTC                                0x1c
+#define PM_RSTS                                0x20
 #define PM_WDOG                                0x24
 
 #define PM_PASSWORD                    0x5a000000
 
 #define PM_WDOG_TIME_SET               0x000fffff
 #define PM_RSTC_WRCFG_CLR              0xffffffcf
+#define PM_RSTS_HADWRH_SET             0x00000040
 #define PM_RSTC_WRCFG_SET              0x00000030
 #define PM_RSTC_WRCFG_FULL_RESET       0x00000020
 #define PM_RSTC_RESET                  0x00000102
@@ -37,6 +42,7 @@
 struct bcm2835_wdt {
        void __iomem            *base;
        spinlock_t              lock;
+       struct notifier_block   restart_handler;
 };
 
 static unsigned int heartbeat;
@@ -106,6 +112,53 @@ static struct watchdog_device bcm2835_wdt_wdd = {
        .timeout =      WDOG_TICKS_TO_SECS(PM_WDOG_TIME_SET),
 };
 
+static int
+bcm2835_restart(struct notifier_block *this, unsigned long mode, void *cmd)
+{
+       struct bcm2835_wdt *wdt = container_of(this, struct bcm2835_wdt,
+                                              restart_handler);
+       u32 val;
+
+       /* use a timeout of 10 ticks (~150us) */
+       writel_relaxed(10 | PM_PASSWORD, wdt->base + PM_WDOG);
+       val = readl_relaxed(wdt->base + PM_RSTC);
+       val &= PM_RSTC_WRCFG_CLR;
+       val |= PM_PASSWORD | PM_RSTC_WRCFG_FULL_RESET;
+       writel_relaxed(val, wdt->base + PM_RSTC);
+
+       /* No sleeping, possibly atomic. */
+       mdelay(1);
+
+       return 0;
+}
+
+/*
+ * We can't really power off, but if we do the normal reset scheme, and
+ * indicate to bootcode.bin not to reboot, then most of the chip will be
+ * powered off.
+ */
+static void bcm2835_power_off(void)
+{
+       struct device_node *np =
+               of_find_compatible_node(NULL, NULL, "brcm,bcm2835-pm-wdt");
+       struct platform_device *pdev = of_find_device_by_node(np);
+       struct bcm2835_wdt *wdt = platform_get_drvdata(pdev);
+       u32 val;
+
+       /*
+        * We set the watchdog hard reset bit here to distinguish this reset
+        * from the normal (full) reset. bootcode.bin will not reboot after a
+        * hard reset.
+        */
+       val = readl_relaxed(wdt->base + PM_RSTS);
+       val &= PM_RSTC_WRCFG_CLR;
+       val |= PM_PASSWORD | PM_RSTS_HADWRH_SET;
+       writel_relaxed(val, wdt->base + PM_RSTS);
+
+       /* Continue with normal reset mechanism */
+       bcm2835_restart(&wdt->restart_handler, REBOOT_HARD, NULL);
+}
+
 static int bcm2835_wdt_probe(struct platform_device *pdev)
 {
        struct device *dev = &pdev->dev;
@@ -136,6 +189,12 @@ static int bcm2835_wdt_probe(struct platform_device *pdev)
                return err;
        }
 
+       wdt->restart_handler.notifier_call = bcm2835_restart;
+       wdt->restart_handler.priority = 128;
+       register_restart_handler(&wdt->restart_handler);
+       if (pm_power_off == NULL)
+               pm_power_off = bcm2835_power_off;
+
        dev_info(dev, "Broadcom BCM2835 watchdog timer");
        return 0;
 }
@@ -144,6 +203,9 @@ static int bcm2835_wdt_remove(struct platform_device *pdev)
 {
        struct bcm2835_wdt *wdt = platform_get_drvdata(pdev);
 
+       unregister_restart_handler(&wdt->restart_handler);
+       if (pm_power_off == bcm2835_power_off)
+               pm_power_off = NULL;
        watchdog_unregister_device(&bcm2835_wdt_wdd);
        iounmap(wdt->base);
 
diff --git a/include/dt-bindings/clock/imx7d-clock.h b/include/dt-bindings/clock/imx7d-clock.h
new file mode 100644 (file)
index 0000000..728df28
--- /dev/null
@@ -0,0 +1,450 @@
+/*
+ * Copyright (C) 2014-2015 Freescale Semiconductor, Inc.
+ *
+ * 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.
+ *
+ */
+
+#ifndef __DT_BINDINGS_CLOCK_IMX7D_H
+#define __DT_BINDINGS_CLOCK_IMX7D_H
+
+#define IMX7D_OSC_24M_CLK              0
+#define IMX7D_PLL_ARM_MAIN             1
+#define IMX7D_PLL_ARM_MAIN_CLK         2
+#define IMX7D_PLL_ARM_MAIN_SRC         3
+#define IMX7D_PLL_ARM_MAIN_BYPASS      4
+#define IMX7D_PLL_SYS_MAIN             5
+#define IMX7D_PLL_SYS_MAIN_CLK         6
+#define IMX7D_PLL_SYS_MAIN_SRC         7
+#define IMX7D_PLL_SYS_MAIN_BYPASS      8
+#define IMX7D_PLL_SYS_MAIN_480M                9
+#define IMX7D_PLL_SYS_MAIN_240M                10
+#define IMX7D_PLL_SYS_MAIN_120M                11
+#define IMX7D_PLL_SYS_MAIN_480M_CLK    12
+#define IMX7D_PLL_SYS_MAIN_240M_CLK    13
+#define IMX7D_PLL_SYS_MAIN_120M_CLK    14
+#define IMX7D_PLL_SYS_PFD0_392M_CLK    15
+#define IMX7D_PLL_SYS_PFD0_196M                16
+#define IMX7D_PLL_SYS_PFD0_196M_CLK    17
+#define IMX7D_PLL_SYS_PFD1_332M_CLK    18
+#define IMX7D_PLL_SYS_PFD1_166M                19
+#define IMX7D_PLL_SYS_PFD1_166M_CLK    20
+#define IMX7D_PLL_SYS_PFD2_270M_CLK    21
+#define IMX7D_PLL_SYS_PFD2_135M                22
+#define IMX7D_PLL_SYS_PFD2_135M_CLK    23
+#define IMX7D_PLL_SYS_PFD3_CLK         24
+#define IMX7D_PLL_SYS_PFD4_CLK         25
+#define IMX7D_PLL_SYS_PFD5_CLK         26
+#define IMX7D_PLL_SYS_PFD6_CLK         27
+#define IMX7D_PLL_SYS_PFD7_CLK         28
+#define IMX7D_PLL_ENET_MAIN            29
+#define IMX7D_PLL_ENET_MAIN_CLK                30
+#define IMX7D_PLL_ENET_MAIN_SRC                31
+#define IMX7D_PLL_ENET_MAIN_BYPASS     32
+#define IMX7D_PLL_ENET_MAIN_500M       33
+#define IMX7D_PLL_ENET_MAIN_250M       34
+#define IMX7D_PLL_ENET_MAIN_125M       35
+#define IMX7D_PLL_ENET_MAIN_100M       36
+#define IMX7D_PLL_ENET_MAIN_50M                37
+#define IMX7D_PLL_ENET_MAIN_40M                38
+#define IMX7D_PLL_ENET_MAIN_25M                39
+#define IMX7D_PLL_ENET_MAIN_500M_CLK   40
+#define IMX7D_PLL_ENET_MAIN_250M_CLK   41
+#define IMX7D_PLL_ENET_MAIN_125M_CLK   42
+#define IMX7D_PLL_ENET_MAIN_100M_CLK   43
+#define IMX7D_PLL_ENET_MAIN_50M_CLK    44
+#define IMX7D_PLL_ENET_MAIN_40M_CLK    45
+#define IMX7D_PLL_ENET_MAIN_25M_CLK    46
+#define IMX7D_PLL_DRAM_MAIN            47
+#define IMX7D_PLL_DRAM_MAIN_CLK                48
+#define IMX7D_PLL_DRAM_MAIN_SRC                49
+#define IMX7D_PLL_DRAM_MAIN_BYPASS     50
+#define IMX7D_PLL_DRAM_MAIN_533M       51
+#define IMX7D_PLL_DRAM_MAIN_533M_CLK   52
+#define IMX7D_PLL_AUDIO_MAIN           53
+#define IMX7D_PLL_AUDIO_MAIN_CLK       54
+#define IMX7D_PLL_AUDIO_MAIN_SRC       55
+#define IMX7D_PLL_AUDIO_MAIN_BYPASS    56
+#define IMX7D_PLL_VIDEO_MAIN_CLK       57
+#define IMX7D_PLL_VIDEO_MAIN           58
+#define IMX7D_PLL_VIDEO_MAIN_SRC       59
+#define IMX7D_PLL_VIDEO_MAIN_BYPASS    60
+#define IMX7D_USB_MAIN_480M_CLK                61
+#define IMX7D_ARM_A7_ROOT_CLK          62
+#define IMX7D_ARM_A7_ROOT_SRC          63
+#define IMX7D_ARM_A7_ROOT_CG           64
+#define IMX7D_ARM_A7_ROOT_DIV          65
+#define IMX7D_ARM_M4_ROOT_CLK          66
+#define IMX7D_ARM_M4_ROOT_SRC          67
+#define IMX7D_ARM_M4_ROOT_CG           68
+#define IMX7D_ARM_M4_ROOT_DIV          69
+#define IMX7D_ARM_M0_ROOT_CLK          70
+#define IMX7D_ARM_M0_ROOT_SRC          71
+#define IMX7D_ARM_M0_ROOT_CG           72
+#define IMX7D_ARM_M0_ROOT_DIV          73
+#define IMX7D_MAIN_AXI_ROOT_CLK                74
+#define IMX7D_MAIN_AXI_ROOT_SRC                75
+#define IMX7D_MAIN_AXI_ROOT_CG         76
+#define IMX7D_MAIN_AXI_ROOT_DIV                77
+#define IMX7D_DISP_AXI_ROOT_CLK                78
+#define IMX7D_DISP_AXI_ROOT_SRC                79
+#define IMX7D_DISP_AXI_ROOT_CG         80
+#define IMX7D_DISP_AXI_ROOT_DIV                81
+#define IMX7D_ENET_AXI_ROOT_CLK                82
+#define IMX7D_ENET_AXI_ROOT_SRC                83
+#define IMX7D_ENET_AXI_ROOT_CG         84
+#define IMX7D_ENET_AXI_ROOT_DIV                85
+#define IMX7D_NAND_USDHC_BUS_ROOT_CLK  86
+#define IMX7D_NAND_USDHC_BUS_ROOT_SRC  87
+#define IMX7D_NAND_USDHC_BUS_ROOT_CG   88
+#define IMX7D_NAND_USDHC_BUS_ROOT_DIV  89
+#define IMX7D_AHB_CHANNEL_ROOT_CLK     90
+#define IMX7D_AHB_CHANNEL_ROOT_SRC     91
+#define IMX7D_AHB_CHANNEL_ROOT_CG      92
+#define IMX7D_AHB_CHANNEL_ROOT_DIV     93
+#define IMX7D_DRAM_PHYM_ROOT_CLK       94
+#define IMX7D_DRAM_PHYM_ROOT_SRC       95
+#define IMX7D_DRAM_PHYM_ROOT_CG                96
+#define IMX7D_DRAM_PHYM_ROOT_DIV       97
+#define IMX7D_DRAM_ROOT_CLK            98
+#define IMX7D_DRAM_ROOT_SRC            99
+#define IMX7D_DRAM_ROOT_CG             100
+#define IMX7D_DRAM_ROOT_DIV            101
+#define IMX7D_DRAM_PHYM_ALT_ROOT_CLK   102
+#define IMX7D_DRAM_PHYM_ALT_ROOT_SRC   103
+#define IMX7D_DRAM_PHYM_ALT_ROOT_CG    104
+#define IMX7D_DRAM_PHYM_ALT_ROOT_DIV   105
+#define IMX7D_DRAM_ALT_ROOT_CLK                106
+#define IMX7D_DRAM_ALT_ROOT_SRC                107
+#define IMX7D_DRAM_ALT_ROOT_CG         108
+#define IMX7D_DRAM_ALT_ROOT_DIV                109
+#define IMX7D_USB_HSIC_ROOT_CLK                110
+#define IMX7D_USB_HSIC_ROOT_SRC                111
+#define IMX7D_USB_HSIC_ROOT_CG         112
+#define IMX7D_USB_HSIC_ROOT_DIV                113
+#define IMX7D_PCIE_CTRL_ROOT_CLK       114
+#define IMX7D_PCIE_CTRL_ROOT_SRC       115
+#define IMX7D_PCIE_CTRL_ROOT_CG                116
+#define IMX7D_PCIE_CTRL_ROOT_DIV       117
+#define IMX7D_PCIE_PHY_ROOT_CLK                118
+#define IMX7D_PCIE_PHY_ROOT_SRC                119
+#define IMX7D_PCIE_PHY_ROOT_CG         120
+#define IMX7D_PCIE_PHY_ROOT_DIV                121
+#define IMX7D_EPDC_PIXEL_ROOT_CLK      122
+#define IMX7D_EPDC_PIXEL_ROOT_SRC      123
+#define IMX7D_EPDC_PIXEL_ROOT_CG       124
+#define IMX7D_EPDC_PIXEL_ROOT_DIV      125
+#define IMX7D_LCDIF_PIXEL_ROOT_CLK     126
+#define IMX7D_LCDIF_PIXEL_ROOT_SRC     127
+#define IMX7D_LCDIF_PIXEL_ROOT_CG      128
+#define IMX7D_LCDIF_PIXEL_ROOT_DIV     129
+#define IMX7D_MIPI_DSI_ROOT_CLK                130
+#define IMX7D_MIPI_DSI_ROOT_SRC                131
+#define IMX7D_MIPI_DSI_ROOT_CG         132
+#define IMX7D_MIPI_DSI_ROOT_DIV                133
+#define IMX7D_MIPI_CSI_ROOT_CLK                134
+#define IMX7D_MIPI_CSI_ROOT_SRC                135
+#define IMX7D_MIPI_CSI_ROOT_CG         136
+#define IMX7D_MIPI_CSI_ROOT_DIV                137
+#define IMX7D_MIPI_DPHY_ROOT_CLK       138
+#define IMX7D_MIPI_DPHY_ROOT_SRC       139
+#define IMX7D_MIPI_DPHY_ROOT_CG                140
+#define IMX7D_MIPI_DPHY_ROOT_DIV       141
+#define IMX7D_SAI1_ROOT_CLK            142
+#define IMX7D_SAI1_ROOT_SRC            143
+#define IMX7D_SAI1_ROOT_CG             144
+#define IMX7D_SAI1_ROOT_DIV            145
+#define IMX7D_SAI2_ROOT_CLK            146
+#define IMX7D_SAI2_ROOT_SRC            147
+#define IMX7D_SAI2_ROOT_CG             148
+#define IMX7D_SAI2_ROOT_DIV            149
+#define IMX7D_SAI3_ROOT_CLK            150
+#define IMX7D_SAI3_ROOT_SRC            151
+#define IMX7D_SAI3_ROOT_CG             152
+#define IMX7D_SAI3_ROOT_DIV            153
+#define IMX7D_SPDIF_ROOT_CLK           154
+#define IMX7D_SPDIF_ROOT_SRC           155
+#define IMX7D_SPDIF_ROOT_CG            156
+#define IMX7D_SPDIF_ROOT_DIV           157
+#define IMX7D_ENET1_REF_ROOT_CLK       158
+#define IMX7D_ENET1_REF_ROOT_SRC       159
+#define IMX7D_ENET1_REF_ROOT_CG                160
+#define IMX7D_ENET1_REF_ROOT_DIV       161
+#define IMX7D_ENET1_TIME_ROOT_CLK      162
+#define IMX7D_ENET1_TIME_ROOT_SRC      163
+#define IMX7D_ENET1_TIME_ROOT_CG       164
+#define IMX7D_ENET1_TIME_ROOT_DIV      165
+#define IMX7D_ENET2_REF_ROOT_CLK       166
+#define IMX7D_ENET2_REF_ROOT_SRC       167
+#define IMX7D_ENET2_REF_ROOT_CG                168
+#define IMX7D_ENET2_REF_ROOT_DIV       169
+#define IMX7D_ENET2_TIME_ROOT_CLK      170
+#define IMX7D_ENET2_TIME_ROOT_SRC      171
+#define IMX7D_ENET2_TIME_ROOT_CG       172
+#define IMX7D_ENET2_TIME_ROOT_DIV      173
+#define IMX7D_ENET_PHY_REF_ROOT_CLK    174
+#define IMX7D_ENET_PHY_REF_ROOT_SRC    175
+#define IMX7D_ENET_PHY_REF_ROOT_CG     176
+#define IMX7D_ENET_PHY_REF_ROOT_DIV    177
+#define IMX7D_EIM_ROOT_CLK             178
+#define IMX7D_EIM_ROOT_SRC             179
+#define IMX7D_EIM_ROOT_CG              180
+#define IMX7D_EIM_ROOT_DIV             181
+#define IMX7D_NAND_ROOT_CLK            182
+#define IMX7D_NAND_ROOT_SRC            183
+#define IMX7D_NAND_ROOT_CG             184
+#define IMX7D_NAND_ROOT_DIV            185
+#define IMX7D_QSPI_ROOT_CLK            186
+#define IMX7D_QSPI_ROOT_SRC            187
+#define IMX7D_QSPI_ROOT_CG             188
+#define IMX7D_QSPI_ROOT_DIV            189
+#define IMX7D_USDHC1_ROOT_CLK          190
+#define IMX7D_USDHC1_ROOT_SRC          191
+#define IMX7D_USDHC1_ROOT_CG           192
+#define IMX7D_USDHC1_ROOT_DIV          193
+#define IMX7D_USDHC2_ROOT_CLK          194
+#define IMX7D_USDHC2_ROOT_SRC          195
+#define IMX7D_USDHC2_ROOT_CG           196
+#define IMX7D_USDHC2_ROOT_DIV          197
+#define IMX7D_USDHC3_ROOT_CLK          198
+#define IMX7D_USDHC3_ROOT_SRC          199
+#define IMX7D_USDHC3_ROOT_CG           200
+#define IMX7D_USDHC3_ROOT_DIV          201
+#define IMX7D_CAN1_ROOT_CLK            202
+#define IMX7D_CAN1_ROOT_SRC            203
+#define IMX7D_CAN1_ROOT_CG             204
+#define IMX7D_CAN1_ROOT_DIV            205
+#define IMX7D_CAN2_ROOT_CLK            206
+#define IMX7D_CAN2_ROOT_SRC            207
+#define IMX7D_CAN2_ROOT_CG             208
+#define IMX7D_CAN2_ROOT_DIV            209
+#define IMX7D_I2C1_ROOT_CLK            210
+#define IMX7D_I2C1_ROOT_SRC            211
+#define IMX7D_I2C1_ROOT_CG             212
+#define IMX7D_I2C1_ROOT_DIV            213
+#define IMX7D_I2C2_ROOT_CLK            214
+#define IMX7D_I2C2_ROOT_SRC            215
+#define IMX7D_I2C2_ROOT_CG             216
+#define IMX7D_I2C2_ROOT_DIV            217
+#define IMX7D_I2C3_ROOT_CLK            218
+#define IMX7D_I2C3_ROOT_SRC            219
+#define IMX7D_I2C3_ROOT_CG             220
+#define IMX7D_I2C3_ROOT_DIV            221
+#define IMX7D_I2C4_ROOT_CLK            222
+#define IMX7D_I2C4_ROOT_SRC            223
+#define IMX7D_I2C4_ROOT_CG             224
+#define IMX7D_I2C4_ROOT_DIV            225
+#define IMX7D_UART1_ROOT_CLK           226
+#define IMX7D_UART1_ROOT_SRC           227
+#define IMX7D_UART1_ROOT_CG            228
+#define IMX7D_UART1_ROOT_DIV           229
+#define IMX7D_UART2_ROOT_CLK           230
+#define IMX7D_UART2_ROOT_SRC           231
+#define IMX7D_UART2_ROOT_CG            232
+#define IMX7D_UART2_ROOT_DIV           233
+#define IMX7D_UART3_ROOT_CLK           234
+#define IMX7D_UART3_ROOT_SRC           235
+#define IMX7D_UART3_ROOT_CG            236
+#define IMX7D_UART3_ROOT_DIV           237
+#define IMX7D_UART4_ROOT_CLK           238
+#define IMX7D_UART4_ROOT_SRC           239
+#define IMX7D_UART4_ROOT_CG            240
+#define IMX7D_UART4_ROOT_DIV           241
+#define IMX7D_UART5_ROOT_CLK           242
+#define IMX7D_UART5_ROOT_SRC           243
+#define IMX7D_UART5_ROOT_CG            244
+#define IMX7D_UART5_ROOT_DIV           245
+#define IMX7D_UART6_ROOT_CLK           246
+#define IMX7D_UART6_ROOT_SRC           247
+#define IMX7D_UART6_ROOT_CG            248
+#define IMX7D_UART6_ROOT_DIV           249
+#define IMX7D_UART7_ROOT_CLK           250
+#define IMX7D_UART7_ROOT_SRC           251
+#define IMX7D_UART7_ROOT_CG            252
+#define IMX7D_UART7_ROOT_DIV           253
+#define IMX7D_ECSPI1_ROOT_CLK          254
+#define IMX7D_ECSPI1_ROOT_SRC          255
+#define IMX7D_ECSPI1_ROOT_CG           256
+#define IMX7D_ECSPI1_ROOT_DIV          257
+#define IMX7D_ECSPI2_ROOT_CLK          258
+#define IMX7D_ECSPI2_ROOT_SRC          259
+#define IMX7D_ECSPI2_ROOT_CG           260
+#define IMX7D_ECSPI2_ROOT_DIV          261
+#define IMX7D_ECSPI3_ROOT_CLK          262
+#define IMX7D_ECSPI3_ROOT_SRC          263
+#define IMX7D_ECSPI3_ROOT_CG           264
+#define IMX7D_ECSPI3_ROOT_DIV          265
+#define IMX7D_ECSPI4_ROOT_CLK          266
+#define IMX7D_ECSPI4_ROOT_SRC          267
+#define IMX7D_ECSPI4_ROOT_CG           268
+#define IMX7D_ECSPI4_ROOT_DIV          269
+#define IMX7D_PWM1_ROOT_CLK            270
+#define IMX7D_PWM1_ROOT_SRC            271
+#define IMX7D_PWM1_ROOT_CG             272
+#define IMX7D_PWM1_ROOT_DIV            273
+#define IMX7D_PWM2_ROOT_CLK            274
+#define IMX7D_PWM2_ROOT_SRC            275
+#define IMX7D_PWM2_ROOT_CG             276
+#define IMX7D_PWM2_ROOT_DIV            277
+#define IMX7D_PWM3_ROOT_CLK            278
+#define IMX7D_PWM3_ROOT_SRC            279
+#define IMX7D_PWM3_ROOT_CG             280
+#define IMX7D_PWM3_ROOT_DIV            281
+#define IMX7D_PWM4_ROOT_CLK            282
+#define IMX7D_PWM4_ROOT_SRC            283
+#define IMX7D_PWM4_ROOT_CG             284
+#define IMX7D_PWM4_ROOT_DIV            285
+#define IMX7D_FLEXTIMER1_ROOT_CLK      286
+#define IMX7D_FLEXTIMER1_ROOT_SRC      287
+#define IMX7D_FLEXTIMER1_ROOT_CG       288
+#define IMX7D_FLEXTIMER1_ROOT_DIV      289
+#define IMX7D_FLEXTIMER2_ROOT_CLK      290
+#define IMX7D_FLEXTIMER2_ROOT_SRC      291
+#define IMX7D_FLEXTIMER2_ROOT_CG       292
+#define IMX7D_FLEXTIMER2_ROOT_DIV      293
+#define IMX7D_SIM1_ROOT_CLK            294
+#define IMX7D_SIM1_ROOT_SRC            295
+#define IMX7D_SIM1_ROOT_CG             296
+#define IMX7D_SIM1_ROOT_DIV            297
+#define IMX7D_SIM2_ROOT_CLK            298
+#define IMX7D_SIM2_ROOT_SRC            299
+#define IMX7D_SIM2_ROOT_CG             300
+#define IMX7D_SIM2_ROOT_DIV            301
+#define IMX7D_GPT1_ROOT_CLK            302
+#define IMX7D_GPT1_ROOT_SRC            303
+#define IMX7D_GPT1_ROOT_CG             304
+#define IMX7D_GPT1_ROOT_DIV            305
+#define IMX7D_GPT2_ROOT_CLK            306
+#define IMX7D_GPT2_ROOT_SRC            307
+#define IMX7D_GPT2_ROOT_CG             308
+#define IMX7D_GPT2_ROOT_DIV            309
+#define IMX7D_GPT3_ROOT_CLK            310
+#define IMX7D_GPT3_ROOT_SRC            311
+#define IMX7D_GPT3_ROOT_CG             312
+#define IMX7D_GPT3_ROOT_DIV            313
+#define IMX7D_GPT4_ROOT_CLK            314
+#define IMX7D_GPT4_ROOT_SRC            315
+#define IMX7D_GPT4_ROOT_CG             316
+#define IMX7D_GPT4_ROOT_DIV            317
+#define IMX7D_TRACE_ROOT_CLK           318
+#define IMX7D_TRACE_ROOT_SRC           319
+#define IMX7D_TRACE_ROOT_CG            320
+#define IMX7D_TRACE_ROOT_DIV           321
+#define IMX7D_WDOG1_ROOT_CLK           322
+#define IMX7D_WDOG_ROOT_SRC            323
+#define IMX7D_WDOG_ROOT_CG             324
+#define IMX7D_WDOG_ROOT_DIV            325
+#define IMX7D_CSI_MCLK_ROOT_CLK                326
+#define IMX7D_CSI_MCLK_ROOT_SRC                327
+#define IMX7D_CSI_MCLK_ROOT_CG         328
+#define IMX7D_CSI_MCLK_ROOT_DIV                329
+#define IMX7D_AUDIO_MCLK_ROOT_CLK      330
+#define IMX7D_AUDIO_MCLK_ROOT_SRC      331
+#define IMX7D_AUDIO_MCLK_ROOT_CG       332
+#define IMX7D_AUDIO_MCLK_ROOT_DIV      333
+#define IMX7D_WRCLK_ROOT_CLK           334
+#define IMX7D_WRCLK_ROOT_SRC           335
+#define IMX7D_WRCLK_ROOT_CG            336
+#define IMX7D_WRCLK_ROOT_DIV           337
+#define IMX7D_CLKO1_ROOT_SRC           338
+#define IMX7D_CLKO1_ROOT_CG            339
+#define IMX7D_CLKO1_ROOT_DIV           340
+#define IMX7D_CLKO2_ROOT_SRC           341
+#define IMX7D_CLKO2_ROOT_CG            342
+#define IMX7D_CLKO2_ROOT_DIV           343
+#define IMX7D_MAIN_AXI_ROOT_PRE_DIV    344
+#define IMX7D_DISP_AXI_ROOT_PRE_DIV    345
+#define IMX7D_ENET_AXI_ROOT_PRE_DIV    346
+#define IMX7D_NAND_USDHC_BUS_ROOT_PRE_DIV 347
+#define IMX7D_AHB_CHANNEL_ROOT_PRE_DIV 348
+#define IMX7D_USB_HSIC_ROOT_PRE_DIV    349
+#define IMX7D_PCIE_CTRL_ROOT_PRE_DIV   350
+#define IMX7D_PCIE_PHY_ROOT_PRE_DIV    351
+#define IMX7D_EPDC_PIXEL_ROOT_PRE_DIV  352
+#define IMX7D_LCDIF_PIXEL_ROOT_PRE_DIV 353
+#define IMX7D_MIPI_DSI_ROOT_PRE_DIV    354
+#define IMX7D_MIPI_CSI_ROOT_PRE_DIV    355
+#define IMX7D_MIPI_DPHY_ROOT_PRE_DIV   356
+#define IMX7D_SAI1_ROOT_PRE_DIV                357
+#define IMX7D_SAI2_ROOT_PRE_DIV                358
+#define IMX7D_SAI3_ROOT_PRE_DIV                359
+#define IMX7D_SPDIF_ROOT_PRE_DIV       360
+#define IMX7D_ENET1_REF_ROOT_PRE_DIV   361
+#define IMX7D_ENET1_TIME_ROOT_PRE_DIV  362
+#define IMX7D_ENET2_REF_ROOT_PRE_DIV   363
+#define IMX7D_ENET2_TIME_ROOT_PRE_DIV  364
+#define IMX7D_ENET_PHY_REF_ROOT_PRE_DIV 365
+#define IMX7D_EIM_ROOT_PRE_DIV         366
+#define IMX7D_NAND_ROOT_PRE_DIV                367
+#define IMX7D_QSPI_ROOT_PRE_DIV                368
+#define IMX7D_USDHC1_ROOT_PRE_DIV      369
+#define IMX7D_USDHC2_ROOT_PRE_DIV      370
+#define IMX7D_USDHC3_ROOT_PRE_DIV      371
+#define IMX7D_CAN1_ROOT_PRE_DIV                372
+#define IMX7D_CAN2_ROOT_PRE_DIV                373
+#define IMX7D_I2C1_ROOT_PRE_DIV                374
+#define IMX7D_I2C2_ROOT_PRE_DIV                375
+#define IMX7D_I2C3_ROOT_PRE_DIV                376
+#define IMX7D_I2C4_ROOT_PRE_DIV                377
+#define IMX7D_UART1_ROOT_PRE_DIV       378
+#define IMX7D_UART2_ROOT_PRE_DIV       379
+#define IMX7D_UART3_ROOT_PRE_DIV       380
+#define IMX7D_UART4_ROOT_PRE_DIV       381
+#define IMX7D_UART5_ROOT_PRE_DIV       382
+#define IMX7D_UART6_ROOT_PRE_DIV       383
+#define IMX7D_UART7_ROOT_PRE_DIV       384
+#define IMX7D_ECSPI1_ROOT_PRE_DIV      385
+#define IMX7D_ECSPI2_ROOT_PRE_DIV      386
+#define IMX7D_ECSPI3_ROOT_PRE_DIV      387
+#define IMX7D_ECSPI4_ROOT_PRE_DIV      388
+#define IMX7D_PWM1_ROOT_PRE_DIV                389
+#define IMX7D_PWM2_ROOT_PRE_DIV                390
+#define IMX7D_PWM3_ROOT_PRE_DIV                391
+#define IMX7D_PWM4_ROOT_PRE_DIV                392
+#define IMX7D_FLEXTIMER1_ROOT_PRE_DIV  393
+#define IMX7D_FLEXTIMER2_ROOT_PRE_DIV  394
+#define IMX7D_SIM1_ROOT_PRE_DIV                395
+#define IMX7D_SIM2_ROOT_PRE_DIV                396
+#define IMX7D_GPT1_ROOT_PRE_DIV                397
+#define IMX7D_GPT2_ROOT_PRE_DIV                398
+#define IMX7D_GPT3_ROOT_PRE_DIV                399
+#define IMX7D_GPT4_ROOT_PRE_DIV                400
+#define IMX7D_TRACE_ROOT_PRE_DIV       401
+#define IMX7D_WDOG_ROOT_PRE_DIV                402
+#define IMX7D_CSI_MCLK_ROOT_PRE_DIV    403
+#define IMX7D_AUDIO_MCLK_ROOT_PRE_DIV  404
+#define IMX7D_WRCLK_ROOT_PRE_DIV       405
+#define IMX7D_CLKO1_ROOT_PRE_DIV       406
+#define IMX7D_CLKO2_ROOT_PRE_DIV       407
+#define IMX7D_DRAM_PHYM_ALT_ROOT_PRE_DIV 408
+#define IMX7D_DRAM_ALT_ROOT_PRE_DIV    409
+#define IMX7D_LVDS1_IN_CLK             410
+#define IMX7D_LVDS1_OUT_SEL            411
+#define IMX7D_LVDS1_OUT_CLK            412
+#define IMX7D_CLK_DUMMY                        413
+#define IMX7D_GPT_3M_CLK               414
+#define IMX7D_OCRAM_CLK                        415
+#define IMX7D_OCRAM_S_CLK              416
+#define IMX7D_WDOG2_ROOT_CLK           417
+#define IMX7D_WDOG3_ROOT_CLK           418
+#define IMX7D_WDOG4_ROOT_CLK           419
+#define IMX7D_SDMA_CORE_CLK            420
+#define IMX7D_USB1_MAIN_480M_CLK       421
+#define IMX7D_USB_CTRL_CLK             422
+#define IMX7D_USB_PHY1_CLK             423
+#define IMX7D_USB_PHY2_CLK             424
+#define IMX7D_IPG_ROOT_CLK             425
+#define IMX7D_SAI1_IPG_CLK             426
+#define IMX7D_SAI2_IPG_CLK             427
+#define IMX7D_SAI3_IPG_CLK             428
+#define IMX7D_PLL_AUDIO_TEST_DIV       429
+#define IMX7D_PLL_AUDIO_POST_DIV       430
+#define IMX7D_PLL_VIDEO_TEST_DIV       431
+#define IMX7D_PLL_VIDEO_POST_DIV       432
+#define IMX7D_MU_ROOT_CLK              433
+#define IMX7D_SEMA4_HS_ROOT_CLK                434
+#define IMX7D_PLL_DRAM_TEST_DIV                435
+#define IMX7D_CLK_END                  436
+#endif /* __DT_BINDINGS_CLOCK_IMX7D_H */
index 979d24a6799f052df426ea3400413c71aa0efbd0..d19763439472237589e216dd64d3b10863682259 100644 (file)
 #define VF610_PLL6_BYPASS              180
 #define VF610_PLL7_BYPASS              181
 #define VF610_CLK_SNVS                 182
-#define VF610_CLK_END                  183
+#define VF610_CLK_DAP                  183
+#define VF610_CLK_END                  184
 
 #endif /* __DT_BINDINGS_CLOCK_VF610_H */
diff --git a/include/dt-bindings/clock/zx296702-clock.h b/include/dt-bindings/clock/zx296702-clock.h
new file mode 100644 (file)
index 0000000..e683dbb
--- /dev/null
@@ -0,0 +1,170 @@
+/*
+ * Copyright 2014 Linaro Ltd.
+ * Copyright (C) 2014 ZTE Corporation.
+ *
+ * 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.
+ */
+
+#ifndef __DT_BINDINGS_CLOCK_ZX296702_H
+#define __DT_BINDINGS_CLOCK_ZX296702_H
+
+#define ZX296702_OSC                           0
+#define ZX296702_PLL_A9                                1
+#define ZX296702_PLL_A9_350M                   2
+#define ZX296702_PLL_MAC_1000M                 3
+#define ZX296702_PLL_MAC_333M                  4
+#define ZX296702_PLL_MM0_1188M                 5
+#define ZX296702_PLL_MM0_396M                  6
+#define ZX296702_PLL_MM0_198M                  7
+#define ZX296702_PLL_MM1_108M                  8
+#define ZX296702_PLL_MM1_72M                   9
+#define ZX296702_PLL_MM1_54M                   10
+#define ZX296702_PLL_LSP_104M                  11
+#define ZX296702_PLL_LSP_26M                   12
+#define ZX296702_PLL_AUDIO_294M912             13
+#define ZX296702_PLL_DDR_266M                  14
+#define ZX296702_CLK_148M5                     15
+#define ZX296702_MATRIX_ACLK                   16
+#define ZX296702_MAIN_HCLK                     17
+#define ZX296702_MAIN_PCLK                     18
+#define ZX296702_CLK_500                       19
+#define ZX296702_CLK_250                       20
+#define ZX296702_CLK_125                       21
+#define ZX296702_CLK_74M25                     22
+#define ZX296702_A9_WCLK                       23
+#define ZX296702_A9_AS1_ACLK_MUX               24
+#define ZX296702_A9_TRACE_CLKIN_MUX            25
+#define ZX296702_A9_AS1_ACLK_DIV               26
+#define ZX296702_CLK_2                         27
+#define ZX296702_CLK_27                                28
+#define ZX296702_DECPPU_ACLK_MUX               29
+#define ZX296702_PPU_ACLK_MUX                  30
+#define ZX296702_MALI400_ACLK_MUX              31
+#define ZX296702_VOU_ACLK_MUX                  32
+#define ZX296702_VOU_MAIN_WCLK_MUX             33
+#define ZX296702_VOU_AUX_WCLK_MUX              34
+#define ZX296702_VOU_SCALER_WCLK_MUX           35
+#define ZX296702_R2D_ACLK_MUX                  36
+#define ZX296702_R2D_WCLK_MUX                  37
+#define ZX296702_CLK_50                                38
+#define ZX296702_CLK_25                                39
+#define ZX296702_CLK_12                                40
+#define ZX296702_CLK_16M384                    41
+#define ZX296702_CLK_32K768                    42
+#define ZX296702_SEC_WCLK_DIV                  43
+#define ZX296702_DDR_WCLK_MUX                  44
+#define ZX296702_NAND_WCLK_MUX                 45
+#define ZX296702_LSP_26_WCLK_MUX               46
+#define ZX296702_A9_AS0_ACLK                   47
+#define ZX296702_A9_AS1_ACLK                   48
+#define ZX296702_A9_TRACE_CLKIN                        49
+#define ZX296702_DECPPU_AXI_M_ACLK             50
+#define ZX296702_DECPPU_AHB_S_HCLK             51
+#define ZX296702_PPU_AXI_M_ACLK                        52
+#define ZX296702_PPU_AHB_S_HCLK                        53
+#define ZX296702_VOU_AXI_M_ACLK                        54
+#define ZX296702_VOU_APB_PCLK                  55
+#define ZX296702_VOU_MAIN_CHANNEL_WCLK         56
+#define ZX296702_VOU_AUX_CHANNEL_WCLK          57
+#define ZX296702_VOU_HDMI_OSCLK_CEC            58
+#define ZX296702_VOU_SCALER_WCLK               59
+#define ZX296702_MALI400_AXI_M_ACLK            60
+#define ZX296702_MALI400_APB_PCLK              61
+#define ZX296702_R2D_WCLK                      62
+#define ZX296702_R2D_AXI_M_ACLK                        63
+#define ZX296702_R2D_AHB_HCLK                  64
+#define ZX296702_DDR3_AXI_S0_ACLK              65
+#define ZX296702_DDR3_APB_PCLK                 66
+#define ZX296702_DDR3_WCLK                     67
+#define ZX296702_USB20_0_AHB_HCLK              68
+#define ZX296702_USB20_0_EXTREFCLK             69
+#define ZX296702_USB20_1_AHB_HCLK              70
+#define ZX296702_USB20_1_EXTREFCLK             71
+#define ZX296702_USB20_2_AHB_HCLK              72
+#define ZX296702_USB20_2_EXTREFCLK             73
+#define ZX296702_GMAC_AXI_M_ACLK               74
+#define ZX296702_GMAC_APB_PCLK                 75
+#define ZX296702_GMAC_125_CLKIN                        76
+#define ZX296702_GMAC_RMII_CLKIN               77
+#define ZX296702_GMAC_25M_CLK                  78
+#define ZX296702_NANDFLASH_AHB_HCLK            79
+#define ZX296702_NANDFLASH_WCLK                        80
+#define ZX296702_LSP0_APB_PCLK                 81
+#define ZX296702_LSP0_AHB_HCLK                 82
+#define ZX296702_LSP0_26M_WCLK                 83
+#define ZX296702_LSP0_104M_WCLK                        84
+#define ZX296702_LSP0_16M384_WCLK              85
+#define ZX296702_LSP1_APB_PCLK                 86
+#define ZX296702_LSP1_26M_WCLK                 87
+#define ZX296702_LSP1_104M_WCLK                        88
+#define ZX296702_LSP1_32K_CLK                  89
+#define ZX296702_AON_HCLK                      90
+#define ZX296702_SYS_CTRL_PCLK                 91
+#define ZX296702_DMA_PCLK                      92
+#define ZX296702_DMA_ACLK                      93
+#define ZX296702_SEC_HCLK                      94
+#define ZX296702_AES_WCLK                      95
+#define ZX296702_DES_WCLK                      96
+#define ZX296702_IRAM_ACLK                     97
+#define ZX296702_IROM_ACLK                     98
+#define ZX296702_BOOT_CTRL_HCLK                        99
+#define ZX296702_EFUSE_CLK_30                  100
+#define ZX296702_VOU_MAIN_CHANNEL_DIV          101
+#define ZX296702_VOU_AUX_CHANNEL_DIV           102
+#define ZX296702_VOU_TV_ENC_HD_DIV             103
+#define ZX296702_VOU_TV_ENC_SD_DIV             104
+#define ZX296702_VL0_MUX                       105
+#define ZX296702_VL1_MUX                       106
+#define ZX296702_VL2_MUX                       107
+#define ZX296702_GL0_MUX                       108
+#define ZX296702_GL1_MUX                       109
+#define ZX296702_GL2_MUX                       110
+#define ZX296702_WB_MUX                                111
+#define ZX296702_HDMI_MUX                      112
+#define ZX296702_VOU_TV_ENC_HD_MUX             113
+#define ZX296702_VOU_TV_ENC_SD_MUX             114
+#define ZX296702_VL0_CLK                       115
+#define ZX296702_VL1_CLK                       116
+#define ZX296702_VL2_CLK                       117
+#define ZX296702_GL0_CLK                       118
+#define ZX296702_GL1_CLK                       119
+#define ZX296702_GL2_CLK                       120
+#define ZX296702_WB_CLK                                121
+#define ZX296702_CL_CLK                                122
+#define ZX296702_MAIN_MIX_CLK                  123
+#define ZX296702_AUX_MIX_CLK                   124
+#define ZX296702_HDMI_CLK                      125
+#define ZX296702_VOU_TV_ENC_HD_DAC_CLK         126
+#define ZX296702_VOU_TV_ENC_SD_DAC_CLK         127
+#define ZX296702_A9_PERIPHCLK                  128
+#define ZX296702_TOPCLK_END                    129
+
+#define ZX296702_SDMMC1_WCLK_MUX               0
+#define ZX296702_SDMMC1_WCLK_DIV               1
+#define ZX296702_SDMMC1_WCLK                   2
+#define ZX296702_SDMMC1_PCLK                   3
+#define ZX296702_SPDIF0_WCLK_MUX               4
+#define ZX296702_SPDIF0_WCLK                   5
+#define ZX296702_SPDIF0_PCLK                   6
+#define ZX296702_SPDIF0_DIV                    7
+#define ZX296702_I2S0_WCLK_MUX                 8
+#define ZX296702_I2S0_WCLK                     9
+#define ZX296702_I2S0_PCLK                     10
+#define ZX296702_I2S0_DIV                      11
+#define ZX296702_LSP0CLK_END                   12
+
+#define ZX296702_UART0_WCLK_MUX                        0
+#define ZX296702_UART0_WCLK                    1
+#define ZX296702_UART0_PCLK                    2
+#define ZX296702_UART1_WCLK_MUX                        3
+#define ZX296702_UART1_WCLK                    4
+#define ZX296702_UART1_PCLK                    5
+#define ZX296702_SDMMC0_WCLK_MUX               6
+#define ZX296702_SDMMC0_WCLK_DIV               7
+#define ZX296702_SDMMC0_WCLK                   8
+#define ZX296702_SDMMC0_PCLK                   9
+#define ZX296702_LSP1CLK_END                   10
+
+#endif /* __DT_BINDINGS_CLOCK_ZX296702_H */
index 62c6901cab550d7f57039c5b7052fc08bbe0964d..2633061364b1d1215ba117e1e6238f87431b011d 100644 (file)
@@ -458,6 +458,8 @@ extern void handle_nested_irq(unsigned int irq);
 
 extern int irq_chip_compose_msi_msg(struct irq_data *data, struct msi_msg *msg);
 #ifdef CONFIG_IRQ_DOMAIN_HIERARCHY
+extern void irq_chip_enable_parent(struct irq_data *data);
+extern void irq_chip_disable_parent(struct irq_data *data);
 extern void irq_chip_ack_parent(struct irq_data *data);
 extern int irq_chip_retrigger_hierarchy(struct irq_data *data);
 extern void irq_chip_mask_parent(struct irq_data *data);
index 676d7306a3609cc9aaccb090f71000f965f0e3bd..744ac0ec98eb2c9e094f8ebdcfd71aebcdd32026 100644 (file)
@@ -258,6 +258,10 @@ int irq_domain_xlate_onetwocell(struct irq_domain *d, struct device_node *ctrlr,
 /* V2 interfaces to support hierarchy IRQ domains. */
 extern struct irq_data *irq_domain_get_irq_data(struct irq_domain *domain,
                                                unsigned int virq);
+extern void irq_domain_set_info(struct irq_domain *domain, unsigned int virq,
+                               irq_hw_number_t hwirq, struct irq_chip *chip,
+                               void *chip_data, irq_flow_handler_t handler,
+                               void *handler_data, const char *handler_name);
 #ifdef CONFIG_IRQ_DOMAIN_HIERARCHY
 extern struct irq_domain *irq_domain_add_hierarchy(struct irq_domain *parent,
                        unsigned int flags, unsigned int size,
@@ -281,10 +285,6 @@ extern int irq_domain_set_hwirq_and_chip(struct irq_domain *domain,
                                         irq_hw_number_t hwirq,
                                         struct irq_chip *chip,
                                         void *chip_data);
-extern void irq_domain_set_info(struct irq_domain *domain, unsigned int virq,
-                               irq_hw_number_t hwirq, struct irq_chip *chip,
-                               void *chip_data, irq_flow_handler_t handler,
-                               void *handler_data, const char *handler_name);
 extern void irq_domain_reset_irq_data(struct irq_data *irq_data);
 extern void irq_domain_free_irqs_common(struct irq_domain *domain,
                                        unsigned int virq,
diff --git a/include/linux/reset/bcm63xx_pmb.h b/include/linux/reset/bcm63xx_pmb.h
new file mode 100644 (file)
index 0000000..bb4af7b
--- /dev/null
@@ -0,0 +1,88 @@
+/*
+ * Broadcom BCM63xx Processor Monitor Bus shared routines (SMP and reset)
+ *
+ * Copyright (C) 2015, Broadcom Corporation
+ * Author: Florian Fainelli <f.fainelli@gmail.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation version 2.
+ *
+ * This program is distributed "as is" WITHOUT ANY WARRANTY of any
+ * kind, whether express or implied; without even the implied warranty
+ * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+#ifndef __BCM63XX_PMB_H
+#define __BCM63XX_PMB_H
+
+#include <linux/io.h>
+#include <linux/types.h>
+#include <linux/delay.h>
+#include <linux/err.h>
+
+/* PMB Master controller register */
+#define PMB_CTRL               0x00
+#define  PMC_PMBM_START                (1 << 31)
+#define  PMC_PMBM_TIMEOUT      (1 << 30)
+#define  PMC_PMBM_SLAVE_ERR    (1 << 29)
+#define  PMC_PMBM_BUSY         (1 << 28)
+#define  PMC_PMBM_READ         (0 << 20)
+#define  PMC_PMBM_WRITE                (1 << 20)
+#define PMB_WR_DATA            0x04
+#define PMB_TIMEOUT            0x08
+#define PMB_RD_DATA            0x0C
+
+#define PMB_BUS_ID_SHIFT       8
+
+/* Perform the low-level PMB master operation, shared between reads and
+ * writes.
+ */
+static inline int __bpcm_do_op(void __iomem *master, unsigned int addr,
+                              u32 off, u32 op)
+{
+       unsigned int timeout = 1000;
+       u32 cmd;
+
+       cmd = (PMC_PMBM_START | op | (addr & 0xff) << 12 | off);
+       writel(cmd, master + PMB_CTRL);
+       do {
+               cmd = readl(master + PMB_CTRL);
+               if (!(cmd & PMC_PMBM_START))
+                       return 0;
+
+               if (cmd & PMC_PMBM_SLAVE_ERR)
+                       return -EIO;
+
+               if (cmd & PMC_PMBM_TIMEOUT)
+                       return -ETIMEDOUT;
+
+               udelay(1);
+       } while (timeout-- > 0);
+
+       return -ETIMEDOUT;
+}
+
+static inline int bpcm_rd(void __iomem *master, unsigned int addr,
+                         u32 off, u32 *val)
+{
+       int ret = 0;
+
+       ret = __bpcm_do_op(master, addr, off >> 2, PMC_PMBM_READ);
+       *val = readl(master + PMB_RD_DATA);
+
+       return ret;
+}
+
+static inline int bpcm_wr(void __iomem *master, unsigned int addr,
+                         u32 off, u32 val)
+{
+       int ret = 0;
+
+       writel(val, master + PMB_WR_DATA);
+       ret = __bpcm_do_op(master, addr, off >> 2, PMC_PMBM_WRITE);
+
+       return ret;
+}
+
+#endif /* __BCM63XX_PMB_H */
diff --git a/include/soc/imx/revision.h b/include/soc/imx/revision.h
new file mode 100644 (file)
index 0000000..9ea3469
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ * Copyright 2015 Linaro Ltd.
+ *
+ * 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.
+ */
+
+#ifndef __SOC_IMX_REVISION_H__
+#define __SOC_IMX_REVISION_H__
+
+#define IMX_CHIP_REVISION_1_0          0x10
+#define IMX_CHIP_REVISION_1_1          0x11
+#define IMX_CHIP_REVISION_1_2          0x12
+#define IMX_CHIP_REVISION_1_3          0x13
+#define IMX_CHIP_REVISION_1_4          0x14
+#define IMX_CHIP_REVISION_1_5          0x15
+#define IMX_CHIP_REVISION_2_0          0x20
+#define IMX_CHIP_REVISION_2_1          0x21
+#define IMX_CHIP_REVISION_2_2          0x22
+#define IMX_CHIP_REVISION_2_3          0x23
+#define IMX_CHIP_REVISION_3_0          0x30
+#define IMX_CHIP_REVISION_3_1          0x31
+#define IMX_CHIP_REVISION_3_2          0x32
+#define IMX_CHIP_REVISION_3_3          0x33
+#define IMX_CHIP_REVISION_UNKNOWN      0xff
+
+int mx27_revision(void);
+int mx31_revision(void);
+int mx35_revision(void);
+int mx51_revision(void);
+int mx53_revision(void);
+
+unsigned int imx_get_soc_revision(void);
+void imx_print_silicon_rev(const char *cpu, int srev);
+
+#endif /* __SOC_IMX_REVISION_H__ */
diff --git a/include/soc/imx/timer.h b/include/soc/imx/timer.h
new file mode 100644 (file)
index 0000000..bbbafd6
--- /dev/null
@@ -0,0 +1,26 @@
+/*
+ * Copyright 2015 Linaro Ltd.
+ *
+ * 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.
+ */
+
+#ifndef __SOC_IMX_TIMER_H__
+#define __SOC_IMX_TIMER_H__
+
+enum imx_gpt_type {
+       GPT_TYPE_IMX1,          /* i.MX1 */
+       GPT_TYPE_IMX21,         /* i.MX21/27 */
+       GPT_TYPE_IMX31,         /* i.MX31/35/25/37/51/6Q */
+       GPT_TYPE_IMX6DL,        /* i.MX6DL/SX/SL */
+};
+
+/*
+ * This is a stop-gap solution for clock drivers like imx1/imx21 which call
+ * mxc_timer_init() to initialize timer for non-DT boot.  It can be removed
+ * when these legacy non-DT support is converted or dropped.
+ */
+void mxc_timer_init(unsigned long pbase, int irq, enum imx_gpt_type type);
+
+#endif  /* __SOC_IMX_TIMER_H__ */
index 65a93273e72fe9d8f9ad5bc9358f734ab031e5ff..f5c0de43a5fad229b0c7cb2f5c82219210e6dec1 100644 (file)
@@ -26,8 +26,6 @@
 struct clk;
 struct reset_control;
 
-void tegra_pmc_restart(enum reboot_mode mode, const char *cmd);
-
 #ifdef CONFIG_PM_SLEEP
 enum tegra_suspend_mode tegra_pmc_get_suspend_mode(void);
 void tegra_pmc_set_suspend_mode(enum tegra_suspend_mode mode);
index e9b4cb0cd7edae5aaf029288db27fe56a8ff05c5..1e5ac4e776da77bdc2cc4f6ab6403d4d7b71f351 100644 (file)
  * Extra serial register definitions for the internal UARTs
  * in TI OMAP processors.
  */
+#define OMAP1_UART1_BASE       0xfffb0000
+#define OMAP1_UART2_BASE       0xfffb0800
+#define OMAP1_UART3_BASE       0xfffb9800
 #define UART_OMAP_MDR1         0x08    /* Mode definition register */
 #define UART_OMAP_MDR2         0x09    /* Mode definition register 2 */
 #define UART_OMAP_SCR          0x10    /* Supplementary control register */
index eb9a4ea394ab33fdde25420f11cb9021df384824..2456fe89719c5a732cdf82046178433ed3dd6239 100644 (file)
@@ -875,6 +875,34 @@ void irq_cpu_offline(void)
 }
 
 #ifdef CONFIG_IRQ_DOMAIN_HIERARCHY
+/**
+ * irq_chip_enable_parent - Enable the parent interrupt (defaults to unmask if
+ * NULL)
+ * @data:      Pointer to interrupt specific data
+ */
+void irq_chip_enable_parent(struct irq_data *data)
+{
+       data = data->parent_data;
+       if (data->chip->irq_enable)
+               data->chip->irq_enable(data);
+       else
+               data->chip->irq_unmask(data);
+}
+
+/**
+ * irq_chip_disable_parent - Disable the parent interrupt (defaults to mask if
+ * NULL)
+ * @data:      Pointer to interrupt specific data
+ */
+void irq_chip_disable_parent(struct irq_data *data)
+{
+       data = data->parent_data;
+       if (data->chip->irq_disable)
+               data->chip->irq_disable(data);
+       else
+               data->chip->irq_mask(data);
+}
+
 /**
  * irq_chip_ack_parent - Acknowledge the parent interrupt
  * @data:      Pointer to interrupt specific data
index 61024e8abdeffdeff717d389ddbe8fd99110532c..15b370daf23446d3a6b5213cbeac4d9559fb095d 100644 (file)
@@ -360,7 +360,7 @@ static struct lock_class_key irq_nested_lock_class;
 int irq_map_generic_chip(struct irq_domain *d, unsigned int virq,
                         irq_hw_number_t hw_irq)
 {
-       struct irq_data *data = irq_get_irq_data(virq);
+       struct irq_data *data = irq_domain_get_irq_data(d, virq);
        struct irq_domain_chip_generic *dgc = d->gc;
        struct irq_chip_generic *gc;
        struct irq_chip_type *ct;
@@ -405,8 +405,7 @@ int irq_map_generic_chip(struct irq_domain *d, unsigned int virq,
        else
                data->mask = 1 << idx;
 
-       irq_set_chip_and_handler(virq, chip, ct->handler);
-       irq_set_chip_data(virq, gc);
+       irq_domain_set_info(d, virq, hw_irq, chip, gc, ct->handler, NULL, NULL);
        irq_modify_status(virq, dgc->irq_flags_to_clear, dgc->irq_flags_to_set);
        return 0;
 }
index 7fac311057b806e7e6ba6c4634fac7151ace347b..41bf6dc49f59a6975cc4def14cf04af7a191226a 100644 (file)
@@ -1232,6 +1232,27 @@ struct irq_data *irq_domain_get_irq_data(struct irq_domain *domain,
        return (irq_data && irq_data->domain == domain) ? irq_data : NULL;
 }
 
+/**
+ * irq_domain_set_info - Set the complete data for a @virq in @domain
+ * @domain:            Interrupt domain to match
+ * @virq:              IRQ number
+ * @hwirq:             The hardware interrupt number
+ * @chip:              The associated interrupt chip
+ * @chip_data:         The associated interrupt chip data
+ * @handler:           The interrupt flow handler
+ * @handler_data:      The interrupt flow handler data
+ * @handler_name:      The interrupt handler name
+ */
+void irq_domain_set_info(struct irq_domain *domain, unsigned int virq,
+                        irq_hw_number_t hwirq, struct irq_chip *chip,
+                        void *chip_data, irq_flow_handler_t handler,
+                        void *handler_data, const char *handler_name)
+{
+       irq_set_chip_and_handler_name(virq, chip, handler, handler_name);
+       irq_set_chip_data(virq, chip_data);
+       irq_set_handler_data(virq, handler_data);
+}
+
 static void irq_domain_check_hierarchy(struct irq_domain *domain)
 {
 }